@mind-fold/open-flow 0.1.17 → 0.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/configurators/templates.d.ts.map +1 -1
- package/dist/configurators/templates.js +17 -6
- package/dist/configurators/templates.js.map +1 -1
- package/dist/configurators/workflow.d.ts.map +1 -1
- package/dist/configurators/workflow.js +82 -6
- package/dist/configurators/workflow.js.map +1 -1
- package/dist/templates/commands/break-loop.txt +107 -0
- package/dist/templates/commands/check-cross-layer.txt +153 -0
- package/dist/templates/commands/finish-work.txt +129 -0
- package/dist/templates/commands/index.d.ts +9 -5
- package/dist/templates/commands/index.d.ts.map +1 -1
- package/dist/templates/commands/index.js +16 -5
- package/dist/templates/commands/index.js.map +1 -1
- package/dist/templates/commands/init-agent.txt +100 -9
- package/dist/templates/commands/sync-from-runtime.txt +140 -0
- package/dist/templates/markdown/flow.md.txt +96 -84
- package/dist/templates/markdown/index.d.ts +21 -4
- package/dist/templates/markdown/index.d.ts.map +1 -1
- package/dist/templates/markdown/index.js +27 -4
- package/dist/templates/markdown/index.js.map +1 -1
- package/dist/templates/markdown/structure/backend/database-guidelines.md.txt +247 -0
- package/dist/templates/markdown/structure/backend/directory-structure.md.txt +153 -0
- package/dist/templates/markdown/structure/backend/error-handling.md.txt +257 -0
- package/dist/templates/markdown/structure/backend/index.md.txt +88 -0
- package/dist/templates/markdown/structure/backend/logging-guidelines.md.txt +212 -0
- package/dist/templates/markdown/structure/backend/quality-guidelines.md.txt +219 -0
- package/dist/templates/markdown/structure/backend/type-safety.md.txt +192 -0
- package/dist/templates/markdown/structure/flows/code-reuse-thinking-guide.md.txt +343 -0
- package/dist/templates/markdown/structure/flows/cross-layer-thinking-guide.md.txt +283 -0
- package/dist/templates/markdown/structure/flows/index.md.txt +133 -0
- package/dist/templates/markdown/structure/flows/pre-implementation-checklist.md.txt +182 -0
- package/dist/templates/markdown/structure/flows/spec-flow-template.md.txt +145 -0
- package/dist/templates/markdown/structure/frontend/component-guidelines.md.txt +335 -0
- package/dist/templates/markdown/structure/frontend/directory-structure.md.txt +172 -0
- package/dist/templates/markdown/structure/frontend/hook-guidelines.md.txt +287 -0
- package/dist/templates/markdown/structure/frontend/index.md.txt +91 -0
- package/dist/templates/markdown/structure/frontend/quality-guidelines.md.txt +274 -0
- package/dist/templates/markdown/structure/frontend/state-management.md.txt +293 -0
- package/dist/templates/markdown/structure/frontend/type-safety.md.txt +275 -0
- package/package.json +2 -2
|
@@ -0,0 +1,343 @@
|
|
|
1
|
+
# Code Reuse Thinking Guide
|
|
2
|
+
|
|
3
|
+
> **Purpose**: Help you notice patterns and reduce duplication before it becomes tech debt.
|
|
4
|
+
|
|
5
|
+
> **Related**: Before writing code, read the [Pre-Implementation Checklist](./pre-implementation-checklist.md) to catch reuse opportunities earlier.
|
|
6
|
+
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
## Why This Guide?
|
|
10
|
+
|
|
11
|
+
**Duplicated code is a symptom of "didn't think of abstraction".**
|
|
12
|
+
|
|
13
|
+
When you write similar code multiple times:
|
|
14
|
+
- Bugs need to be fixed in multiple places
|
|
15
|
+
- Changes require updating multiple files
|
|
16
|
+
- Inconsistencies creep in over time
|
|
17
|
+
- Codebase becomes harder to understand
|
|
18
|
+
|
|
19
|
+
This guide helps you **recognize reuse opportunities** before they become problems.
|
|
20
|
+
|
|
21
|
+
---
|
|
22
|
+
|
|
23
|
+
## The Core Question
|
|
24
|
+
|
|
25
|
+
Before writing code, ask:
|
|
26
|
+
|
|
27
|
+
> **"Is there a pattern here that already exists or should be abstracted?"**
|
|
28
|
+
|
|
29
|
+
---
|
|
30
|
+
|
|
31
|
+
## Pattern Recognition Checklist
|
|
32
|
+
|
|
33
|
+
### 1. Schema/Type Patterns
|
|
34
|
+
|
|
35
|
+
**Trigger**: You're defining a new type with common fields (success, error, etc.).
|
|
36
|
+
|
|
37
|
+
**Questions**:
|
|
38
|
+
- [ ] Is this the same structure as other types?
|
|
39
|
+
- [ ] Could a base type/schema be extended?
|
|
40
|
+
- [ ] Are there utility functions that could generate this?
|
|
41
|
+
|
|
42
|
+
**Example - Before**:
|
|
43
|
+
```typescript
|
|
44
|
+
// File 1, 2, 3... same pattern 30+ times
|
|
45
|
+
export const createUserOutput = z.object({
|
|
46
|
+
success: z.boolean(),
|
|
47
|
+
error: z.string().optional(),
|
|
48
|
+
user: userSchema.optional(),
|
|
49
|
+
});
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
**Example - After**:
|
|
53
|
+
```typescript
|
|
54
|
+
// common.ts - one abstraction
|
|
55
|
+
export function createOutputSchema<T extends z.ZodRawShape>(shape: T) {
|
|
56
|
+
return z.object({
|
|
57
|
+
success: z.boolean(),
|
|
58
|
+
error: z.string().optional(),
|
|
59
|
+
}).extend(shape);
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
// Usage
|
|
63
|
+
export const createUserOutput = createOutputSchema({ user: userSchema.optional() });
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
---
|
|
67
|
+
|
|
68
|
+
### 2. Function/Logic Patterns
|
|
69
|
+
|
|
70
|
+
**Trigger**: Writing a function that does something similar to existing code.
|
|
71
|
+
|
|
72
|
+
**Questions**:
|
|
73
|
+
- [ ] Is there a function that does 80% of what I need?
|
|
74
|
+
- [ ] Can I extract common logic and parameterize the difference?
|
|
75
|
+
|
|
76
|
+
**Example - Before**:
|
|
77
|
+
```typescript
|
|
78
|
+
// In multiple files
|
|
79
|
+
function createTodo(input) {
|
|
80
|
+
const parseResult = schema.safeParse(input);
|
|
81
|
+
if (!parseResult.success) {
|
|
82
|
+
return { success: false, error: formatError(parseResult.error) };
|
|
83
|
+
}
|
|
84
|
+
// ... specific logic
|
|
85
|
+
}
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
**Example - After**:
|
|
89
|
+
```typescript
|
|
90
|
+
// Shared validation wrapper
|
|
91
|
+
function withValidation<TInput, TOutput>(
|
|
92
|
+
schema: z.ZodSchema<TInput>,
|
|
93
|
+
handler: (input: TInput) => TOutput
|
|
94
|
+
) {
|
|
95
|
+
return (rawInput: unknown) => {
|
|
96
|
+
const parseResult = schema.safeParse(rawInput);
|
|
97
|
+
if (!parseResult.success) {
|
|
98
|
+
return { success: false, error: formatError(parseResult.error) };
|
|
99
|
+
}
|
|
100
|
+
return handler(parseResult.data);
|
|
101
|
+
};
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
// Usage - specific logic only
|
|
105
|
+
const createTodo = withValidation(todoSchema, (input) => { /* ... */ });
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
---
|
|
109
|
+
|
|
110
|
+
### 3. Component Patterns
|
|
111
|
+
|
|
112
|
+
**Trigger**: Creating a UI component similar to existing ones.
|
|
113
|
+
|
|
114
|
+
**Questions**:
|
|
115
|
+
- [ ] Is there a base component I can extend or compose?
|
|
116
|
+
- [ ] Are props similar to another component?
|
|
117
|
+
|
|
118
|
+
**Example - Before**:
|
|
119
|
+
```tsx
|
|
120
|
+
// TodoCard.tsx
|
|
121
|
+
<div className="rounded-lg border p-4 shadow-sm">
|
|
122
|
+
<h3>{todo.title}</h3>
|
|
123
|
+
<p>{todo.description}</p>
|
|
124
|
+
<Badge>{todo.status}</Badge>
|
|
125
|
+
</div>
|
|
126
|
+
|
|
127
|
+
// JournalCard.tsx (almost identical)
|
|
128
|
+
<div className="rounded-lg border p-4 shadow-sm">
|
|
129
|
+
<h3>{journal.title}</h3>
|
|
130
|
+
<p>{journal.content}</p>
|
|
131
|
+
<Badge>{journal.date}</Badge>
|
|
132
|
+
</div>
|
|
133
|
+
```
|
|
134
|
+
|
|
135
|
+
**Example - After**:
|
|
136
|
+
```tsx
|
|
137
|
+
// Card.tsx - reusable base
|
|
138
|
+
function Card({ title, content, badge }: CardProps) {
|
|
139
|
+
return (
|
|
140
|
+
<div className="rounded-lg border p-4 shadow-sm">
|
|
141
|
+
<h3>{title}</h3>
|
|
142
|
+
<p>{content}</p>
|
|
143
|
+
{badge && <Badge>{badge}</Badge>}
|
|
144
|
+
</div>
|
|
145
|
+
);
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
// Usage
|
|
149
|
+
<Card title={todo.title} content={todo.description} badge={todo.status} />
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
---
|
|
153
|
+
|
|
154
|
+
### 4. UI Display Constants (Labels, Icons, Colors)
|
|
155
|
+
|
|
156
|
+
**Trigger**: Changing a display label, icon, or color for a domain concept.
|
|
157
|
+
|
|
158
|
+
**Questions**:
|
|
159
|
+
- [ ] Is this display value defined in multiple components?
|
|
160
|
+
- [ ] Should there be a shared config for this domain concept?
|
|
161
|
+
|
|
162
|
+
**The Problem**: Same domain concept displayed in multiple components, each with its own config. Changing one, forgetting others → inconsistency.
|
|
163
|
+
|
|
164
|
+
**Example - Before (bug)**:
|
|
165
|
+
```tsx
|
|
166
|
+
// TodoColumn.tsx
|
|
167
|
+
const stateConfig = { open: { label: "Open", ... } }; // ✅ Updated
|
|
168
|
+
|
|
169
|
+
// TodoDetailPanel.tsx (FORGOT!)
|
|
170
|
+
const stateConfig = { open: { label: "Todo", ... } }; // ❌ Still old
|
|
171
|
+
|
|
172
|
+
// Result: Column shows "Open", Detail panel shows "Todo"
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
**Example - After**:
|
|
176
|
+
```tsx
|
|
177
|
+
// shared/constants/todo.ts - Single source of truth
|
|
178
|
+
export const TODO_STATE_CONFIG = {
|
|
179
|
+
open: { label: "Open", icon: OpenIcon, colorClass: "text-muted" },
|
|
180
|
+
// ...
|
|
181
|
+
};
|
|
182
|
+
|
|
183
|
+
// Both components import and use the same config
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
**Search pattern**:
|
|
187
|
+
```bash
|
|
188
|
+
rg "stateConfig|StateConfig|state.*label" --type tsx
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
---
|
|
192
|
+
|
|
193
|
+
### 5. Visual-Logic Consistency
|
|
194
|
+
|
|
195
|
+
**Trigger**: Implementing logic that determines how something is displayed (sorting, filtering).
|
|
196
|
+
|
|
197
|
+
**Questions**:
|
|
198
|
+
- [ ] Is there already a visual distinction for this concept?
|
|
199
|
+
- [ ] Does the logic use the **same criteria** as the visual representation?
|
|
200
|
+
|
|
201
|
+
**The Problem**: Visual representation and logic use different criteria → inconsistent behavior.
|
|
202
|
+
|
|
203
|
+
**Example - Before (bug)**:
|
|
204
|
+
```typescript
|
|
205
|
+
// Frontend: Icon shows folder if node has children
|
|
206
|
+
if (hasChildren) return <FolderIcon />; // Uses: children.length > 0
|
|
207
|
+
|
|
208
|
+
// Backend: Sorting puts "folders" first based on content
|
|
209
|
+
const isFolder = currentVersion > 0; // Uses: different criteria!
|
|
210
|
+
|
|
211
|
+
// Result: Icon and sort order don't match
|
|
212
|
+
```
|
|
213
|
+
|
|
214
|
+
**Example - After**:
|
|
215
|
+
```typescript
|
|
216
|
+
// Both use the same criteria: hasChildren
|
|
217
|
+
const isFolder = children.length > 0;
|
|
218
|
+
```
|
|
219
|
+
|
|
220
|
+
**Rule**: If users see a visual distinction, the underlying logic must use the **exact same criteria**.
|
|
221
|
+
|
|
222
|
+
---
|
|
223
|
+
|
|
224
|
+
### 6. Cross-Layer Shared Constants
|
|
225
|
+
|
|
226
|
+
**Trigger**: Same value needed in both frontend and backend.
|
|
227
|
+
|
|
228
|
+
**Questions**:
|
|
229
|
+
- [ ] Is this value used in multiple files?
|
|
230
|
+
- [ ] Would changing it require updating multiple places?
|
|
231
|
+
|
|
232
|
+
**Example - Before (bug)**:
|
|
233
|
+
```typescript
|
|
234
|
+
// Backend
|
|
235
|
+
const BATCH_SIZE = 15;
|
|
236
|
+
|
|
237
|
+
// Frontend file1, file2, file3... each defines
|
|
238
|
+
const BATCH_SIZE = 15; // Duplicated 5 times!
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
**Example - After**:
|
|
242
|
+
```typescript
|
|
243
|
+
// shared/constants/config.ts - Single source of truth
|
|
244
|
+
export const SYNC_CONSTANTS = {
|
|
245
|
+
BATCH_SIZE: 15, // API limit
|
|
246
|
+
DEBOUNCE_MS: 2000,
|
|
247
|
+
} as const;
|
|
248
|
+
|
|
249
|
+
// Both layers import from shared
|
|
250
|
+
import { SYNC_CONSTANTS } from "@shared/constants";
|
|
251
|
+
```
|
|
252
|
+
|
|
253
|
+
---
|
|
254
|
+
|
|
255
|
+
## When to Abstract vs. Duplicate
|
|
256
|
+
|
|
257
|
+
**Abstract when**:
|
|
258
|
+
- Pattern repeats 3+ times
|
|
259
|
+
- Logic is identical (not just similar)
|
|
260
|
+
- Changes should propagate to all uses
|
|
261
|
+
|
|
262
|
+
**Duplicate when**:
|
|
263
|
+
- Pattern only appears 2 times
|
|
264
|
+
- Logic might diverge in the future
|
|
265
|
+
- Abstraction would be confusing
|
|
266
|
+
|
|
267
|
+
**Rule of thumb**:
|
|
268
|
+
> "Duplication is cheaper than the wrong abstraction" — Sandi Metz
|
|
269
|
+
|
|
270
|
+
But once you see 3+ occurrences, it's time to abstract.
|
|
271
|
+
|
|
272
|
+
---
|
|
273
|
+
|
|
274
|
+
## Pre-Modification Checklist
|
|
275
|
+
|
|
276
|
+
**Before changing any value, ALWAYS search first:**
|
|
277
|
+
|
|
278
|
+
```bash
|
|
279
|
+
# Search for the value you're about to change
|
|
280
|
+
rg "Todo" --type tsx
|
|
281
|
+
rg "stateConfig|priorityConfig" --type tsx
|
|
282
|
+
|
|
283
|
+
# Search for the concept
|
|
284
|
+
rg "open.*label|label.*open" --type tsx
|
|
285
|
+
```
|
|
286
|
+
|
|
287
|
+
**Questions**:
|
|
288
|
+
- [ ] How many files define this value?
|
|
289
|
+
- [ ] Should this be a shared constant instead?
|
|
290
|
+
- [ ] If I change it here, where else needs to change?
|
|
291
|
+
|
|
292
|
+
**The rule**: If you find the same value in 2+ places, **extract to shared constant first**, then make the change in one place.
|
|
293
|
+
|
|
294
|
+
---
|
|
295
|
+
|
|
296
|
+
## Quick Decision Tree
|
|
297
|
+
|
|
298
|
+
```
|
|
299
|
+
You're about to write some code
|
|
300
|
+
│
|
|
301
|
+
├─ Does similar code exist?
|
|
302
|
+
│ ├─ Yes → Can you reuse/extend it?
|
|
303
|
+
│ │ ├─ Yes → Reuse it
|
|
304
|
+
│ │ └─ No → Why not? (might need abstraction)
|
|
305
|
+
│ └─ No → Continue
|
|
306
|
+
│
|
|
307
|
+
├─ Is this the 3rd time writing this pattern?
|
|
308
|
+
│ ├─ Yes → Time to abstract
|
|
309
|
+
│ └─ No → OK to duplicate for now
|
|
310
|
+
│
|
|
311
|
+
└─ Done
|
|
312
|
+
```
|
|
313
|
+
|
|
314
|
+
---
|
|
315
|
+
|
|
316
|
+
## Lessons Learned
|
|
317
|
+
|
|
318
|
+
| Situation | Mistake | Solution |
|
|
319
|
+
|-----------|---------|----------|
|
|
320
|
+
| 30+ Output schemas | Didn't abstract base schema | Create `createOutputSchema()` |
|
|
321
|
+
| Changed label in one place | Forgot other components | Extract to shared constants |
|
|
322
|
+
| Icon uses criterion A, sort uses B | Visual-logic mismatch | Unify to same criterion |
|
|
323
|
+
| Same constant in 6 files | No shared constants | Create `@shared/constants/` |
|
|
324
|
+
| Same hook logic in 5 files | Didn't create abstraction | Create shared hook first |
|
|
325
|
+
|
|
326
|
+
---
|
|
327
|
+
|
|
328
|
+
## Related Documents
|
|
329
|
+
|
|
330
|
+
| Document | Purpose | Timing |
|
|
331
|
+
|----------|---------|--------|
|
|
332
|
+
| [Pre-Implementation Checklist](./pre-implementation-checklist.md) | Questions before coding | **Before** writing code |
|
|
333
|
+
| **Code Reuse Thinking Guide** (this) | Pattern recognition | During/after implementation |
|
|
334
|
+
| [Cross-Layer Thinking Guide](./cross-layer-thinking-guide.md) | Data flow across layers | Complex feature planning |
|
|
335
|
+
| `/check-cross-layer` command | Verification check | After implementation |
|
|
336
|
+
|
|
337
|
+
---
|
|
338
|
+
|
|
339
|
+
**Core Principle**: Notice patterns. Ask "should this be abstracted?" before writing similar code again.
|
|
340
|
+
|
|
341
|
+
---
|
|
342
|
+
|
|
343
|
+
**Language**: All documentation must be written in **English**.
|
|
@@ -0,0 +1,283 @@
|
|
|
1
|
+
# Cross-Layer Thinking Guide
|
|
2
|
+
|
|
3
|
+
> **Purpose**: A checklist to think through data flow and integration points BEFORE implementing a feature.
|
|
4
|
+
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
## Why This Guide?
|
|
8
|
+
|
|
9
|
+
Most bugs happen at **layer boundaries**. This guide helps you:
|
|
10
|
+
|
|
11
|
+
1. Identify all layers a feature touches
|
|
12
|
+
2. Think through data transformations at each boundary
|
|
13
|
+
3. Catch missing integration points before coding
|
|
14
|
+
4. Document decisions for future reference
|
|
15
|
+
|
|
16
|
+
---
|
|
17
|
+
|
|
18
|
+
## Pre-Implementation Checklist
|
|
19
|
+
|
|
20
|
+
Before writing code, answer these questions:
|
|
21
|
+
|
|
22
|
+
### 1. Layer Identification
|
|
23
|
+
|
|
24
|
+
**Q: Which layers does this feature touch?**
|
|
25
|
+
|
|
26
|
+
| Layer | Touched? | Responsibility |
|
|
27
|
+
|-------|----------|----------------|
|
|
28
|
+
| UI Component | [ ] | Render, user interaction |
|
|
29
|
+
| Custom Hook | [ ] | Data fetching, state logic |
|
|
30
|
+
| API Route | [ ] | Request handling, validation |
|
|
31
|
+
| Service Layer | [ ] | Business logic |
|
|
32
|
+
| Database | [ ] | Data persistence |
|
|
33
|
+
| External API | [ ] | Third-party integration |
|
|
34
|
+
|
|
35
|
+
### 2. Data Flow Direction
|
|
36
|
+
|
|
37
|
+
**Q: How does data flow?**
|
|
38
|
+
|
|
39
|
+
```
|
|
40
|
+
[ ] Read flow: Database → Service → API → Hook → Component
|
|
41
|
+
[ ] Write flow: Component → Hook → API → Service → Database
|
|
42
|
+
[ ] Both ways (bidirectional)
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
### 3. Data Transformation Points
|
|
46
|
+
|
|
47
|
+
**Q: Where does data format change?**
|
|
48
|
+
|
|
49
|
+
| From | To | Transformation | Who handles it? |
|
|
50
|
+
|------|----|----------------|-----------------|
|
|
51
|
+
| Database rows | Service objects | ORM hydration | ORM (Drizzle) |
|
|
52
|
+
| Service objects | API response | Serialization | API route |
|
|
53
|
+
| API response | Hook data | Type casting | React Query |
|
|
54
|
+
| Hook data | Component props | Selection/filter | Component |
|
|
55
|
+
|
|
56
|
+
### 4. Validation Points
|
|
57
|
+
|
|
58
|
+
**Q: Where is data validated?**
|
|
59
|
+
|
|
60
|
+
| Point | Validation | Schema |
|
|
61
|
+
|-------|------------|--------|
|
|
62
|
+
| API input | Request body/params | Zod schema |
|
|
63
|
+
| Service input | Business rules | Custom checks |
|
|
64
|
+
| Database | Constraints | Schema constraints |
|
|
65
|
+
|
|
66
|
+
### 5. Error Handling
|
|
67
|
+
|
|
68
|
+
**Q: How do errors propagate?**
|
|
69
|
+
|
|
70
|
+
| Layer | Error Type | Handling |
|
|
71
|
+
|-------|------------|----------|
|
|
72
|
+
| Database | Query error | Throw, log |
|
|
73
|
+
| Service | Business error | Throw custom error |
|
|
74
|
+
| API | HTTP error | Return status + message |
|
|
75
|
+
| Hook | Error state | Expose to component |
|
|
76
|
+
| Component | UI error | Show error message |
|
|
77
|
+
|
|
78
|
+
---
|
|
79
|
+
|
|
80
|
+
## Common Cross-Layer Patterns
|
|
81
|
+
|
|
82
|
+
### Pattern A: CRUD Feature
|
|
83
|
+
|
|
84
|
+
```
|
|
85
|
+
┌─────────────────────────────────────────────────────────────┐
|
|
86
|
+
│ THINK THROUGH │
|
|
87
|
+
├─────────────────────────────────────────────────────────────┤
|
|
88
|
+
│ │
|
|
89
|
+
│ 1. CREATE │
|
|
90
|
+
│ └─ UI: What triggers creation? (button, form) │
|
|
91
|
+
│ └─ API: What's the input schema? │
|
|
92
|
+
│ └─ DB: What tables are affected? │
|
|
93
|
+
│ └─ Response: What does UI need back? │
|
|
94
|
+
│ │
|
|
95
|
+
│ 2. READ │
|
|
96
|
+
│ └─ List view: What fields needed? (avoid over-fetch) │
|
|
97
|
+
│ └─ Detail view: Lazy load heavy content? │
|
|
98
|
+
│ └─ Loading: Show skeleton? Empty state? │
|
|
99
|
+
│ │
|
|
100
|
+
│ 3. UPDATE │
|
|
101
|
+
│ └─ Optimistic UI? (update local before API responds) │
|
|
102
|
+
│ └─ Validation: Same rules as create? │
|
|
103
|
+
│ └─ Partial update? (PATCH vs PUT) │
|
|
104
|
+
│ │
|
|
105
|
+
│ 4. DELETE │
|
|
106
|
+
│ └─ Soft delete? (isDeleted flag) │
|
|
107
|
+
│ └─ Cascade? (related entities) │
|
|
108
|
+
│ └─ Confirmation required? │
|
|
109
|
+
│ │
|
|
110
|
+
└─────────────────────────────────────────────────────────────┘
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
### Pattern B: Form Submission
|
|
114
|
+
|
|
115
|
+
```
|
|
116
|
+
┌─────────────────────────────────────────────────────────────┐
|
|
117
|
+
│ THINK THROUGH │
|
|
118
|
+
├─────────────────────────────────────────────────────────────┤
|
|
119
|
+
│ │
|
|
120
|
+
│ 1. INPUT │
|
|
121
|
+
│ └─ What fields are required vs optional? │
|
|
122
|
+
│ └─ What validations on each field? │
|
|
123
|
+
│ └─ Real-time validation or on submit? │
|
|
124
|
+
│ │
|
|
125
|
+
│ 2. SUBMISSION │
|
|
126
|
+
│ └─ Disable button while submitting? │
|
|
127
|
+
│ └─ Show loading indicator? │
|
|
128
|
+
│ └─ Prevent double submission? │
|
|
129
|
+
│ │
|
|
130
|
+
│ 3. SUCCESS │
|
|
131
|
+
│ └─ Redirect to where? │
|
|
132
|
+
│ └─ Show success message? │
|
|
133
|
+
│ └─ Invalidate which queries? │
|
|
134
|
+
│ │
|
|
135
|
+
│ 4. ERROR │
|
|
136
|
+
│ └─ Show inline errors or toast? │
|
|
137
|
+
│ └─ Which fields keep values? │
|
|
138
|
+
│ └─ How to retry? │
|
|
139
|
+
│ │
|
|
140
|
+
└─────────────────────────────────────────────────────────────┘
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
### Pattern C: Data List with Filters
|
|
144
|
+
|
|
145
|
+
```
|
|
146
|
+
┌─────────────────────────────────────────────────────────────┐
|
|
147
|
+
│ THINK THROUGH │
|
|
148
|
+
├─────────────────────────────────────────────────────────────┤
|
|
149
|
+
│ │
|
|
150
|
+
│ 1. FILTERS │
|
|
151
|
+
│ └─ Which filters are available? │
|
|
152
|
+
│ └─ Filters in URL for shareability? │
|
|
153
|
+
│ └─ Server-side or client-side filtering? │
|
|
154
|
+
│ │
|
|
155
|
+
│ 2. PAGINATION │
|
|
156
|
+
│ └─ Page-based or cursor-based? │
|
|
157
|
+
│ └─ Total count needed? │
|
|
158
|
+
│ └─ Infinite scroll or explicit pages? │
|
|
159
|
+
│ │
|
|
160
|
+
│ 3. SORTING │
|
|
161
|
+
│ └─ Default sort order? │
|
|
162
|
+
│ └─ Multi-column sort? │
|
|
163
|
+
│ └─ Server-side or client-side? │
|
|
164
|
+
│ │
|
|
165
|
+
│ 4. LOADING │
|
|
166
|
+
│ └─ Skeleton for initial load? │
|
|
167
|
+
│ └─ Overlay for filter change? │
|
|
168
|
+
│ └─ Keep previous data while loading? │
|
|
169
|
+
│ │
|
|
170
|
+
└─────────────────────────────────────────────────────────────┘
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
---
|
|
174
|
+
|
|
175
|
+
## Layer-Specific Questions
|
|
176
|
+
|
|
177
|
+
### Component Layer
|
|
178
|
+
|
|
179
|
+
- [ ] What props are required vs optional?
|
|
180
|
+
- [ ] What callbacks are needed? (onChange, onSubmit, onError)
|
|
181
|
+
- [ ] Loading/error/empty states handled?
|
|
182
|
+
|
|
183
|
+
### Hook Layer
|
|
184
|
+
|
|
185
|
+
- [ ] Query key includes all dependencies?
|
|
186
|
+
- [ ] Enabled condition correct?
|
|
187
|
+
- [ ] Error handling defined?
|
|
188
|
+
- [ ] Invalidation after mutation?
|
|
189
|
+
|
|
190
|
+
### API Layer
|
|
191
|
+
|
|
192
|
+
- [ ] Input schema defined?
|
|
193
|
+
- [ ] Output schema defined?
|
|
194
|
+
- [ ] Error responses standardized?
|
|
195
|
+
- [ ] Authentication required?
|
|
196
|
+
|
|
197
|
+
### Service Layer
|
|
198
|
+
|
|
199
|
+
- [ ] Business validation complete?
|
|
200
|
+
- [ ] Transactions for multi-table ops?
|
|
201
|
+
- [ ] Errors properly typed?
|
|
202
|
+
|
|
203
|
+
### Database Layer
|
|
204
|
+
|
|
205
|
+
- [ ] Indexes for query patterns?
|
|
206
|
+
- [ ] Foreign key constraints?
|
|
207
|
+
- [ ] Soft delete vs hard delete?
|
|
208
|
+
|
|
209
|
+
---
|
|
210
|
+
|
|
211
|
+
## Quick Decision Tree
|
|
212
|
+
|
|
213
|
+
```
|
|
214
|
+
Start: New Feature
|
|
215
|
+
│
|
|
216
|
+
├─ Touches 3+ layers?
|
|
217
|
+
│ ├─ Yes → Use this thinking guide
|
|
218
|
+
│ └─ No → Standard implementation
|
|
219
|
+
│
|
|
220
|
+
├─ Has form submission?
|
|
221
|
+
│ ├─ Yes → Think through Pattern B
|
|
222
|
+
│ └─ No → Skip
|
|
223
|
+
│
|
|
224
|
+
├─ Has data list?
|
|
225
|
+
│ ├─ Yes → Think through Pattern C
|
|
226
|
+
│ └─ No → Skip
|
|
227
|
+
│
|
|
228
|
+
├─ Has CRUD operations?
|
|
229
|
+
│ ├─ Yes → Think through Pattern A
|
|
230
|
+
│ └─ No → Skip
|
|
231
|
+
│
|
|
232
|
+
└─ Done: Implementation checklist ready
|
|
233
|
+
```
|
|
234
|
+
|
|
235
|
+
---
|
|
236
|
+
|
|
237
|
+
## Lessons from Past Bugs
|
|
238
|
+
|
|
239
|
+
| Bug | Root Cause | Prevention |
|
|
240
|
+
|-----|------------|------------|
|
|
241
|
+
| Data missing in component | API didn't include field | Document required fields |
|
|
242
|
+
| Type mismatch | API returns string, hook expects number | Use shared Zod schemas |
|
|
243
|
+
| Stale UI after mutation | Forgot to invalidate query | Checklist for mutations |
|
|
244
|
+
| Error not shown | Error thrown but not caught | Error boundary + hook error state |
|
|
245
|
+
| Double submission | No loading state check | Disable button + loading state |
|
|
246
|
+
|
|
247
|
+
---
|
|
248
|
+
|
|
249
|
+
## Template: Pre-Implementation Notes
|
|
250
|
+
|
|
251
|
+
Copy this template when starting a new feature:
|
|
252
|
+
|
|
253
|
+
```markdown
|
|
254
|
+
## Feature: [Name]
|
|
255
|
+
|
|
256
|
+
### Layers Touched
|
|
257
|
+
- [ ] Component
|
|
258
|
+
- [ ] Hook
|
|
259
|
+
- [ ] API
|
|
260
|
+
- [ ] Service
|
|
261
|
+
- [ ] Database
|
|
262
|
+
|
|
263
|
+
### Data Flow
|
|
264
|
+
[Draw ASCII diagram]
|
|
265
|
+
|
|
266
|
+
### Key Decisions
|
|
267
|
+
1. Validation:
|
|
268
|
+
2. Error handling:
|
|
269
|
+
3. Loading states:
|
|
270
|
+
4. Caching strategy:
|
|
271
|
+
|
|
272
|
+
### Open Questions
|
|
273
|
+
- [ ] Question 1
|
|
274
|
+
- [ ] Question 2
|
|
275
|
+
```
|
|
276
|
+
|
|
277
|
+
---
|
|
278
|
+
|
|
279
|
+
**Remember**: 30 minutes of thinking saves 3 hours of debugging.
|
|
280
|
+
|
|
281
|
+
---
|
|
282
|
+
|
|
283
|
+
**Language**: All documentation must be written in **English**.
|