@comfanion/workflow 4.38.1-dev.1 → 4.38.1-dev.3
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/package.json
CHANGED
package/src/build-info.json
CHANGED
|
@@ -306,83 +306,39 @@ DO NOT skip this step. DO NOT ask user what to do. Just read these files first.`
|
|
|
306
306
|
|
|
307
307
|
async function getActiveStory(): Promise<StoryContext | null> {
|
|
308
308
|
try {
|
|
309
|
-
|
|
309
|
+
let storyPath: string | null = null
|
|
310
|
+
|
|
311
|
+
// First, try epic state file for story path
|
|
310
312
|
const epicState = await getActiveEpicState()
|
|
311
|
-
if (epicState) {
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
if (storyPathMatch) {
|
|
315
|
-
const storyFileName = storyPathMatch[1]
|
|
316
|
-
// Find story file
|
|
317
|
-
const sprintMatch = epicState.statePath.match(/sprint-(\d+)/)
|
|
318
|
-
if (sprintMatch) {
|
|
319
|
-
const storyPath = `docs/sprint-artifacts/sprint-${sprintMatch[1]}/stories/${storyFileName}`
|
|
320
|
-
const storyContent = await readFile(join(directory, storyPath), "utf-8")
|
|
321
|
-
|
|
322
|
-
const titleMatch = storyContent.match(/^#\s+(.+)/m)
|
|
323
|
-
const statusMatch = storyContent.match(/\*\*Status:\*\*\s*(\w+)/i)
|
|
324
|
-
|
|
325
|
-
const completedTasks: string[] = []
|
|
326
|
-
const pendingTasks: string[] = []
|
|
327
|
-
let currentTask: string | null = null
|
|
328
|
-
|
|
329
|
-
// Parse tasks with more detail
|
|
330
|
-
const taskRegex = /- \[([ x])\]\s+\*\*T(\d+)\*\*[:\s]+(.+?)(?=\n|$)/g
|
|
331
|
-
let match
|
|
332
|
-
while ((match = taskRegex.exec(storyContent)) !== null) {
|
|
333
|
-
const [, checked, taskId, taskName] = match
|
|
334
|
-
const taskInfo = `T${taskId}: ${taskName.trim()}`
|
|
335
|
-
if (checked === "x") {
|
|
336
|
-
completedTasks.push(taskInfo)
|
|
337
|
-
} else {
|
|
338
|
-
if (!currentTask) currentTask = taskInfo
|
|
339
|
-
pendingTasks.push(taskInfo)
|
|
340
|
-
}
|
|
341
|
-
}
|
|
342
|
-
|
|
343
|
-
// Parse acceptance criteria
|
|
344
|
-
const acceptanceCriteria: string[] = []
|
|
345
|
-
const acSection = storyContent.match(/## Acceptance Criteria[\s\S]*?(?=##|$)/i)
|
|
346
|
-
if (acSection) {
|
|
347
|
-
const acRegex = /- \[([ x])\]\s+(.+?)(?=\n|$)/g
|
|
348
|
-
while ((match = acRegex.exec(acSection[0])) !== null) {
|
|
349
|
-
const [, checked, criteria] = match
|
|
350
|
-
acceptanceCriteria.push(`${checked === "x" ? "✅" : "⬜"} ${criteria.trim()}`)
|
|
351
|
-
}
|
|
352
|
-
}
|
|
313
|
+
if (epicState?.nextStoryPath) {
|
|
314
|
+
storyPath = epicState.nextStoryPath
|
|
315
|
+
}
|
|
353
316
|
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
fullContent: storyContent
|
|
363
|
-
}
|
|
317
|
+
// Fallback: try sprint-status.yaml
|
|
318
|
+
if (!storyPath) {
|
|
319
|
+
try {
|
|
320
|
+
const sprintStatusPath = join(directory, "docs", "sprint-artifacts", "sprint-status.yaml")
|
|
321
|
+
const content = await readFile(sprintStatusPath, "utf-8")
|
|
322
|
+
const inProgressMatch = content.match(/status:\s*in-progress[\s\S]*?path:\s*["']?([^"'\n]+)["']?/i)
|
|
323
|
+
if (inProgressMatch) {
|
|
324
|
+
storyPath = inProgressMatch[1]
|
|
364
325
|
}
|
|
326
|
+
} catch {
|
|
327
|
+
// No sprint-status.yaml
|
|
365
328
|
}
|
|
366
329
|
}
|
|
367
|
-
|
|
368
|
-
// Fallback: try old sprint-status.yaml format
|
|
369
|
-
const sprintStatusPath = join(directory, "docs", "sprint-artifacts", "sprint-status.yaml")
|
|
370
|
-
const content = await readFile(sprintStatusPath, "utf-8")
|
|
371
|
-
|
|
372
|
-
const inProgressMatch = content.match(/status:\s*in-progress[\s\S]*?path:\s*["']?([^"'\n]+)["']?/i)
|
|
373
|
-
if (!inProgressMatch) return null
|
|
374
330
|
|
|
375
|
-
|
|
331
|
+
if (!storyPath) return null
|
|
332
|
+
|
|
333
|
+
// Parse story file
|
|
376
334
|
const storyContent = await readFile(join(directory, storyPath), "utf-8")
|
|
377
|
-
|
|
378
335
|
const titleMatch = storyContent.match(/^#\s+(.+)/m)
|
|
379
336
|
const statusMatch = storyContent.match(/\*\*Status:\*\*\s*(\w+)/i)
|
|
380
|
-
|
|
337
|
+
|
|
381
338
|
const completedTasks: string[] = []
|
|
382
339
|
const pendingTasks: string[] = []
|
|
383
340
|
let currentTask: string | null = null
|
|
384
|
-
|
|
385
|
-
// Parse tasks with more detail
|
|
341
|
+
|
|
386
342
|
const taskRegex = /- \[([ x])\]\s+\*\*T(\d+)\*\*[:\s]+(.+?)(?=\n|$)/g
|
|
387
343
|
let match
|
|
388
344
|
while ((match = taskRegex.exec(storyContent)) !== null) {
|
|
@@ -395,8 +351,7 @@ DO NOT skip this step. DO NOT ask user what to do. Just read these files first.`
|
|
|
395
351
|
pendingTasks.push(taskInfo)
|
|
396
352
|
}
|
|
397
353
|
}
|
|
398
|
-
|
|
399
|
-
// Parse acceptance criteria
|
|
354
|
+
|
|
400
355
|
const acceptanceCriteria: string[] = []
|
|
401
356
|
const acSection = storyContent.match(/## Acceptance Criteria[\s\S]*?(?=##|$)/i)
|
|
402
357
|
if (acSection) {
|
|
@@ -9,22 +9,34 @@ metadata:
|
|
|
9
9
|
|
|
10
10
|
# Dev Epic Skill
|
|
11
11
|
|
|
12
|
+
## CRITICAL: Context Rules
|
|
13
|
+
|
|
14
|
+
**READ ONLY (max ~70KB):**
|
|
15
|
+
- `CLAUDE.md`
|
|
16
|
+
- `docs/coding-standards/README.md`
|
|
17
|
+
- `docs/coding-standards/patterns.md`
|
|
18
|
+
- Epic file (ONE)
|
|
19
|
+
- Current story file (ONE at a time)
|
|
20
|
+
|
|
21
|
+
**❌ DO NOT READ — WASTES CONTEXT:**
|
|
22
|
+
- ❌ `docs/prd.md` — epic/story already has context
|
|
23
|
+
- ❌ `docs/architecture.md` — too large, coding-standards has patterns
|
|
24
|
+
- ❌ All stories at once — read ONE, execute, then next
|
|
25
|
+
|
|
26
|
+
---
|
|
27
|
+
|
|
12
28
|
<workflow name="dev-epic">
|
|
13
29
|
|
|
14
30
|
<phase name="1-context" title="Load Minimal Context">
|
|
31
|
+
<critical>DO NOT read prd.md, architecture.md, or all stories!</critical>
|
|
15
32
|
<read>
|
|
16
33
|
<file>CLAUDE.md</file>
|
|
17
34
|
<file>docs/coding-standards/README.md</file>
|
|
18
35
|
<file>docs/coding-standards/patterns.md</file>
|
|
19
36
|
<file>{epic-file}</file>
|
|
20
|
-
<file>{current-story-file}
|
|
37
|
+
<file>{current-story-file} — ONE only!</file>
|
|
21
38
|
</read>
|
|
22
|
-
<
|
|
23
|
-
<file>docs/prd.md</file>
|
|
24
|
-
<file>docs/architecture.md</file>
|
|
25
|
-
<file>all stories at once</file>
|
|
26
|
-
</skip>
|
|
27
|
-
<goal>~70KB per story</goal>
|
|
39
|
+
<goal>~70KB per story, NOT 200KB+</goal>
|
|
28
40
|
</phase>
|
|
29
41
|
|
|
30
42
|
<phase name="2-init" title="Initialize Epic">
|
|
@@ -9,23 +9,37 @@ metadata:
|
|
|
9
9
|
|
|
10
10
|
# Dev Sprint Skill
|
|
11
11
|
|
|
12
|
+
## CRITICAL: Context Rules
|
|
13
|
+
|
|
14
|
+
**READ ONLY (max ~70KB):**
|
|
15
|
+
- `CLAUDE.md`
|
|
16
|
+
- `docs/coding-standards/README.md`
|
|
17
|
+
- `docs/coding-standards/patterns.md`
|
|
18
|
+
- `sprint-status.yaml`
|
|
19
|
+
- Current epic file (ONE)
|
|
20
|
+
- Current story file (ONE at a time)
|
|
21
|
+
|
|
22
|
+
**❌ DO NOT READ — WASTES CONTEXT:**
|
|
23
|
+
- ❌ `docs/prd.md` — epic/story already has context
|
|
24
|
+
- ❌ `docs/architecture.md` — too large, coding-standards has patterns
|
|
25
|
+
- ❌ All epics at once — read ONE, execute, then next
|
|
26
|
+
- ❌ All stories at once — read ONE, execute, then next
|
|
27
|
+
|
|
28
|
+
---
|
|
29
|
+
|
|
12
30
|
<workflow name="dev-sprint">
|
|
13
31
|
|
|
14
32
|
<phase name="1-context" title="Load Minimal Context">
|
|
33
|
+
<critical>DO NOT read prd.md, architecture.md, or all epics/stories!</critical>
|
|
15
34
|
<read>
|
|
16
35
|
<file>CLAUDE.md</file>
|
|
17
36
|
<file>docs/coding-standards/README.md</file>
|
|
18
37
|
<file>docs/coding-standards/patterns.md</file>
|
|
19
38
|
<file>sprint-status.yaml</file>
|
|
20
|
-
<file>{current-epic-file}
|
|
21
|
-
<file>{current-story-file}
|
|
39
|
+
<file>{current-epic-file} — ONE only!</file>
|
|
40
|
+
<file>{current-story-file} — ONE only!</file>
|
|
22
41
|
</read>
|
|
23
|
-
<
|
|
24
|
-
<file>docs/prd.md</file>
|
|
25
|
-
<file>docs/architecture.md</file>
|
|
26
|
-
<file>all epics/stories at once</file>
|
|
27
|
-
</skip>
|
|
28
|
-
<goal>~70KB per story</goal>
|
|
42
|
+
<goal>~70KB per story, NOT 200KB+</goal>
|
|
29
43
|
</phase>
|
|
30
44
|
|
|
31
45
|
<phase name="2-init" title="Initialize Sprint">
|
|
@@ -11,20 +11,31 @@ metadata:
|
|
|
11
11
|
|
|
12
12
|
# Dev Story Skill
|
|
13
13
|
|
|
14
|
+
## CRITICAL: Context Rules
|
|
15
|
+
|
|
16
|
+
**READ ONLY (max ~70KB):**
|
|
17
|
+
- `CLAUDE.md`
|
|
18
|
+
- `docs/coding-standards/README.md`
|
|
19
|
+
- `docs/coding-standards/patterns.md`
|
|
20
|
+
- Story file
|
|
21
|
+
|
|
22
|
+
**❌ DO NOT READ — WASTES CONTEXT:**
|
|
23
|
+
- ❌ `docs/prd.md` — story already has context
|
|
24
|
+
- ❌ `docs/architecture.md` — too large, coding-standards has patterns
|
|
25
|
+
|
|
26
|
+
---
|
|
27
|
+
|
|
14
28
|
<workflow name="dev-story">
|
|
15
29
|
|
|
16
30
|
<phase name="1-context" title="Load Minimal Context">
|
|
31
|
+
<critical>DO NOT read prd.md or architecture.md!</critical>
|
|
17
32
|
<read>
|
|
18
33
|
<file>CLAUDE.md</file>
|
|
19
34
|
<file>docs/coding-standards/README.md</file>
|
|
20
35
|
<file>docs/coding-standards/patterns.md</file>
|
|
21
36
|
<file>{story-file}</file>
|
|
22
37
|
</read>
|
|
23
|
-
<
|
|
24
|
-
<file>docs/prd.md</file>
|
|
25
|
-
<file>docs/architecture.md</file>
|
|
26
|
-
</skip>
|
|
27
|
-
<goal>~70KB context, not 200KB+</goal>
|
|
38
|
+
<goal>~70KB context, NOT 200KB+</goal>
|
|
28
39
|
</phase>
|
|
29
40
|
|
|
30
41
|
<phase name="2-transform" title="Transform Story Task → Executable Instruction">
|