ma-agents 3.1.0 → 3.3.0
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/.opencode/skills/.ma-agents.json +99 -99
- package/.roo/rules/00-ma-agents.md +13 -0
- package/.roo/skills/.ma-agents.json +241 -0
- package/.roo/skills/MANIFEST.yaml +254 -0
- package/.roo/skills/ai-audit-trail/SKILL.md +23 -0
- package/.roo/skills/auto-bug-detection/SKILL.md +169 -0
- package/.roo/skills/cmake-best-practices/SKILL.md +64 -0
- package/.roo/skills/cmake-best-practices/examples/cmake.md +59 -0
- package/.roo/skills/code-documentation/SKILL.md +57 -0
- package/.roo/skills/code-documentation/examples/cpp.md +29 -0
- package/.roo/skills/code-documentation/examples/csharp.md +28 -0
- package/.roo/skills/code-documentation/examples/javascript_typescript.md +28 -0
- package/.roo/skills/code-documentation/examples/python.md +57 -0
- package/.roo/skills/code-review/SKILL.md +43 -0
- package/.roo/skills/commit-message/SKILL.md +79 -0
- package/.roo/skills/cpp-best-practices/SKILL.md +234 -0
- package/.roo/skills/cpp-best-practices/examples/modern-idioms.md +189 -0
- package/.roo/skills/cpp-best-practices/examples/naming-and-organization.md +102 -0
- package/.roo/skills/cpp-concurrency-safety/SKILL.md +60 -0
- package/.roo/skills/cpp-concurrency-safety/examples/concurrency.md +73 -0
- package/.roo/skills/cpp-const-correctness/SKILL.md +63 -0
- package/.roo/skills/cpp-const-correctness/examples/const_correctness.md +54 -0
- package/.roo/skills/cpp-memory-handling/SKILL.md +42 -0
- package/.roo/skills/cpp-memory-handling/examples/modern-cpp.md +49 -0
- package/.roo/skills/cpp-memory-handling/examples/smart-pointers.md +46 -0
- package/.roo/skills/cpp-modern-composition/SKILL.md +64 -0
- package/.roo/skills/cpp-modern-composition/examples/composition.md +51 -0
- package/.roo/skills/cpp-robust-interfaces/SKILL.md +55 -0
- package/.roo/skills/cpp-robust-interfaces/examples/interfaces.md +56 -0
- package/.roo/skills/create-hardened-docker-skill/SKILL.md +637 -0
- package/.roo/skills/create-hardened-docker-skill/scripts/create-all.sh +489 -0
- package/.roo/skills/csharp-best-practices/SKILL.md +278 -0
- package/.roo/skills/docker-hardening-verification/SKILL.md +28 -0
- package/.roo/skills/docker-hardening-verification/scripts/verify-hardening.sh +39 -0
- package/.roo/skills/docker-image-signing/SKILL.md +28 -0
- package/.roo/skills/docker-image-signing/scripts/sign-image.sh +33 -0
- package/.roo/skills/document-revision-history/SKILL.md +104 -0
- package/.roo/skills/git-workflow-skill/SKILL.md +194 -0
- package/.roo/skills/git-workflow-skill/hooks/commit-msg +61 -0
- package/.roo/skills/git-workflow-skill/hooks/pre-commit +38 -0
- package/.roo/skills/git-workflow-skill/hooks/prepare-commit-msg +56 -0
- package/.roo/skills/git-workflow-skill/scripts/finish-feature.sh +192 -0
- package/.roo/skills/git-workflow-skill/scripts/install-hooks.sh +55 -0
- package/.roo/skills/git-workflow-skill/scripts/start-feature.sh +110 -0
- package/.roo/skills/git-workflow-skill/scripts/validate-workflow.sh +229 -0
- package/.roo/skills/js-ts-dependency-mgmt/SKILL.md +49 -0
- package/.roo/skills/js-ts-dependency-mgmt/examples/dependency_mgmt.md +60 -0
- package/.roo/skills/js-ts-security-skill/SKILL.md +64 -0
- package/.roo/skills/js-ts-security-skill/scripts/verify-security.sh +136 -0
- package/.roo/skills/logging-best-practices/SKILL.md +50 -0
- package/.roo/skills/logging-best-practices/examples/cpp.md +36 -0
- package/.roo/skills/logging-best-practices/examples/csharp.md +49 -0
- package/.roo/skills/logging-best-practices/examples/javascript.md +77 -0
- package/.roo/skills/logging-best-practices/examples/python.md +57 -0
- package/.roo/skills/logging-best-practices/references/logging-standards.md +29 -0
- package/.roo/skills/open-presentation/SKILL.md +35 -0
- package/.roo/skills/opentelemetry-best-practices/SKILL.md +34 -0
- package/.roo/skills/opentelemetry-best-practices/examples/go.md +32 -0
- package/.roo/skills/opentelemetry-best-practices/examples/javascript.md +58 -0
- package/.roo/skills/opentelemetry-best-practices/examples/python.md +37 -0
- package/.roo/skills/opentelemetry-best-practices/references/otel-standards.md +37 -0
- package/.roo/skills/python-best-practices/SKILL.md +385 -0
- package/.roo/skills/python-dependency-mgmt/SKILL.md +42 -0
- package/.roo/skills/python-dependency-mgmt/examples/dependency_mgmt.md +67 -0
- package/.roo/skills/python-security-skill/SKILL.md +56 -0
- package/.roo/skills/python-security-skill/examples/security.md +56 -0
- package/.roo/skills/self-signed-cert/SKILL.md +42 -0
- package/.roo/skills/self-signed-cert/scripts/generate-cert.ps1 +45 -0
- package/.roo/skills/self-signed-cert/scripts/generate-cert.sh +43 -0
- package/.roo/skills/skill-creator/SKILL.md +196 -0
- package/.roo/skills/skill-creator/references/output-patterns.md +82 -0
- package/.roo/skills/skill-creator/references/workflows.md +28 -0
- package/.roo/skills/skill-creator/scripts/init_skill.py +208 -0
- package/.roo/skills/skill-creator/scripts/package_skill.py +99 -0
- package/.roo/skills/skill-creator/scripts/quick_validate.py +113 -0
- package/.roo/skills/story-status-lookup/SKILL.md +78 -0
- package/.roo/skills/test-accompanied-development/SKILL.md +50 -0
- package/.roo/skills/test-generator/SKILL.md +65 -0
- package/.roo/skills/vercel-react-best-practices/SKILL.md +109 -0
- package/.roo/skills/verify-hardened-docker-skill/SKILL.md +442 -0
- package/.roo/skills/verify-hardened-docker-skill/scripts/verify-docker-hardening.sh +439 -0
- package/README.md +50 -3
- package/lib/agents.js +23 -0
- package/lib/bmad-extension/module-help.csv +8 -4
- package/lib/bmad-extension/skills/add-sprint/SKILL.md +126 -40
- package/lib/bmad-extension/skills/add-to-sprint/SKILL.md +116 -142
- package/lib/bmad-extension/skills/cleanup-done/.gitkeep +0 -0
- package/lib/bmad-extension/skills/cleanup-done/SKILL.md +159 -0
- package/lib/bmad-extension/skills/cleanup-done/bmad-skill-manifest.yaml +3 -0
- package/lib/bmad-extension/skills/create-bug-story/SKILL.md +75 -7
- package/lib/bmad-extension/skills/generate-backlog/SKILL.md +183 -0
- package/lib/bmad-extension/skills/generate-backlog/bmad-skill-manifest.yaml +3 -0
- package/lib/bmad-extension/skills/modify-sprint/SKILL.md +63 -0
- package/lib/bmad-extension/skills/prioritize-backlog/.gitkeep +0 -0
- package/lib/bmad-extension/skills/prioritize-backlog/SKILL.md +195 -0
- package/lib/bmad-extension/skills/prioritize-backlog/bmad-skill-manifest.yaml +3 -0
- package/lib/bmad-extension/skills/remove-from-sprint/.gitkeep +0 -0
- package/lib/bmad-extension/skills/remove-from-sprint/SKILL.md +163 -0
- package/lib/bmad-extension/skills/remove-from-sprint/bmad-skill-manifest.yaml +3 -0
- package/lib/bmad-extension/skills/sprint-status-view/SKILL.md +199 -138
- package/lib/bmad-extension/workflows/add-sprint/workflow.md +129 -39
- package/lib/bmad-extension/workflows/add-to-sprint/workflow.md +3 -205
- package/lib/bmad-extension/workflows/modify-sprint/workflow.md +5 -0
- package/lib/bmad-extension/workflows/sprint-status-view/workflow.md +3 -192
- package/package.json +4 -3
- package/test/roo-code-agent.test.js +166 -0
- package/test/roo-code-injection.test.js +172 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: sprint-status-view
|
|
3
|
-
description: Display sprint progress with
|
|
3
|
+
description: Display sprint progress with capacity, items, and backlog. Regenerates sprint-status.yaml.
|
|
4
4
|
type: skill
|
|
5
5
|
triggers:
|
|
6
6
|
- "sprint status view"
|
|
@@ -9,194 +9,255 @@ triggers:
|
|
|
9
9
|
|
|
10
10
|
# Sprint Status View Workflow
|
|
11
11
|
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
> **Architecture mandate:** This workflow is a NEW extension at `lib/bmad-extension/workflows/sprint-status-view/`. It does NOT modify any files under `_bmad/bmm/workflows/`.
|
|
12
|
+
Display sprint status with capacity, items, and backlog summary. Regenerates `sprint-status.yaml` from authoritative sources.
|
|
15
13
|
|
|
16
14
|
<workflow>
|
|
17
15
|
|
|
18
|
-
<step n="1" goal="
|
|
19
|
-
<
|
|
20
|
-
|
|
16
|
+
<step n="1" goal="Suggest running /cleanup-done first">
|
|
17
|
+
<output>
|
|
18
|
+
**Tip:** Consider running `/cleanup-done` before viewing sprint status to archive completed items and free capacity.
|
|
19
|
+
</output>
|
|
20
|
+
<action>Continue to next step (advisory only -- do not auto-invoke /cleanup-done)</action>
|
|
21
|
+
</step>
|
|
22
|
+
|
|
23
|
+
<step n="2" goal="Load data sources">
|
|
24
|
+
<action>Glob `_bmad-output/implementation-artifacts/sprints/sprint-*.yaml` to discover all sprint entity files</action>
|
|
25
|
+
<action>Store discovered sprint files as {{sprint_files}} list</action>
|
|
26
|
+
|
|
27
|
+
<action>Read `_bmad-output/implementation-artifacts/backlog.yaml` if it exists</action>
|
|
28
|
+
<action>Store the backlog items list as {{backlog_items}} (or empty list if file not found)</action>
|
|
29
|
+
|
|
30
|
+
<action>Glob `_bmad-output/implementation-artifacts/bug-*.md` to discover all bug story files (fallback for bug metadata)</action>
|
|
31
|
+
<action>For each bug file found, parse YAML frontmatter to extract: title, severity, status</action>
|
|
32
|
+
<action>Store as {{bug_metadata_map}} keyed by file basename (e.g., `bug-login-crash`)</action>
|
|
33
|
+
|
|
34
|
+
<action>Read `_bmad-output/implementation-artifacts/sprint-status.yaml` if it exists (fallback for story status when backlog.yaml is missing or incomplete)</action>
|
|
35
|
+
<action>Parse development_status section into {{status_fallback_map}} -- key: story key, value: status</action>
|
|
36
|
+
<action>Exclude epic-* keys and *-retrospective keys from the fallback map</action>
|
|
37
|
+
|
|
38
|
+
<check if="no sprint files found AND no backlog.yaml exists">
|
|
21
39
|
<output>
|
|
22
|
-
|
|
40
|
+
**No Sprint Data Found**
|
|
23
41
|
|
|
24
|
-
No sprint
|
|
42
|
+
No sprint files exist (`sprints/sprint-*.yaml`) and no `backlog.yaml` was found.
|
|
25
43
|
|
|
26
44
|
**To get started:**
|
|
27
|
-
|
|
28
|
-
|
|
45
|
+
1. Run `/generate-backlog` to create a backlog from your epics
|
|
46
|
+
2. Run `/add-sprint` to create your first sprint
|
|
47
|
+
3. Run `/add-to-sprint` to assign backlog items to it
|
|
29
48
|
</output>
|
|
30
49
|
<action>Exit workflow</action>
|
|
31
50
|
</check>
|
|
32
|
-
<action>For each sprint file found, read the full YAML content and store as {{sprint_plans}} list</action>
|
|
33
|
-
<action>Sort {{sprint_plans}} by sprint_number ascending</action>
|
|
34
51
|
</step>
|
|
35
52
|
|
|
36
|
-
<step n="
|
|
37
|
-
<action>
|
|
38
|
-
<
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
</step>
|
|
58
|
-
|
|
59
|
-
<step n="4" goal="Display sprint status for each sprint">
|
|
60
|
-
<action>For each sprint in {{sprint_plans}} (in order):</action>
|
|
61
|
-
<action>Calculate: {{assigned_count}} = length(sprint.assigned_items)</action>
|
|
62
|
-
<action>Calculate: {{remaining_capacity}} = sprint.capacity - {{assigned_count}}</action>
|
|
63
|
-
|
|
64
|
-
<action>For each item identifier in sprint.assigned_items, resolve item details:
|
|
65
|
-
|
|
66
|
-
**If item is a story (key matches regex `^\d+-\d+-.+`):**
|
|
67
|
-
- Look up status in {{story_status_map}}[item_key]
|
|
68
|
-
- If NOT found in {{story_status_map}}:
|
|
69
|
-
→ Record as DATA INTEGRITY WARNING: "Item {item_key} has no status entry in sprint-status.yaml — run /sprint-planning to initialize status tracking for this item."
|
|
70
|
-
→ Display item with marker: ⚠️ [status unknown]
|
|
71
|
-
- If found: display with current status label
|
|
72
|
-
|
|
73
|
-
**If item is a bug (key matches regex `^bug-.+`):**
|
|
74
|
-
- Look up in {{bug_metadata_map}}[item_key]
|
|
75
|
-
- If NOT found: display with title as item_key, severity as "unknown"
|
|
76
|
-
- If found: display with title and severity from frontmatter
|
|
77
|
-
- Bug execution status: use `status` from bug file frontmatter if present; otherwise "not-started"
|
|
78
|
-
|
|
79
|
-
**If item matches neither pattern:** display as type "Unknown" with raw identifier as title
|
|
53
|
+
<step n="3" goal="Display each sprint">
|
|
54
|
+
<action>For each sprint in {{sprint_files}}, read the full YAML content</action>
|
|
55
|
+
<action>Sort sprints for display: active first, then planning, then closed</action>
|
|
56
|
+
<action>Initialize {{total_done_in_sprints}} = 0 for step 4</action>
|
|
57
|
+
|
|
58
|
+
<action>For each sprint (in sorted order):
|
|
59
|
+
|
|
60
|
+
**If sprint.status is "closed":**
|
|
61
|
+
- Count total items in sprint.items
|
|
62
|
+
- Display collapsed summary line only
|
|
63
|
+
|
|
64
|
+
**If sprint.status is NOT "closed" (active or planning):**
|
|
65
|
+
- Calculate {{item_count}} = length(sprint.items)
|
|
66
|
+
- For each item identifier in sprint.items, resolve details:
|
|
67
|
+
- Look up item in {{backlog_items}} by matching `id` field
|
|
68
|
+
- If found in backlog: use `type`, `title`, `status`, `severity` from backlog entry
|
|
69
|
+
- If NOT found in backlog and item matches `^bug-`: look up in {{bug_metadata_map}} for title/severity, use status from bug frontmatter or default to "backlog"
|
|
70
|
+
- If NOT found in backlog and item matches a story pattern: look up in {{status_fallback_map}} for status, infer title from key, set type to "story"
|
|
71
|
+
- If item cannot be resolved from any source: display with raw identifier, type "unknown", status "unknown"
|
|
72
|
+
- If resolved item status is "done", increment {{total_done_in_sprints}}
|
|
73
|
+
- Build capacity bar: `[===---]` style where `=` represents filled slots and `-` represents remaining capacity
|
|
80
74
|
</action>
|
|
81
75
|
|
|
76
|
+
<action>Display non-closed sprints:</action>
|
|
82
77
|
<output>
|
|
78
|
+
{{#each non_closed_sprints}}
|
|
83
79
|
---
|
|
84
80
|
|
|
85
|
-
##
|
|
81
|
+
## {{sprint.name}} ({{sprint.status}}) -- {{item_count}}/{{sprint.capacity}} items
|
|
86
82
|
|
|
87
|
-
|
|
88
|
-
{{#if sprint.start_context}}**Start:** {{sprint.start_context}}{{/if}} {{#if sprint.end_context}}| **End:** {{sprint.end_context}}{{/if}}
|
|
83
|
+
{{#if sprint.start}}**Start:** {{sprint.start}}{{/if}}{{#if sprint.end}} | **End:** {{sprint.end}}{{/if}}
|
|
89
84
|
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
{{/if}}
|
|
93
|
-
|
|
94
|
-
### Assigned Items
|
|
95
|
-
|
|
96
|
-
| Item | Title | Type | Status / Severity |
|
|
97
|
-
|---|---|---|---|
|
|
85
|
+
| Item | Type | Status |
|
|
86
|
+
|---|---|---|
|
|
98
87
|
{{#each resolved_items}}
|
|
99
|
-
{{#if is_story}}
|
|
100
|
-
| {{item_key}} | {{title}} | 📋 Story | {{status}} |
|
|
101
|
-
{{/if}}
|
|
102
|
-
{{#if is_bug}}
|
|
103
|
-
| {{item_key}} | {{title}} | 🐛 Bug | Severity: {{severity}} / {{bug_status}} |
|
|
104
|
-
{{/if}}
|
|
88
|
+
| {{id}} | {{#if is_story}}[story]{{/if}}{{#if is_bug}}[bug, {{severity}}]{{/if}} | {{status}} |
|
|
105
89
|
{{/each}}
|
|
90
|
+
{{#if items_empty}}
|
|
91
|
+
*(No items assigned)*
|
|
92
|
+
{{/if}}
|
|
106
93
|
|
|
107
|
-
{{
|
|
108
|
-
**⚠️ Data Integrity Warnings:**
|
|
109
|
-
{{#each data_integrity_warnings}}
|
|
110
|
-
- {{this}}
|
|
94
|
+
**Capacity:** {{capacity_bar}}
|
|
111
95
|
{{/each}}
|
|
112
|
-
|
|
96
|
+
</output>
|
|
113
97
|
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
{{
|
|
98
|
+
<action>Display closed sprints:</action>
|
|
99
|
+
<output>
|
|
100
|
+
{{#each closed_sprints}}
|
|
101
|
+
---
|
|
102
|
+
**{{sprint.name}}** (closed) -- {{item_count}} items completed
|
|
103
|
+
{{/each}}
|
|
117
104
|
</output>
|
|
118
105
|
</step>
|
|
119
106
|
|
|
120
|
-
<step n="
|
|
121
|
-
<action>
|
|
122
|
-
<
|
|
123
|
-
|
|
124
|
-
<output>
|
|
107
|
+
<step n="4" goal="Completed items summary">
|
|
108
|
+
<action>Count items with status "done" that are still present in non-closed sprint files (use {{total_done_in_sprints}} from step 3)</action>
|
|
109
|
+
<check if="total_done_in_sprints > 0">
|
|
110
|
+
<output>
|
|
125
111
|
---
|
|
126
112
|
|
|
127
|
-
##
|
|
113
|
+
## Completed Items
|
|
128
114
|
|
|
129
|
-
|
|
115
|
+
{{total_done_in_sprints}} done item(s) are still in sprint files. Run `/cleanup-done` to archive them and free capacity.
|
|
116
|
+
</output>
|
|
117
|
+
</check>
|
|
118
|
+
<check if="total_done_in_sprints == 0">
|
|
119
|
+
<action>Skip this section -- no done items lingering in sprints</action>
|
|
120
|
+
</check>
|
|
121
|
+
</step>
|
|
130
122
|
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
123
|
+
<step n="5" goal="Unassigned backlog">
|
|
124
|
+
<action>Filter {{backlog_items}} to find items where sprint is null (unassigned)</action>
|
|
125
|
+
<action>Exclude items with status "done" from the unassigned list</action>
|
|
126
|
+
<action>Sort unassigned items by priority ascending (lowest number = highest priority)</action>
|
|
127
|
+
<action>Store as {{unassigned_items}}</action>
|
|
128
|
+
<action>Store total count as {{unassigned_total}}</action>
|
|
129
|
+
<action>Take top 15 items for display as {{unassigned_display}}</action>
|
|
138
130
|
|
|
139
|
-
|
|
131
|
+
<check if="unassigned_total > 0">
|
|
132
|
+
<output>
|
|
133
|
+
---
|
|
140
134
|
|
|
141
|
-
|
|
135
|
+
## Unassigned Backlog
|
|
142
136
|
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
{{
|
|
147
|
-
| {{id}} | {{title}} | {{severity}} |
|
|
137
|
+
| # | Item | Type | Priority | Status |
|
|
138
|
+
|---|---|---|---|---|
|
|
139
|
+
{{#each unassigned_display}}
|
|
140
|
+
| {{priority}} | {{id}} | {{type}} | {{priority}} | {{status}} |
|
|
148
141
|
{{/each}}
|
|
149
|
-
{{
|
|
150
|
-
*(No unassigned bugs)*
|
|
151
|
-
{{/if}}
|
|
152
|
-
|
|
153
|
-
**Tip:** Use `/add-to-sprint` to assign unassigned items to a sprint.
|
|
154
|
-
</output>
|
|
155
|
-
</step>
|
|
156
|
-
|
|
157
|
-
<step n="6" goal="Offer next actions">
|
|
158
|
-
<ask>Options:
|
|
159
|
-
1. Show full unassigned backlog item list (IDs + titles + statuses)
|
|
160
|
-
2. Add items to a sprint — run `/add-to-sprint`
|
|
161
|
-
3. Modify a sprint — run `/modify-sprint`
|
|
162
|
-
4. Create a new sprint — run `/add-sprint`
|
|
163
|
-
5. Exit
|
|
142
|
+
{{#if unassigned_total > 15}}
|
|
164
143
|
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
144
|
+
... and {{unassigned_total - 15}} more
|
|
145
|
+
{{/if}}
|
|
146
|
+
</output>
|
|
147
|
+
</check>
|
|
148
|
+
<check if="unassigned_total == 0">
|
|
169
149
|
<output>
|
|
170
|
-
|
|
150
|
+
---
|
|
171
151
|
|
|
172
|
-
|
|
173
|
-
| Key | Title | Status |
|
|
174
|
-
|---|---|---|
|
|
175
|
-
{{#each unassigned_story_items}}
|
|
176
|
-
| {{key}} | {{title}} | {{status}} |
|
|
177
|
-
{{/each}}
|
|
152
|
+
## Unassigned Backlog
|
|
178
153
|
|
|
179
|
-
|
|
180
|
-
| ID | Title | Severity |
|
|
181
|
-
|---|---|---|
|
|
182
|
-
{{#each unassigned_bugs}}
|
|
183
|
-
| {{id}} | {{title}} | {{severity}} |
|
|
184
|
-
{{/each}}
|
|
154
|
+
*(All backlog items are assigned to sprints)*
|
|
185
155
|
</output>
|
|
156
|
+
</check>
|
|
157
|
+
</step>
|
|
158
|
+
|
|
159
|
+
<step n="6" goal="Next actions menu">
|
|
160
|
+
<ask>
|
|
161
|
+
**Next Actions:**
|
|
162
|
+
[1] Full backlog
|
|
163
|
+
[2] /add-to-sprint
|
|
164
|
+
[3] /remove-from-sprint
|
|
165
|
+
[4] /prioritize-backlog
|
|
166
|
+
[5] /add-sprint
|
|
167
|
+
[6] /cleanup-done
|
|
168
|
+
[7] Exit
|
|
169
|
+
|
|
170
|
+
Choice:
|
|
171
|
+
</ask>
|
|
172
|
+
<check if="choice == 1">
|
|
173
|
+
<action>Display all items from {{backlog_items}} in a table: id, type, priority, status, sprint, severity</action>
|
|
186
174
|
<goto step="6" />
|
|
187
175
|
</check>
|
|
188
176
|
<check if="choice == 2">
|
|
189
|
-
<output
|
|
177
|
+
<output>Run `/add-to-sprint` to assign backlog items to a sprint.</output>
|
|
190
178
|
</check>
|
|
191
179
|
<check if="choice == 3">
|
|
192
|
-
<output
|
|
180
|
+
<output>Run `/remove-from-sprint` to remove items from a sprint.</output>
|
|
193
181
|
</check>
|
|
194
182
|
<check if="choice == 4">
|
|
195
|
-
<output
|
|
183
|
+
<output>Run `/prioritize-backlog` to reorder backlog priorities.</output>
|
|
196
184
|
</check>
|
|
197
185
|
<check if="choice == 5">
|
|
186
|
+
<output>Run `/add-sprint` to create a new sprint.</output>
|
|
187
|
+
</check>
|
|
188
|
+
<check if="choice == 6">
|
|
189
|
+
<output>Run `/cleanup-done` to archive completed items from sprints.</output>
|
|
190
|
+
</check>
|
|
191
|
+
<check if="choice == 7">
|
|
198
192
|
<action>Exit workflow</action>
|
|
199
193
|
</check>
|
|
200
194
|
</step>
|
|
201
195
|
|
|
196
|
+
<step n="7" goal="Regenerate sprint-status.yaml (internal)" internal="true">
|
|
197
|
+
<action>This step runs automatically after display (steps 3-6) completes, before the workflow exits.</action>
|
|
198
|
+
|
|
199
|
+
<action>Read existing `_bmad-output/implementation-artifacts/sprint-status.yaml` if it exists</action>
|
|
200
|
+
<action>Preserve the STATUS DEFINITIONS comment block at the top of the file (lines starting with `#` that define status values)</action>
|
|
201
|
+
<action>Preserve any epic-* keys and *-retrospective keys from the existing file</action>
|
|
202
|
+
|
|
203
|
+
<action>Build the new development_status section:
|
|
204
|
+
- Source 1: {{backlog_items}} from backlog.yaml -- for each item where status is NOT "done", add an entry: key = item.id, value = item.status
|
|
205
|
+
- Source 2: sprint entity files -- for each sprint, for each item in sprint.items, ensure the item has an entry. If the item was already added from backlog.yaml, the backlog value wins. If the item is NOT in backlog.yaml, look up status from {{bug_metadata_map}} or {{status_fallback_map}}.
|
|
206
|
+
- Exclude items with status "done" -- only non-done items appear in sprint-status.yaml
|
|
207
|
+
</action>
|
|
208
|
+
|
|
209
|
+
<action>Collect sprint metadata for header comments:
|
|
210
|
+
- For each sprint: id, name, status, item count, capacity
|
|
211
|
+
</action>
|
|
212
|
+
|
|
213
|
+
<action>Get current ISO timestamp as {{generated_at}}</action>
|
|
214
|
+
|
|
215
|
+
<action>Write `_bmad-output/implementation-artifacts/sprint-status.yaml` with this structure:
|
|
216
|
+
|
|
217
|
+
```yaml
|
|
218
|
+
# generated: {{original_generated_date or generated_at}}
|
|
219
|
+
# updated: {{generated_at}} — regenerated by sprint-status-view
|
|
220
|
+
# project: {{project_name from existing file or "unknown"}}
|
|
221
|
+
# project_key: {{project_key from existing file or "NOKEY"}}
|
|
222
|
+
# tracking_system: file-system
|
|
223
|
+
# story_location: _bmad-output/implementation-artifacts
|
|
224
|
+
#
|
|
225
|
+
# Sprints:
|
|
226
|
+
{{#each sprints}}
|
|
227
|
+
# {{sprint.id}}: {{sprint.name}} ({{sprint.status}}) — {{item_count}}/{{sprint.capacity}} items
|
|
228
|
+
{{/each}}
|
|
229
|
+
#
|
|
230
|
+
# STATUS DEFINITIONS:
|
|
231
|
+
# ==================
|
|
232
|
+
# (preserve the full STATUS DEFINITIONS block from the existing file verbatim)
|
|
233
|
+
# If no existing file, use these defaults:
|
|
234
|
+
# backlog — item is in the backlog, not yet started
|
|
235
|
+
# ready-for-dev — story file created, ready for development
|
|
236
|
+
# in-progress — item is actively being worked on
|
|
237
|
+
# review — item is in review
|
|
238
|
+
# done — item is complete (excluded from this file)
|
|
239
|
+
|
|
240
|
+
{{#if preserved_epic_keys}}
|
|
241
|
+
# Epic tracking
|
|
242
|
+
{{#each preserved_epic_keys}}
|
|
243
|
+
{{key}}: {{value}}
|
|
244
|
+
{{/each}}
|
|
245
|
+
{{/if}}
|
|
246
|
+
|
|
247
|
+
development_status:
|
|
248
|
+
{{#each active_items}}
|
|
249
|
+
{{id}}: {{status}}
|
|
250
|
+
{{/each}}
|
|
251
|
+
|
|
252
|
+
{{#if preserved_retro_keys}}
|
|
253
|
+
# Retrospective tracking
|
|
254
|
+
{{#each preserved_retro_keys}}
|
|
255
|
+
{{key}}: {{value}}
|
|
256
|
+
{{/each}}
|
|
257
|
+
{{/if}}
|
|
258
|
+
```
|
|
259
|
+
|
|
260
|
+
</action>
|
|
261
|
+
</step>
|
|
262
|
+
|
|
202
263
|
</workflow>
|
|
@@ -1,16 +1,38 @@
|
|
|
1
|
+
<!-- IMPORTANT: This file must be kept in sync with lib/bmad-extension/skills/add-sprint/SKILL.md
|
|
2
|
+
SKILL.md is the authoritative source (resolved via skill:add-sprint in module-help.csv).
|
|
3
|
+
This workflow.md is a legacy copy. Any changes should be made to SKILL.md first, then synced here. -->
|
|
4
|
+
|
|
1
5
|
# Add Sprint Workflow
|
|
2
6
|
|
|
3
|
-
Guided workflow to create a new sprint with capacity limits
|
|
7
|
+
Guided workflow to create a new sprint entity with capacity limits, optional ISO dates, and structured YAML schema.
|
|
4
8
|
|
|
5
9
|
<workflow>
|
|
6
10
|
|
|
7
|
-
<step n="1" goal="Gather sprint number and name">
|
|
8
|
-
<action>Ask the user for the sprint number
|
|
9
|
-
<ask>What is the sprint number? (e.g., 1)</ask>
|
|
10
|
-
<action>Store as {{
|
|
11
|
-
<
|
|
12
|
-
<action>
|
|
13
|
-
<
|
|
11
|
+
<step n="1" goal="Gather and validate sprint number and name">
|
|
12
|
+
<action>Ask the user for the sprint number</action>
|
|
13
|
+
<ask>What is the sprint number? (positive integer, e.g., 1, 2, 3)</ask>
|
|
14
|
+
<action>Store input as {{sprint_number_input}}</action>
|
|
15
|
+
<action>Validate {{sprint_number_input}} matches `^[1-9]\d*$` (positive integer, no leading zeros, no non-numeric characters)</action>
|
|
16
|
+
<action>Validate {{sprint_number_input}} is <= 9999</action>
|
|
17
|
+
<check if="{{sprint_number_input}} fails validation (zero, negative, non-numeric, leading zeros like '03', or > 9999)">
|
|
18
|
+
<output>❌ Invalid sprint number: "{{sprint_number_input}}". Must be a positive integer (1-9999), no leading zeros.</output>
|
|
19
|
+
<goto step="1" />
|
|
20
|
+
</check>
|
|
21
|
+
<action>Store as {{sprint_number}} (integer)</action>
|
|
22
|
+
<action>Construct {{sprint_id}} = "sprint-{{sprint_number}}"</action>
|
|
23
|
+
|
|
24
|
+
<!-- Smart default name: detect naming patterns from existing sprints -->
|
|
25
|
+
<action>Glob `_bmad-output/implementation-artifacts/sprints/sprint-*.yaml` to discover existing sprint files</action>
|
|
26
|
+
<action>If existing sprints found, read the `name` field from the most recent one (highest sprint number)</action>
|
|
27
|
+
<action>Infer a smart default name:
|
|
28
|
+
- If previous name follows a sequential pattern with a numeric suffix (e.g., "app04"), suggest the next increment (e.g., "app05")
|
|
29
|
+
- If previous name follows a date pattern (e.g., "2026-W14"), suggest the next date interval
|
|
30
|
+
- If previous name is "Sprint {n}", suggest "Sprint {{sprint_number}}"
|
|
31
|
+
- If no pattern detected or no existing sprints, default to "Sprint {{sprint_number}}"
|
|
32
|
+
</action>
|
|
33
|
+
<ask>Sprint name? (press Enter for "{{default_name}}", or type a custom name):</ask>
|
|
34
|
+
<action>If user presses Enter or leaves blank, set {{sprint_name}} = "{{default_name}}"</action>
|
|
35
|
+
<action>If user provides input, store as {{sprint_name}}</action>
|
|
14
36
|
</step>
|
|
15
37
|
|
|
16
38
|
<step n="2" goal="Gather capacity as positive integer">
|
|
@@ -25,32 +47,71 @@ Guided workflow to create a new sprint with capacity limits for realistic sprint
|
|
|
25
47
|
<action>Store as {{capacity}} (integer)</action>
|
|
26
48
|
</step>
|
|
27
49
|
|
|
28
|
-
<step n="
|
|
29
|
-
<action>Explain: start
|
|
30
|
-
<ask>Optional — Sprint start
|
|
31
|
-
<action>Store as {{
|
|
32
|
-
<
|
|
33
|
-
|
|
50
|
+
<step n="3a" goal="Gather optional start date (ISO format)">
|
|
51
|
+
<action>Explain: start and end dates are optional ISO dates (YYYY-MM-DD format). Press Enter to skip.</action>
|
|
52
|
+
<ask>Optional — Sprint start date (YYYY-MM-DD, press Enter to skip):</ask>
|
|
53
|
+
<action>Store input as {{start_input}}</action>
|
|
54
|
+
<check if="{{start_input}} is not empty">
|
|
55
|
+
<action>Validate {{start_input}} matches regex `^\d{4}-\d{2}-\d{2}$`</action>
|
|
56
|
+
<action>Verify {{start_input}} resolves to a real calendar date (reject impossible dates like 2026-02-30, 2026-13-45, etc.)</action>
|
|
57
|
+
<check if="{{start_input}} fails date validation">
|
|
58
|
+
<output>❌ Invalid date: "{{start_input}}". Must be a valid date in YYYY-MM-DD format (e.g., 2026-04-01).</output>
|
|
59
|
+
<goto step="3a" />
|
|
60
|
+
</check>
|
|
61
|
+
</check>
|
|
62
|
+
<action>Store as {{start_date}} (valid ISO date string, or empty string "" if skipped)</action>
|
|
63
|
+
</step>
|
|
64
|
+
|
|
65
|
+
<step n="3b" goal="Gather optional end date (ISO format)">
|
|
66
|
+
<ask>Optional — Sprint end date (YYYY-MM-DD, press Enter to skip):</ask>
|
|
67
|
+
<action>Store input as {{end_input}}</action>
|
|
68
|
+
<check if="{{end_input}} is not empty">
|
|
69
|
+
<action>Validate {{end_input}} matches regex `^\d{4}-\d{2}-\d{2}$`</action>
|
|
70
|
+
<action>Verify {{end_input}} resolves to a real calendar date</action>
|
|
71
|
+
<check if="{{end_input}} fails date validation">
|
|
72
|
+
<output>❌ Invalid date: "{{end_input}}". Must be a valid date in YYYY-MM-DD format (e.g., 2026-04-14).</output>
|
|
73
|
+
<goto step="3b" />
|
|
74
|
+
</check>
|
|
75
|
+
</check>
|
|
76
|
+
<action>Store as {{end_date}} (valid ISO date string, or empty string "" if skipped)</action>
|
|
77
|
+
|
|
78
|
+
<check if="both {{start_date}} and {{end_date}} are non-empty AND {{start_date}} > {{end_date}}">
|
|
79
|
+
<output>❌ Invalid date range: start date ({{start_date}}) is after end date ({{end_date}}). Start must be on or before end.</output>
|
|
80
|
+
<goto step="3a" />
|
|
81
|
+
</check>
|
|
34
82
|
</step>
|
|
35
83
|
|
|
36
84
|
<step n="4" goal="Confirm and validate all inputs">
|
|
37
85
|
<output>
|
|
38
86
|
## Sprint Summary — Please Confirm
|
|
39
87
|
|
|
40
|
-
- **Sprint
|
|
41
|
-
- **Sprint Name:** {{sprint_name}}
|
|
88
|
+
- **Sprint ID:** {{sprint_id}}
|
|
89
|
+
- **Sprint Name:** "{{sprint_name}}"
|
|
90
|
+
- **Status:** planning
|
|
42
91
|
- **Capacity (max items):** {{capacity}}
|
|
43
|
-
- **Start
|
|
44
|
-
- **End
|
|
45
|
-
- **
|
|
92
|
+
- **Start Date:** {{start_date}} *(empty if skipped)*
|
|
93
|
+
- **End Date:** {{end_date}} *(empty if skipped)*
|
|
94
|
+
- **Items:** [] *(empty — items assigned via /add-to-sprint)*
|
|
95
|
+
- **Output File:** `_bmad-output/implementation-artifacts/sprints/{{sprint_id}}.yaml`
|
|
46
96
|
</output>
|
|
47
97
|
<ask>Confirm creation? [y] Yes / [n] Cancel / [e] Edit a field:</ask>
|
|
48
98
|
<check if="user selects 'e'">
|
|
49
99
|
<ask>Which field to edit? (number / name / capacity / start / end)</ask>
|
|
50
100
|
<check if="field == 'number'">
|
|
51
|
-
<ask>New sprint number
|
|
52
|
-
<action>Store as {{
|
|
53
|
-
<action>
|
|
101
|
+
<ask>New sprint number? (positive integer, 1-9999)</ask>
|
|
102
|
+
<action>Store input as {{sprint_number_input}}</action>
|
|
103
|
+
<action>Validate {{sprint_number_input}} matches `^[1-9]\d*$` and is <= 9999</action>
|
|
104
|
+
<check if="{{sprint_number_input}} fails validation">
|
|
105
|
+
<output>❌ Invalid sprint number: "{{sprint_number_input}}". Must be a positive integer (1-9999), no leading zeros.</output>
|
|
106
|
+
<goto step="4" />
|
|
107
|
+
</check>
|
|
108
|
+
<action>Store as {{sprint_number}} (integer)</action>
|
|
109
|
+
<action>Construct {{sprint_id}} = "sprint-{{sprint_number}}"</action>
|
|
110
|
+
<action>If sprint name was using previous default "Sprint {old_n}", update to "Sprint {{sprint_number}}"</action>
|
|
111
|
+
<action>Check if file exists at `_bmad-output/implementation-artifacts/sprints/{{sprint_id}}.yaml`</action>
|
|
112
|
+
<check if="file already exists at new path">
|
|
113
|
+
<output>⚠️ A sprint entity already exists at `_bmad-output/implementation-artifacts/sprints/{{sprint_id}}.yaml`. You will be prompted to overwrite at creation.</output>
|
|
114
|
+
</check>
|
|
54
115
|
<goto step="4" />
|
|
55
116
|
</check>
|
|
56
117
|
<check if="field == 'name'">
|
|
@@ -59,45 +120,74 @@ Guided workflow to create a new sprint with capacity limits for realistic sprint
|
|
|
59
120
|
<goto step="4" />
|
|
60
121
|
</check>
|
|
61
122
|
<check if="field == 'capacity'"><goto step="2" /></check>
|
|
62
|
-
<check if="field == 'start'"><goto step="
|
|
63
|
-
<check if="field == 'end'"><goto step="
|
|
123
|
+
<check if="field == 'start'"><goto step="3a" /></check>
|
|
124
|
+
<check if="field == 'end'"><goto step="3b" /></check>
|
|
125
|
+
<check if="field is not recognized">
|
|
126
|
+
<output>❌ Unrecognized field: "{{field}}". Valid options: number, name, capacity, start, end.</output>
|
|
127
|
+
<goto step="4" />
|
|
128
|
+
</check>
|
|
64
129
|
</check>
|
|
65
130
|
<check if="user selects 'n'">
|
|
66
131
|
<output>❌ Sprint creation cancelled.</output>
|
|
67
132
|
<action>Exit workflow</action>
|
|
68
133
|
</check>
|
|
134
|
+
<check if="user input is not 'y', 'n', or 'e'">
|
|
135
|
+
<output>❌ Unrecognized option: "{{user_input}}". Please enter [y] Yes, [n] Cancel, or [e] Edit a field.</output>
|
|
136
|
+
<goto step="4" />
|
|
137
|
+
</check>
|
|
69
138
|
</step>
|
|
70
139
|
|
|
71
|
-
<step n="5" goal="Generate sprint
|
|
72
|
-
<action>Determine output path: `_bmad-output/implementation-artifacts/
|
|
73
|
-
<action>
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
140
|
+
<step n="5" goal="Generate sprint entity YAML file">
|
|
141
|
+
<action>Determine output path: `_bmad-output/implementation-artifacts/sprints/{{sprint_id}}.yaml`</action>
|
|
142
|
+
<action>Ensure directory `_bmad-output/implementation-artifacts/sprints/` exists (create if needed)</action>
|
|
143
|
+
|
|
144
|
+
<!-- Overwrite protection for new path -->
|
|
145
|
+
<action>Check if file already exists at `_bmad-output/implementation-artifacts/sprints/{{sprint_id}}.yaml`</action>
|
|
146
|
+
<check if="file already exists at new path">
|
|
147
|
+
<anchor id="overwrite_prompt" />
|
|
148
|
+
<output>⚠️ A sprint entity already exists at `_bmad-output/implementation-artifacts/sprints/{{sprint_id}}.yaml`.</output>
|
|
149
|
+
<ask>Overwrite existing sprint? [y] Yes / [n] Cancel:</ask>
|
|
77
150
|
<check if="user selects 'n'">
|
|
78
|
-
<output>❌ Sprint creation cancelled to preserve existing sprint
|
|
151
|
+
<output>❌ Sprint creation cancelled to preserve existing sprint.</output>
|
|
79
152
|
<action>Exit workflow</action>
|
|
80
153
|
</check>
|
|
154
|
+
<check if="user input is not 'y' or 'n'">
|
|
155
|
+
<output>❌ Unrecognized option: "{{user_input}}". Please enter [y] Yes or [n] Cancel.</output>
|
|
156
|
+
<goto anchor="overwrite_prompt" />
|
|
157
|
+
</check>
|
|
81
158
|
</check>
|
|
159
|
+
|
|
160
|
+
<!-- Advisory check for old-format file -->
|
|
161
|
+
<action>Check if file exists at old path: `_bmad-output/implementation-artifacts/sprint-plan-{{sprint_number}}.yaml`</action>
|
|
162
|
+
<check if="old-format file exists">
|
|
163
|
+
<output>ℹ️ **Note:** An old-format sprint file exists at `_bmad-output/implementation-artifacts/sprint-plan-{{sprint_number}}.yaml`. The new sprint will be created at the new path. The old file is NOT auto-migrated — review or remove it manually if no longer needed.</output>
|
|
164
|
+
</check>
|
|
165
|
+
|
|
82
166
|
<action>Get current ISO timestamp for created_date and last_modified</action>
|
|
83
|
-
<action>Write sprint
|
|
167
|
+
<action>Write sprint entity YAML to `_bmad-output/implementation-artifacts/sprints/{{sprint_id}}.yaml` with this structure:
|
|
84
168
|
|
|
85
169
|
```yaml
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
capacity: {{capacity}}
|
|
89
|
-
assigned_items: []
|
|
170
|
+
id: {{sprint_id}}
|
|
171
|
+
name: "{{sprint_name}}"
|
|
90
172
|
status: planning
|
|
91
|
-
|
|
92
|
-
|
|
173
|
+
capacity: {{capacity}}
|
|
174
|
+
start: "{{start_date}}"
|
|
175
|
+
end: "{{end_date}}"
|
|
176
|
+
items: []
|
|
93
177
|
created_date: "{{current_iso_timestamp}}"
|
|
94
178
|
last_modified: "{{current_iso_timestamp}}"
|
|
95
179
|
```
|
|
180
|
+
|
|
181
|
+
**YAML output rules:**
|
|
182
|
+
- Always quote the `name` field to handle special characters
|
|
183
|
+
- `start` and `end` are empty string `""` if skipped
|
|
184
|
+
- `items` is always empty array `[]` at creation
|
|
185
|
+
- `status` is always `planning` at creation (never `active` or `closed`)
|
|
96
186
|
</action>
|
|
97
187
|
<output>
|
|
98
188
|
✅ **Sprint created successfully!**
|
|
99
189
|
|
|
100
|
-
- **File:** `_bmad-output/implementation-artifacts/
|
|
190
|
+
- **File:** `_bmad-output/implementation-artifacts/sprints/{{sprint_id}}.yaml`
|
|
101
191
|
- **Sprint:** {{sprint_name}}
|
|
102
192
|
- **Capacity:** {{capacity}} items
|
|
103
193
|
- **Status:** planning
|