skilldrop-cli 0.11.5 → 0.11.7
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/README.md +162 -23
- package/contracts/loop.schema.json +87 -0
- package/contracts/terminals.json +33 -0
- package/loops/build/LOOP.md +65 -0
- package/loops/build/loop.json +48 -0
- package/loops/design/LOOP.md +68 -0
- package/loops/design/loop.json +47 -0
- package/loops/discover/LOOP.md +66 -0
- package/loops/discover/loop.json +41 -0
- package/loops/operate/LOOP.md +69 -0
- package/loops/operate/loop.json +41 -0
- package/loops/ship-a-draft/LOOP.md +62 -0
- package/loops/ship-a-draft/loop.json +41 -0
- package/package.json +4 -2
- package/skills/architecture-diagrams/manifest.json +3 -0
- package/skills/bug-triage/manifest.json +3 -0
- package/skills/design-doc/manifest.json +3 -0
- package/skills/feature-implement-loop/manifest.json +3 -0
- package/skills/incident-comms/manifest.json +3 -0
- package/skills/nfr-spec/manifest.json +5 -0
- package/skills/observability-plan/manifest.json +4 -0
- package/skills/output-hygiene/manifest.json +3 -0
- package/skills/postmortem-generator/manifest.json +3 -0
- package/skills/prd-draft/manifest.json +5 -0
- package/skills/pre-merge-review/manifest.json +3 -0
- package/skills/requirements-interview/manifest.json +3 -0
- package/skills/strategy-analysis/manifest.json +4 -0
- package/skills/user-journey-map/manifest.json +4 -0
- package/skills/user-story-splitter/manifest.json +3 -0
package/README.md
CHANGED
|
@@ -20,55 +20,194 @@ Every skill is a plain `SKILL.md` folder — the [**Agent Skills open standard**
|
|
|
20
20
|
|
|
21
21
|
## How skilldrop works
|
|
22
22
|
|
|
23
|
-
skilldrop
|
|
23
|
+
skilldrop ships **loops**, not just parts. A loop is a named sequence of stages over existing skills with a gate between them: [`loops/<name>/LOOP.md`](loops/) is what an agent reads, `loop.json` is the machine-readable contract ([RFC-0028](docs/rfcs/0028-loops-as-a-primitive.md)). **Nothing comes out of a loop until it passes that loop's gate.**
|
|
24
24
|
|
|
25
|
-
|
|
25
|
+
A loop *sequences* skills — it never contains one. Every skill stays independently installable and runnable on its own, which is what keeps a single-folder copy working in Cursor, Kiro, or Aider.
|
|
26
26
|
|
|
27
|
-
|
|
27
|
+
Four loops cover the lifecycle, and they are separated by **reversibility** — how expensive the mistake is to unwind — which is why each gets its own gate rather than folding into a neighbour:
|
|
28
|
+
|
|
29
|
+
| Loop | Takes | Gate | Produces | Mistake costs |
|
|
30
|
+
|---|---|---|---|---|
|
|
31
|
+
| [`discover`](loops/discover/LOOP.md) | interviews, journeys, a strategy question | **G0** human — a person ratifies the brief | a ratified requirement | a re-brief |
|
|
32
|
+
| [`design`](loops/design/LOOP.md) | a ratified requirement | **G1** review — `council-review`'s panel | a recorded decision (ADR) | months, unwound in code |
|
|
33
|
+
| [`build`](loops/build/LOOP.md) | an agreed requirement or triaged defect | **G2** mechanical — `pre-merge-review`'s gate script decides | merged code | a revert |
|
|
34
|
+
| [`operate`](loops/operate/LOOP.md) | a shipped service | **G3** human — the incident is closed | a postmortem and runbook deltas | live users, irreversible |
|
|
35
|
+
|
|
36
|
+
Plus one **wrapper**, which is not a lifecycle stage but the two passes either side of *any* generator:
|
|
37
|
+
|
|
38
|
+
| Wrapper | Takes | Gate | Produces |
|
|
39
|
+
|---|---|---|---|
|
|
40
|
+
| [`ship-a-draft`](loops/ship-a-draft/LOOP.md) | raw notes, a transcript, a ticket | **G4** review — `doc-critique`'s verdict | a stakeholder-ready artifact |
|
|
41
|
+
|
|
42
|
+
Every gate emits a verdict from one shared vocabulary ([`contracts/terminals.json`](contracts/terminals.json)) in five classes — pass, conditional, revise, redirect, blocked — so `READY`, `PROCEED` and `SHIP IT` are recognisably the same kind of answer. Both diagrams render on GitHub; the Mermaid sources live in [`docs/`](docs/) for easy re-rendering.
|
|
43
|
+
|
|
44
|
+
*Diagrams below are generated from each loop's `loop.json` by [`build_loops.py`](build_loops.py) — edit the contract, not the picture.*
|
|
45
|
+
|
|
46
|
+
### `discover` — raw signal to a ratified requirement
|
|
47
|
+
|
|
48
|
+
Interviews, journeys and strategy questions become one tagged brief, then numbered requirements a **human ratifies** before any design starts.
|
|
49
|
+
|
|
50
|
+
<!-- loop:discover:start -->
|
|
51
|
+
|
|
52
|
+
```mermaid
|
|
53
|
+
%%{init: {'theme':'base','themeVariables':{'fontFamily':'Segoe UI, Helvetica, Arial','fontSize':'15px','lineColor':'#9AA5B1'},'flowchart':{'curve':'basis','rankSpacing':70,'nodeSpacing':50,'padding':16}}}%%
|
|
54
|
+
flowchart LR
|
|
55
|
+
classDef gen fill:#E8F0FE,stroke:#4C7DF0,stroke-width:1.5px,color:#1A3A8F;
|
|
56
|
+
classDef review fill:#FDEAEA,stroke:#E05B5B,stroke-width:1.5px,color:#8A1F1F;
|
|
57
|
+
classDef gate fill:#FBE3A2,stroke:#D9971E,stroke-width:2px,color:#6B4500,font-weight:bold;
|
|
58
|
+
classDef ship fill:#E6F7EC,stroke:#34A853,stroke-width:2px,color:#0F6B33,font-weight:bold;
|
|
59
|
+
|
|
60
|
+
gather["gather<br/><small>requirements-interview +2</small>"]:::gen
|
|
61
|
+
structure["structure<br/><small>brief-intake</small>"]:::gen
|
|
62
|
+
specify["specify<br/><small>prd-draft</small>"]:::gen
|
|
63
|
+
ratify["ratify<br/><small>doc-critique</small>"]:::gate
|
|
64
|
+
G0{"G0 · human"}:::gate
|
|
65
|
+
DONE(["complete"]):::ship
|
|
66
|
+
|
|
67
|
+
gather --> structure
|
|
68
|
+
structure --> specify
|
|
69
|
+
specify --> ratify
|
|
70
|
+
ratify --> G0
|
|
71
|
+
G0 == "PROCEED" ==> DONE
|
|
72
|
+
|
|
73
|
+
G0 -- "REVISE (max 3)" --> structure
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
<!-- loop:discover:end -->
|
|
77
|
+
|
|
78
|
+
### `design` — a requirement to a recorded decision
|
|
79
|
+
|
|
80
|
+
Constraints first, then structure and diagrams, then an attack, then a panel that must agree — and only then is the decision written down as an ADR.
|
|
81
|
+
|
|
82
|
+
<!-- loop:design:start -->
|
|
83
|
+
|
|
84
|
+
```mermaid
|
|
85
|
+
%%{init: {'theme':'base','themeVariables':{'fontFamily':'Segoe UI, Helvetica, Arial','fontSize':'15px','lineColor':'#9AA5B1'},'flowchart':{'curve':'basis','rankSpacing':70,'nodeSpacing':50,'padding':16}}}%%
|
|
86
|
+
flowchart LR
|
|
87
|
+
classDef gen fill:#E8F0FE,stroke:#4C7DF0,stroke-width:1.5px,color:#1A3A8F;
|
|
88
|
+
classDef review fill:#FDEAEA,stroke:#E05B5B,stroke-width:1.5px,color:#8A1F1F;
|
|
89
|
+
classDef gate fill:#FBE3A2,stroke:#D9971E,stroke-width:2px,color:#6B4500,font-weight:bold;
|
|
90
|
+
classDef ship fill:#E6F7EC,stroke:#34A853,stroke-width:2px,color:#0F6B33,font-weight:bold;
|
|
91
|
+
|
|
92
|
+
constrain["constrain<br/><small>nfr-spec</small>"]:::gen
|
|
93
|
+
shape["shape<br/><small>design-doc·architecture-diagrams</small>"]:::gen
|
|
94
|
+
threat["threat<br/><small>threat-model</small>"]:::review
|
|
95
|
+
ratify["ratify<br/><small>council-review</small>"]:::gate
|
|
96
|
+
record["record<br/><small>adr-generator</small>"]:::gen
|
|
97
|
+
G1{"G1 · review"}:::gate
|
|
98
|
+
DONE(["complete"]):::ship
|
|
99
|
+
|
|
100
|
+
constrain --> shape
|
|
101
|
+
shape --> threat
|
|
102
|
+
threat --> ratify
|
|
103
|
+
ratify --> G1
|
|
104
|
+
G1 == "PROCEED" ==> record
|
|
105
|
+
record --> DONE
|
|
106
|
+
|
|
107
|
+
G1 -- "REVISE (max 3)" --> shape
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
<!-- loop:design:end -->
|
|
111
|
+
|
|
112
|
+
### `build` — a requirement to merged code
|
|
113
|
+
|
|
114
|
+
A vertical slice becomes shippable code through a self-correcting loop, gated by a script whose exit code decides. The inner generate-challenge cycle is the [`feature-implement-loop`](skills/feature-implement-loop/SKILL.md) skill.
|
|
115
|
+
|
|
116
|
+
<!-- loop:build:start -->
|
|
28
117
|
|
|
29
118
|
```mermaid
|
|
30
119
|
%%{init: {'theme':'base','themeVariables':{'fontFamily':'Segoe UI, Helvetica, Arial','fontSize':'15px','lineColor':'#9AA5B1'},'flowchart':{'curve':'basis','rankSpacing':70,'nodeSpacing':50,'padding':16}}}%%
|
|
31
120
|
flowchart LR
|
|
32
|
-
classDef input fill:#FFF4E0,stroke:#E8A93B,stroke-width:2px,color:#7A4E00,font-weight:bold;
|
|
33
121
|
classDef gen fill:#E8F0FE,stroke:#4C7DF0,stroke-width:1.5px,color:#1A3A8F;
|
|
34
122
|
classDef review fill:#FDEAEA,stroke:#E05B5B,stroke-width:1.5px,color:#8A1F1F;
|
|
123
|
+
classDef gate fill:#FBE3A2,stroke:#D9971E,stroke-width:2px,color:#6B4500,font-weight:bold;
|
|
35
124
|
classDef ship fill:#E6F7EC,stroke:#34A853,stroke-width:2px,color:#0F6B33,font-weight:bold;
|
|
36
125
|
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
126
|
+
shape["shape<br/><small>user-story-splitter·bug-triage</small>"]:::gen
|
|
127
|
+
implement["implement<br/><small>feature-implement-loop</small>"]:::gen
|
|
128
|
+
verify["verify<br/><small>pre-merge-review</small>"]:::review
|
|
129
|
+
decide["decide<br/><small>council-review</small>"]:::gate
|
|
130
|
+
G2{"G2 · mechanical"}:::gate
|
|
131
|
+
G2_1{"G2.1 · human"}:::gate
|
|
132
|
+
DONE(["complete"]):::ship
|
|
133
|
+
|
|
134
|
+
shape --> implement
|
|
135
|
+
implement --> verify
|
|
136
|
+
verify --> G2
|
|
137
|
+
G2 == "READY" ==> decide
|
|
138
|
+
decide --> G2_1
|
|
139
|
+
G2_1 == "PROCEED" ==> DONE
|
|
140
|
+
|
|
141
|
+
G2 -- "NOT READY (max 3)" --> implement
|
|
142
|
+
G2_1 -- "REVISE (max 3)" --> shape
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
<!-- loop:build:end -->
|
|
146
|
+
|
|
147
|
+
### `operate` — a shipped service through detection and learning
|
|
148
|
+
|
|
149
|
+
Instrument, write the runbook, communicate the incident, then feed the postmortem's runbook deltas straight back into the runbook. The one loop whose failures are live.
|
|
150
|
+
|
|
151
|
+
<!-- loop:operate:start -->
|
|
42
152
|
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
153
|
+
```mermaid
|
|
154
|
+
%%{init: {'theme':'base','themeVariables':{'fontFamily':'Segoe UI, Helvetica, Arial','fontSize':'15px','lineColor':'#9AA5B1'},'flowchart':{'curve':'basis','rankSpacing':70,'nodeSpacing':50,'padding':16}}}%%
|
|
155
|
+
flowchart LR
|
|
156
|
+
classDef gen fill:#E8F0FE,stroke:#4C7DF0,stroke-width:1.5px,color:#1A3A8F;
|
|
157
|
+
classDef review fill:#FDEAEA,stroke:#E05B5B,stroke-width:1.5px,color:#8A1F1F;
|
|
158
|
+
classDef gate fill:#FBE3A2,stroke:#D9971E,stroke-width:2px,color:#6B4500,font-weight:bold;
|
|
159
|
+
classDef ship fill:#E6F7EC,stroke:#34A853,stroke-width:2px,color:#0F6B33,font-weight:bold;
|
|
160
|
+
|
|
161
|
+
instrument["instrument<br/><small>observability-plan</small>"]:::gen
|
|
162
|
+
document["document<br/><small>runbook-generator</small>"]:::gen
|
|
163
|
+
respond["respond<br/><small>incident-comms</small>"]:::gen
|
|
164
|
+
learn["learn<br/><small>postmortem-generator</small>"]:::review
|
|
165
|
+
G3{"G3 · human"}:::gate
|
|
166
|
+
DONE(["complete"]):::ship
|
|
167
|
+
|
|
168
|
+
instrument --> document
|
|
169
|
+
document --> respond
|
|
170
|
+
respond --> learn
|
|
171
|
+
learn --> G3
|
|
172
|
+
G3 == "PROCEED" ==> DONE
|
|
173
|
+
|
|
174
|
+
G3 -- "REVISE (max 3)" --> document
|
|
46
175
|
```
|
|
47
176
|
|
|
48
|
-
|
|
177
|
+
<!-- loop:operate:end -->
|
|
178
|
+
|
|
179
|
+
### `ship-a-draft` — raw input to a stakeholder-ready artifact
|
|
49
180
|
|
|
50
|
-
|
|
181
|
+
The wrapper: structured intake before any generator, critique and a machine-residue scrub after. Loops back through intake — not the draft — until it's approved.
|
|
182
|
+
|
|
183
|
+
<!-- loop:ship-a-draft:start -->
|
|
51
184
|
|
|
52
185
|
```mermaid
|
|
53
186
|
%%{init: {'theme':'base','themeVariables':{'fontFamily':'Segoe UI, Helvetica, Arial','fontSize':'15px','lineColor':'#9AA5B1'},'flowchart':{'curve':'basis','rankSpacing':70,'nodeSpacing':50,'padding':16}}}%%
|
|
54
187
|
flowchart LR
|
|
55
|
-
classDef input fill:#FFF4E0,stroke:#E8A93B,stroke-width:2px,color:#7A4E00,font-weight:bold;
|
|
56
188
|
classDef gen fill:#E8F0FE,stroke:#4C7DF0,stroke-width:1.5px,color:#1A3A8F;
|
|
57
189
|
classDef review fill:#FDEAEA,stroke:#E05B5B,stroke-width:1.5px,color:#8A1F1F;
|
|
58
190
|
classDef gate fill:#FBE3A2,stroke:#D9971E,stroke-width:2px,color:#6B4500,font-weight:bold;
|
|
59
191
|
classDef ship fill:#E6F7EC,stroke:#34A853,stroke-width:2px,color:#0F6B33,font-weight:bold;
|
|
60
192
|
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
193
|
+
intake["intake<br/><small>brief-intake</small>"]:::gen
|
|
194
|
+
draft["draft<br/><small>*</small>"]:::gen
|
|
195
|
+
critique["critique<br/><small>doc-critique</small>"]:::review
|
|
196
|
+
polish["polish<br/><small>output-hygiene</small>"]:::review
|
|
197
|
+
G4{"G4 · review"}:::gate
|
|
198
|
+
DONE(["complete"]):::ship
|
|
199
|
+
|
|
200
|
+
intake --> draft
|
|
201
|
+
draft --> critique
|
|
202
|
+
critique --> G4
|
|
203
|
+
G4 == "SHIP IT" ==> polish
|
|
204
|
+
polish --> DONE
|
|
66
205
|
|
|
67
|
-
|
|
68
|
-
gate -- "yes (up to 3 rounds)" --> gC
|
|
69
|
-
gate == "no" ==> SHIP
|
|
206
|
+
G4 -- "MAJOR REWRITE (max 3)" --> intake
|
|
70
207
|
```
|
|
71
208
|
|
|
209
|
+
<!-- loop:ship-a-draft:end -->
|
|
210
|
+
|
|
72
211
|
## Skills in this repo
|
|
73
212
|
|
|
74
213
|
### Pipeline glue
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
|
+
"$id": "https://github.com/sananthanarayan/skilldrop/contracts/loop.schema.json",
|
|
4
|
+
"title": "skilldrop loop",
|
|
5
|
+
"$comment": "RFC-0028. A loop sequences existing skills; it never contains one. Skills stay in flat skills/<name> folders and stay independently installable — a loop is a named order plus the gates between stages. Enforced by validate.py with hand-rolled stdlib checks: skilldrop ships zero runtime dependencies and this file must not become a reason to add `jsonschema`.",
|
|
6
|
+
"type": "object",
|
|
7
|
+
"additionalProperties": false,
|
|
8
|
+
"required": ["name", "description", "entrypoint", "kind", "stages"],
|
|
9
|
+
"properties": {
|
|
10
|
+
"$comment": { "type": "string" },
|
|
11
|
+
"name": {
|
|
12
|
+
"type": "string",
|
|
13
|
+
"pattern": "^[a-z0-9][a-z0-9-]*$",
|
|
14
|
+
"description": "Kebab-case. Must equal the folder name and the LOOP.md frontmatter name — the same triple-match skills are held to."
|
|
15
|
+
},
|
|
16
|
+
"version": { "type": "string" },
|
|
17
|
+
"description": {
|
|
18
|
+
"type": "string",
|
|
19
|
+
"description": "Use-case-first. First half says what the loop delivers; second half states the trigger phrases an agent matches on."
|
|
20
|
+
},
|
|
21
|
+
"entrypoint": { "const": "LOOP.md" },
|
|
22
|
+
"kind": {
|
|
23
|
+
"enum": ["loop", "wrapper"],
|
|
24
|
+
"description": "`loop` advances stage to stage toward a terminal. `wrapper` wraps an arbitrary generator skill chosen at run time — its stages are the passes either side of that generator."
|
|
25
|
+
},
|
|
26
|
+
"cap": {
|
|
27
|
+
"type": "integer",
|
|
28
|
+
"minimum": 1,
|
|
29
|
+
"maximum": 10,
|
|
30
|
+
"default": 3,
|
|
31
|
+
"description": "Maximum revision rounds before the loop stops looping and emits its conditional or blocked terminal. Default 3, matching agent-loop-design's revision cap."
|
|
32
|
+
},
|
|
33
|
+
"stages": {
|
|
34
|
+
"type": "array",
|
|
35
|
+
"minItems": 1,
|
|
36
|
+
"items": {
|
|
37
|
+
"type": "object",
|
|
38
|
+
"additionalProperties": false,
|
|
39
|
+
"required": ["id", "type", "intent", "skills"],
|
|
40
|
+
"properties": {
|
|
41
|
+
"id": { "type": "string", "pattern": "^[a-z0-9][a-z0-9-]*$" },
|
|
42
|
+
"type": {
|
|
43
|
+
"enum": ["generate", "verify", "gate"],
|
|
44
|
+
"description": "The three state types agent-loop-design mandates: 'Every loop has exactly these three state types.'"
|
|
45
|
+
},
|
|
46
|
+
"intent": { "type": "string", "description": "One line: what this stage is for." },
|
|
47
|
+
"skills": {
|
|
48
|
+
"type": "array",
|
|
49
|
+
"minItems": 1,
|
|
50
|
+
"items": { "type": "string" },
|
|
51
|
+
"description": "Skill folder names, in order. Each must be a real skills/<name>. `*` means any generator, and is legal only in a wrapper."
|
|
52
|
+
},
|
|
53
|
+
"gate": {
|
|
54
|
+
"type": "object",
|
|
55
|
+
"additionalProperties": false,
|
|
56
|
+
"required": ["id", "kind", "verdicts"],
|
|
57
|
+
"properties": {
|
|
58
|
+
"id": {
|
|
59
|
+
"type": "string",
|
|
60
|
+
"pattern": "^G[0-9]+(\\.[0-9]+)?$",
|
|
61
|
+
"description": "Named gate, unique across the repo. A gate is a place a human or a script can point at."
|
|
62
|
+
},
|
|
63
|
+
"kind": {
|
|
64
|
+
"enum": ["mechanical", "review", "human"],
|
|
65
|
+
"description": "mechanical = a script's exit code decides. review = a skill or subagent panel decides. human = a person decides and the agent may not proceed without it."
|
|
66
|
+
},
|
|
67
|
+
"script": {
|
|
68
|
+
"type": "string",
|
|
69
|
+
"description": "Repo-relative path to the deciding script. Required when kind is mechanical, forbidden otherwise."
|
|
70
|
+
},
|
|
71
|
+
"verdicts": {
|
|
72
|
+
"type": "array",
|
|
73
|
+
"minItems": 2,
|
|
74
|
+
"items": { "type": "string" },
|
|
75
|
+
"description": "Every verdict this gate can emit. All must exist in contracts/terminals.json. Must include >=1 pass-class and >=1 non-pass."
|
|
76
|
+
},
|
|
77
|
+
"revise_to": {
|
|
78
|
+
"type": "string",
|
|
79
|
+
"description": "Stage id a revise-class verdict returns to. Must be an earlier stage in this loop."
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$comment": "RFC-0028 — the shared verdict vocabulary. Before this file, every gating skill invented its own terminal words: feature-implement-loop says VERIFIED, pre-merge-review says READY, council-review says PROCEED, doc-critique says SHIP IT. They mean the same five things. A loop's gate declares which verdicts it can emit, and validate.py checks every one against this file — so a new loop cannot invent a sixth kind of 'yes'.",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"classes": {
|
|
5
|
+
"pass": "The gate is satisfied. The loop advances to the next stage, or terminates successfully.",
|
|
6
|
+
"conditional": "The gate is satisfied, but named open items travel forward with the artifact. Advancing is allowed; forgetting the items is not.",
|
|
7
|
+
"revise": "The gate is not satisfied and the fix is known. Return to the stage named by the loop's revision edge, subject to the cap.",
|
|
8
|
+
"redirect": "The gate is not satisfied and the work is the wrong shape. Do not revise — re-enter a different stage, a different loop, or a different artifact.",
|
|
9
|
+
"blocked": "The gate cannot be evaluated. A required input, decision, or permission is missing. Stop and name what is needed."
|
|
10
|
+
},
|
|
11
|
+
"verdicts": {
|
|
12
|
+
"VERIFIED": { "class": "pass", "origin": "feature-implement-loop" },
|
|
13
|
+
"READY": { "class": "pass", "origin": "pre-merge-review" },
|
|
14
|
+
"PROCEED": { "class": "pass", "origin": "council-review" },
|
|
15
|
+
"SHIP IT": { "class": "pass", "origin": "doc-critique" },
|
|
16
|
+
"VERIFIED WITH OPEN ITEMS": { "class": "conditional", "origin": "feature-implement-loop" },
|
|
17
|
+
"PROCEED WITH CONDITIONS": { "class": "conditional", "origin": "council-review" },
|
|
18
|
+
"SHIP WITH CHANGES": { "class": "conditional", "origin": "doc-critique" },
|
|
19
|
+
"NOT READY": { "class": "revise", "origin": "pre-merge-review" },
|
|
20
|
+
"REVISE": { "class": "revise", "origin": "council-review" },
|
|
21
|
+
"MAJOR REWRITE": { "class": "revise", "origin": "doc-critique" },
|
|
22
|
+
"RECONSIDER": { "class": "redirect", "origin": "council-review" },
|
|
23
|
+
"SPLIT": { "class": "redirect", "origin": "council-review" },
|
|
24
|
+
"WRONG ARTIFACT": { "class": "redirect", "origin": "doc-critique" },
|
|
25
|
+
"BLOCKED": { "class": "blocked", "origin": "feature-implement-loop" }
|
|
26
|
+
},
|
|
27
|
+
"rules": [
|
|
28
|
+
"Every gate declares at least one `pass` verdict and at least one non-pass verdict. A gate that can only succeed is not a gate.",
|
|
29
|
+
"Every gate can emit BLOCKED. A missing input is always possible and must never be fabricated past (AGENTS.md, non-interactive invocation).",
|
|
30
|
+
"A `revise` verdict is subject to the loop's `cap`. On the cap-th revise, the loop emits its conditional or blocked terminal instead of looping again.",
|
|
31
|
+
"A `redirect` verdict leaves the loop. It names where the work goes instead."
|
|
32
|
+
]
|
|
33
|
+
}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: build
|
|
3
|
+
description: Take an agreed requirement to merged code through a capped generate-verify-gate loop, with a mechanical gate that decides and a human who owns the merge. Use when the user wants to implement a story, fix a triaged bug, or ask whether a change is safe to merge.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# build
|
|
7
|
+
|
|
8
|
+
The repo-scope loop: a requirement enters, merged code leaves, and nothing crosses a stage
|
|
9
|
+
boundary without passing that stage's gate. This loop *sequences* skills — it never contains
|
|
10
|
+
one. Every skill named below stays independently installable and runnable on its own.
|
|
11
|
+
|
|
12
|
+
## Stages
|
|
13
|
+
|
|
14
|
+
| # | Stage | Type | Skills | Gate |
|
|
15
|
+
|---|---|---|---|---|
|
|
16
|
+
| 1 | `shape` | generate | [`user-story-splitter`](../../skills/user-story-splitter/SKILL.md), [`bug-triage`](../../skills/bug-triage/SKILL.md) | — |
|
|
17
|
+
| 2 | `implement` | generate | [`feature-implement-loop`](../../skills/feature-implement-loop/SKILL.md) | — |
|
|
18
|
+
| 3 | `verify` | verify | [`pre-merge-review`](../../skills/pre-merge-review/SKILL.md) | **G2** mechanical |
|
|
19
|
+
| 4 | `decide` | gate | [`council-review`](../../skills/council-review/SKILL.md) | **G2.1** human |
|
|
20
|
+
|
|
21
|
+
## How to run this loop
|
|
22
|
+
|
|
23
|
+
1. **Establish the unit of work.** New capability → `user-story-splitter`. Reported defect →
|
|
24
|
+
`bug-triage`. The stage is done when there is one vertical slice with acceptance criteria a
|
|
25
|
+
test can assert. Vague criteria are the single largest cause of a wasted round 3.
|
|
26
|
+
2. **Implement.** Hand the slice to `feature-implement-loop`, which runs its own capped
|
|
27
|
+
generate-challenge-gate cycle internally. Do not re-implement its rounds here — this loop's
|
|
28
|
+
`cap` governs returns from G2, not the inner skill's rounds.
|
|
29
|
+
3. **Verify at G2.** Run `pre-merge-review`. Its script decides and its panel explains:
|
|
30
|
+
`python3 skills/pre-merge-review/scripts/gate.py`. The exit code is the verdict —
|
|
31
|
+
`READY`, `NOT READY`, or `BLOCKED`.
|
|
32
|
+
4. **Honour the gate.** `NOT READY` returns to `implement`, up to `cap` (3) times. On the
|
|
33
|
+
third return, stop looping and emit `BLOCKED` naming what did not converge. Never edit the
|
|
34
|
+
gate to make it pass.
|
|
35
|
+
5. **Decide at G2.1.** The merge is a human's. Escalate design disagreements surfaced at G2 to
|
|
36
|
+
`council-review` rather than arguing them inside the diff; `RECONSIDER` and `SPLIT` both
|
|
37
|
+
leave this loop rather than revising within it.
|
|
38
|
+
|
|
39
|
+
## Verdicts
|
|
40
|
+
|
|
41
|
+
Defined in [`contracts/terminals.json`](../../contracts/terminals.json). G2 emits
|
|
42
|
+
`READY` / `NOT READY` / `BLOCKED`. G2.1 emits the council vocabulary. A `revise`-class verdict
|
|
43
|
+
returns to the stage named in `revise_to`; a `redirect`-class verdict leaves the loop.
|
|
44
|
+
|
|
45
|
+
## When a stage's skill is not installed
|
|
46
|
+
|
|
47
|
+
Skills install à la carte, so a stage may name a skill the target environment does not have.
|
|
48
|
+
Name the missing skill and skilldrop as its source, do the minimal inline version of that
|
|
49
|
+
stage, and record that the stage ran degraded. A missing skill is never a reason to skip a
|
|
50
|
+
**gate** — the gate is the loop's whole value.
|
|
51
|
+
|
|
52
|
+
## Quality bar
|
|
53
|
+
|
|
54
|
+
- **The gate decides, not the agent.** G2's verdict is `gate.py`'s exit code. An agent that reasons its way past a red gate has broken the loop, not passed it.
|
|
55
|
+
- **The cap is honoured.** Three returns to `implement`, then `BLOCKED` with what did not converge. A fourth round is a defect in this loop, not diligence.
|
|
56
|
+
- **Every stage leaves evidence.** Each stage names its skill, its verdict, and its round number, so the run is auditable after the fact rather than asserted.
|
|
57
|
+
- **Acceptance criteria exist before `implement` starts.** A slice whose criteria a test cannot assert is not shaped; return it to `shape`.
|
|
58
|
+
|
|
59
|
+
## Anti-patterns to avoid
|
|
60
|
+
|
|
61
|
+
- ❌ **Calling a skill from inside a skill to "continue the loop."** The loop sequences; skills do not chain. This is what keeps every skill portable to Cursor, Kiro, and Aider.
|
|
62
|
+
- ❌ **Editing `gate.py`, its config, or a test to turn G2 green.** That converts a mechanical gate into a decorative one.
|
|
63
|
+
- ❌ **Treating `PROCEED WITH CONDITIONS` as `PROCEED`.** The conditions travel with the artifact; dropping them is how conditional approvals become unconditional ones.
|
|
64
|
+
- ❌ **Running `decide` for every change.** G2.1 exists for escalated disagreement and the merge itself, not as a ceremony on top of a green gate.
|
|
65
|
+
- ❌ **Starting at `implement` because the story "is obvious."** Unshaped work is what produces a diff nobody can review against anything.
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$comment": "RFC-0028. This loop is docs/code-implement-verify.mmd promoted from a hand-maintained diagram into the machine-readable source that diagram is now generated from.",
|
|
3
|
+
"name": "build",
|
|
4
|
+
"version": "0.1.0",
|
|
5
|
+
"description": "Take an agreed requirement to merged code through a capped generate-verify-gate loop, with a mechanical gate that decides and a human who owns the merge. Use when the user wants to implement a story, fix a triaged bug, or ask whether a change is safe to merge.",
|
|
6
|
+
"entrypoint": "LOOP.md",
|
|
7
|
+
"kind": "loop",
|
|
8
|
+
"cap": 3,
|
|
9
|
+
"stages": [
|
|
10
|
+
{
|
|
11
|
+
"id": "shape",
|
|
12
|
+
"type": "generate",
|
|
13
|
+
"intent": "Turn a requirement or defect into one vertically-sliced unit of work with acceptance criteria.",
|
|
14
|
+
"skills": ["user-story-splitter", "bug-triage"]
|
|
15
|
+
},
|
|
16
|
+
{
|
|
17
|
+
"id": "implement",
|
|
18
|
+
"type": "generate",
|
|
19
|
+
"intent": "Write the code and its tests against the acceptance criteria, challenging the result each round.",
|
|
20
|
+
"skills": ["feature-implement-loop"]
|
|
21
|
+
},
|
|
22
|
+
{
|
|
23
|
+
"id": "verify",
|
|
24
|
+
"type": "verify",
|
|
25
|
+
"intent": "Judge the diff that now exists. The script decides; the panel explains.",
|
|
26
|
+
"skills": ["pre-merge-review"],
|
|
27
|
+
"gate": {
|
|
28
|
+
"id": "G2",
|
|
29
|
+
"kind": "mechanical",
|
|
30
|
+
"script": "skills/pre-merge-review/scripts/gate.py",
|
|
31
|
+
"verdicts": ["READY", "NOT READY", "BLOCKED"],
|
|
32
|
+
"revise_to": "implement"
|
|
33
|
+
}
|
|
34
|
+
},
|
|
35
|
+
{
|
|
36
|
+
"id": "decide",
|
|
37
|
+
"type": "gate",
|
|
38
|
+
"intent": "A human merges. Design disagreements surfaced at G2 are adjudicated here, not argued in the diff.",
|
|
39
|
+
"skills": ["council-review"],
|
|
40
|
+
"gate": {
|
|
41
|
+
"id": "G2.1",
|
|
42
|
+
"kind": "human",
|
|
43
|
+
"verdicts": ["PROCEED", "PROCEED WITH CONDITIONS", "REVISE", "RECONSIDER", "SPLIT", "BLOCKED"],
|
|
44
|
+
"revise_to": "shape"
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
]
|
|
48
|
+
}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: design
|
|
3
|
+
description: Take a ratified requirement to a recorded architectural decision — constraints, structure, diagrams, threats, then a panel that must agree before the decision is written down. Use when the user is designing a system, choosing an architecture, or asking how something should be built.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# design
|
|
7
|
+
|
|
8
|
+
The loop with the worst reversibility profile in the repo. A discovery mistake costs a
|
|
9
|
+
re-brief; a design mistake surfaces months later, in code nobody wants to unwind. That is why
|
|
10
|
+
its gate is a **panel** — independent positions, surfaced cruxes, recorded dissent — and not
|
|
11
|
+
a script, and why the decision is recorded only *after* the panel agrees.
|
|
12
|
+
|
|
13
|
+
## Stages
|
|
14
|
+
|
|
15
|
+
| # | Stage | Type | Skills | Gate |
|
|
16
|
+
|---|---|---|---|---|
|
|
17
|
+
| 1 | `constrain` | generate | [`nfr-spec`](../../skills/nfr-spec/SKILL.md) | — |
|
|
18
|
+
| 2 | `shape` | generate | [`design-doc`](../../skills/design-doc/SKILL.md), [`architecture-diagrams`](../../skills/architecture-diagrams/SKILL.md) | — |
|
|
19
|
+
| 3 | `threat` | verify | [`threat-model`](../../skills/threat-model/SKILL.md) | — |
|
|
20
|
+
| 4 | `ratify` | gate | [`council-review`](../../skills/council-review/SKILL.md) | **G1** review |
|
|
21
|
+
| 5 | `record` | generate | [`adr-generator`](../../skills/adr-generator/SKILL.md) | — |
|
|
22
|
+
|
|
23
|
+
## How to run this loop
|
|
24
|
+
|
|
25
|
+
1. **Constrain before shaping.** `nfr-spec` first, always. A design produced before its
|
|
26
|
+
quality targets exist gets judged on taste, and taste does not survive a review panel.
|
|
27
|
+
2. **Shape prose and picture together.** `design-doc` and `architecture-diagrams` are one
|
|
28
|
+
artifact in two renderings. A diagram that disagrees with the doc is a defect in both.
|
|
29
|
+
3. **Attack it before ratifying.** `threat-model` consumes the design directly. Running it
|
|
30
|
+
after G1 means the panel ratified something nobody had attacked.
|
|
31
|
+
4. **Ratify at G1.** `council-review` seats the standing panel, takes positions *before*
|
|
32
|
+
cross-talk, names the cruxes, and records dissent with "what would change our mind".
|
|
33
|
+
`REVISE` returns to `shape`. `SPLIT` and `RECONSIDER` leave the loop.
|
|
34
|
+
5. **Record last.** `adr-generator` writes the decision *after* it is a decision, with the
|
|
35
|
+
rejected options and the reasoning that killed them. An ADR written before G1 is a proposal
|
|
36
|
+
wearing an ADR's clothes.
|
|
37
|
+
|
|
38
|
+
## Verdicts
|
|
39
|
+
|
|
40
|
+
Defined in [`contracts/terminals.json`](../../contracts/terminals.json). `PROCEED WITH
|
|
41
|
+
CONDITIONS` is the common outcome and the most abused: the conditions are part of the
|
|
42
|
+
decision, and `record` must carry them into the ADR.
|
|
43
|
+
|
|
44
|
+
## Non-interactive runs
|
|
45
|
+
|
|
46
|
+
`council-review` can be run by an agent seating the panel itself, so G1 is satisfiable without
|
|
47
|
+
a human. `SPLIT` is not — a genuine unresolved split needs a person. Emit
|
|
48
|
+
`BLOCKED: need a decision-maker for <the crux>` and name the positions.
|
|
49
|
+
|
|
50
|
+
## When a stage's skill is not installed
|
|
51
|
+
|
|
52
|
+
Name the missing skill and skilldrop as its source, do the minimal inline version, and record
|
|
53
|
+
the stage as degraded. If `council-review` is missing, do not skip G1 — run the panel inline
|
|
54
|
+
from the design's own quality attributes and say the seating was improvised.
|
|
55
|
+
|
|
56
|
+
## Quality bar
|
|
57
|
+
|
|
58
|
+
- **Quality targets exist before structure does.** `nfr-spec` is stage 1 because a design without numbers can only be argued about.
|
|
59
|
+
- **The ADR names what was rejected and why.** A decision record with one option is a description of what happened, not a decision.
|
|
60
|
+
- **Dissent is recorded, not resolved away.** A panel that always reaches consensus is not seating real positions.
|
|
61
|
+
- **The diagram and the doc say the same thing.** They are checked against each other before G1, not after someone builds from the wrong one.
|
|
62
|
+
|
|
63
|
+
## Anti-patterns to avoid
|
|
64
|
+
|
|
65
|
+
- ❌ **Writing the ADR before G1.** It pre-commits the panel to a decision it has not made, and every reviewer can feel it.
|
|
66
|
+
- ❌ **Running `threat-model` after ratification.** The panel then ratified an unattacked design, which is the failure this ordering exists to prevent.
|
|
67
|
+
- ❌ **Treating `PROCEED WITH CONDITIONS` as `PROCEED`.** The conditions must reach the ADR; dropping them is how a conditional approval silently becomes unconditional.
|
|
68
|
+
- ❌ **Skipping `constrain` because the NFRs are "obvious".** Obvious targets are the ones nobody writes down and everybody remembers differently.
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$comment": "RFC-0028. The loop with the worst reversibility profile: a design mistake surfaces months later in code nobody wants to unwind. That is why its gate is a panel, not a script.",
|
|
3
|
+
"name": "design",
|
|
4
|
+
"version": "0.1.0",
|
|
5
|
+
"description": "Take a ratified requirement to a recorded architectural decision — constraints, structure, diagrams, threats, then a panel that must agree before the decision is written down. Use when the user is designing a system, choosing an architecture, or asking how something should be built.",
|
|
6
|
+
"entrypoint": "LOOP.md",
|
|
7
|
+
"kind": "loop",
|
|
8
|
+
"cap": 3,
|
|
9
|
+
"stages": [
|
|
10
|
+
{
|
|
11
|
+
"id": "constrain",
|
|
12
|
+
"type": "generate",
|
|
13
|
+
"intent": "Name the quality targets before the structure, so the design is judged against numbers rather than taste.",
|
|
14
|
+
"skills": ["nfr-spec"]
|
|
15
|
+
},
|
|
16
|
+
{
|
|
17
|
+
"id": "shape",
|
|
18
|
+
"type": "generate",
|
|
19
|
+
"intent": "Write the design and render it. The prose and the picture are one artifact and must not disagree.",
|
|
20
|
+
"skills": ["design-doc", "architecture-diagrams"]
|
|
21
|
+
},
|
|
22
|
+
{
|
|
23
|
+
"id": "threat",
|
|
24
|
+
"type": "verify",
|
|
25
|
+
"intent": "Attack the design that now exists, before it is ratified rather than after it is built.",
|
|
26
|
+
"skills": ["threat-model"]
|
|
27
|
+
},
|
|
28
|
+
{
|
|
29
|
+
"id": "ratify",
|
|
30
|
+
"type": "gate",
|
|
31
|
+
"intent": "A standing panel takes independent positions before cross-talk, surfaces the cruxes, and records dissent.",
|
|
32
|
+
"skills": ["council-review"],
|
|
33
|
+
"gate": {
|
|
34
|
+
"id": "G1",
|
|
35
|
+
"kind": "review",
|
|
36
|
+
"verdicts": ["PROCEED", "PROCEED WITH CONDITIONS", "REVISE", "RECONSIDER", "SPLIT", "BLOCKED"],
|
|
37
|
+
"revise_to": "shape"
|
|
38
|
+
}
|
|
39
|
+
},
|
|
40
|
+
{
|
|
41
|
+
"id": "record",
|
|
42
|
+
"type": "generate",
|
|
43
|
+
"intent": "Write the decision down with its rejected alternatives, so the next team inherits the reasoning and not just the outcome.",
|
|
44
|
+
"skills": ["adr-generator"]
|
|
45
|
+
}
|
|
46
|
+
]
|
|
47
|
+
}
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: discover
|
|
3
|
+
description: Take raw signal — interviews, journeys, a strategy question — to a requirement a human has ratified, so design starts from an agreed problem rather than an assumed one. Use when the user is deciding what to build, scoping a feature, or turning stakeholder conversations into requirements.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# discover
|
|
7
|
+
|
|
8
|
+
The first loop of the lifecycle, and the cheapest one to run twice. Everything downstream
|
|
9
|
+
inherits whatever this loop got wrong, which is why it ends at a **human** gate rather than a
|
|
10
|
+
script: no check can tell you that you solved the wrong problem well.
|
|
11
|
+
|
|
12
|
+
## Stages
|
|
13
|
+
|
|
14
|
+
| # | Stage | Type | Skills | Gate |
|
|
15
|
+
|---|---|---|---|---|
|
|
16
|
+
| 1 | `gather` | generate | [`requirements-interview`](../../skills/requirements-interview/SKILL.md), [`user-journey-map`](../../skills/user-journey-map/SKILL.md), [`strategy-analysis`](../../skills/strategy-analysis/SKILL.md) | — |
|
|
17
|
+
| 2 | `structure` | generate | [`brief-intake`](../../skills/brief-intake/SKILL.md) | — |
|
|
18
|
+
| 3 | `specify` | generate | [`prd-draft`](../../skills/prd-draft/SKILL.md) | — |
|
|
19
|
+
| 4 | `ratify` | gate | [`doc-critique`](../../skills/doc-critique/SKILL.md) | **G0** human |
|
|
20
|
+
|
|
21
|
+
## How to run this loop
|
|
22
|
+
|
|
23
|
+
1. **Gather from whichever direction the signal arrives.** A stakeholder conversation →
|
|
24
|
+
`requirements-interview`. An existing experience with known friction → `user-journey-map`.
|
|
25
|
+
An open strategic question → `strategy-analysis`. Run one; running all three on the same
|
|
26
|
+
input produces three views of the same thing and no more information.
|
|
27
|
+
2. **Structure once.** `brief-intake` tags every field `[explicit]` / `[implied]` /
|
|
28
|
+
`[inferred]` / `[missing]` with verbatim quotes. The tags are the deliverable — an
|
|
29
|
+
untagged brief hides which parts are somebody's assumption.
|
|
30
|
+
3. **Resolve the missing before specifying.** `brief-intake` ends with what the downstream
|
|
31
|
+
skill will refuse to start without. Answer those; do not let `prd-draft` invent them.
|
|
32
|
+
4. **Specify.** `prd-draft` turns the brief into numbered requirements a design can be held to.
|
|
33
|
+
5. **Ratify at G0.** Run `doc-critique` against the PRD, then put the decision to a human.
|
|
34
|
+
The critique informs; the human decides. `REVISE` returns to `structure`, not to `specify`
|
|
35
|
+
— a weak PRD almost always means a thin brief.
|
|
36
|
+
|
|
37
|
+
## Verdicts
|
|
38
|
+
|
|
39
|
+
Defined in [`contracts/terminals.json`](../../contracts/terminals.json). G0 emits `PROCEED`,
|
|
40
|
+
`PROCEED WITH CONDITIONS`, `REVISE`, `RECONSIDER`, or `BLOCKED`. `RECONSIDER` leaves the loop:
|
|
41
|
+
the problem itself is wrong, and no amount of re-briefing fixes that.
|
|
42
|
+
|
|
43
|
+
## Non-interactive runs
|
|
44
|
+
|
|
45
|
+
With no human present, G0 cannot be satisfied. Emit `BLOCKED: need ratification of <the
|
|
46
|
+
brief's central claim>` and stop. Do not self-ratify — a fabricated goal corrupts every
|
|
47
|
+
artifact the other four loops produce.
|
|
48
|
+
|
|
49
|
+
## When a stage's skill is not installed
|
|
50
|
+
|
|
51
|
+
Name the missing skill and skilldrop as its source, do the minimal inline version of that
|
|
52
|
+
stage, and record that it ran degraded. Never skip G0.
|
|
53
|
+
|
|
54
|
+
## Quality bar
|
|
55
|
+
|
|
56
|
+
- **Every field carries a provenance tag.** A brief that does not distinguish quoted from inferred cannot be ratified, only believed.
|
|
57
|
+
- **`[missing]` is resolved or stated, never filled.** Inventing the goal, the customer, or the success measure is the one failure this loop exists to prevent.
|
|
58
|
+
- **The requirements are numbered and testable.** "Fast" is not a requirement; a latency target is.
|
|
59
|
+
- **A human ratifies before design starts.** G0 is the loop's only reason to exist — an unratified brief is a draft, whatever the critique said.
|
|
60
|
+
|
|
61
|
+
## Anti-patterns to avoid
|
|
62
|
+
|
|
63
|
+
- ❌ **Running all three `gather` skills to be thorough.** Three lenses on one input is not three inputs; pick the one that matches where the signal came from.
|
|
64
|
+
- ❌ **Letting `prd-draft` fill a `[missing]` field.** That converts an open question into a fact nobody agreed to.
|
|
65
|
+
- ❌ **Treating `doc-critique`'s `SHIP IT` as ratification.** The critique judges the document; G0 judges the problem.
|
|
66
|
+
- ❌ **Returning `REVISE` to `specify`.** Re-writing the PRD from the same thin brief reproduces the same gaps in better prose.
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$comment": "RFC-0028. The first loop of the lifecycle: nothing is designed or built until a human has ratified what problem is being solved. Cheapest loop to redo and the most expensive to skip.",
|
|
3
|
+
"name": "discover",
|
|
4
|
+
"version": "0.1.0",
|
|
5
|
+
"description": "Take raw signal — interviews, journeys, a strategy question — to a requirement a human has ratified, so design starts from an agreed problem rather than an assumed one. Use when the user is deciding what to build, scoping a feature, or turning stakeholder conversations into requirements.",
|
|
6
|
+
"entrypoint": "LOOP.md",
|
|
7
|
+
"kind": "loop",
|
|
8
|
+
"cap": 3,
|
|
9
|
+
"stages": [
|
|
10
|
+
{
|
|
11
|
+
"id": "gather",
|
|
12
|
+
"type": "generate",
|
|
13
|
+
"intent": "Collect the raw signal from whichever direction it arrives: a stakeholder conversation, an existing user journey, or a strategic question.",
|
|
14
|
+
"skills": ["requirements-interview", "user-journey-map", "strategy-analysis"]
|
|
15
|
+
},
|
|
16
|
+
{
|
|
17
|
+
"id": "structure",
|
|
18
|
+
"type": "generate",
|
|
19
|
+
"intent": "Turn the mess into one brief with every field tagged explicit / implied / inferred / missing, so downstream can see what was assumed.",
|
|
20
|
+
"skills": ["brief-intake"]
|
|
21
|
+
},
|
|
22
|
+
{
|
|
23
|
+
"id": "specify",
|
|
24
|
+
"type": "generate",
|
|
25
|
+
"intent": "Turn the ratified brief into numbered requirements a design can be held to.",
|
|
26
|
+
"skills": ["prd-draft"]
|
|
27
|
+
},
|
|
28
|
+
{
|
|
29
|
+
"id": "ratify",
|
|
30
|
+
"type": "gate",
|
|
31
|
+
"intent": "A human agrees this is the problem worth solving. The critique informs that decision; it does not make it.",
|
|
32
|
+
"skills": ["doc-critique"],
|
|
33
|
+
"gate": {
|
|
34
|
+
"id": "G0",
|
|
35
|
+
"kind": "human",
|
|
36
|
+
"verdicts": ["PROCEED", "PROCEED WITH CONDITIONS", "REVISE", "RECONSIDER", "BLOCKED"],
|
|
37
|
+
"revise_to": "structure"
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
]
|
|
41
|
+
}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: operate
|
|
3
|
+
description: Take a shipped service through detection, response, and learning — instrument it, write the runbook, communicate the incident, then feed the postmortem's deltas back into the runbook. Use when the user is preparing to run a service, is in an incident, or is writing a postmortem.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# operate
|
|
7
|
+
|
|
8
|
+
The only loop whose failures are **irreversible and live**. The other four can be re-run at
|
|
9
|
+
the cost of time; this one runs while real users are affected. Its feedback edge is the point:
|
|
10
|
+
`postmortem-generator` emits runbook deltas phrased as edits, and those go straight back into
|
|
11
|
+
`document`. An incident that changes no procedure has not been learned from.
|
|
12
|
+
|
|
13
|
+
## Stages
|
|
14
|
+
|
|
15
|
+
| # | Stage | Type | Skills | Gate |
|
|
16
|
+
|---|---|---|---|---|
|
|
17
|
+
| 1 | `instrument` | generate | [`observability-plan`](../../skills/observability-plan/SKILL.md) | — |
|
|
18
|
+
| 2 | `document` | generate | [`runbook-generator`](../../skills/runbook-generator/SKILL.md) | — |
|
|
19
|
+
| 3 | `respond` | generate | [`incident-comms`](../../skills/incident-comms/SKILL.md) | — |
|
|
20
|
+
| 4 | `learn` | verify | [`postmortem-generator`](../../skills/postmortem-generator/SKILL.md) | **G3** human |
|
|
21
|
+
|
|
22
|
+
## How to run this loop
|
|
23
|
+
|
|
24
|
+
1. **Instrument first.** `observability-plan` decides what is measured and what pages a human.
|
|
25
|
+
You cannot respond to what you never detected, and you cannot write a runbook entry for an
|
|
26
|
+
alert that does not exist.
|
|
27
|
+
2. **Write the runbook per alert.** Each alert the previous stage defined maps to a
|
|
28
|
+
`runbook-generator` entry. An alert with no procedure wakes someone who then has to think.
|
|
29
|
+
3. **Respond to the audience the incident actually has.** `incident-comms` is staged —
|
|
30
|
+
detect, mitigate, resolve — and the stage determines the message. Writing a resolution
|
|
31
|
+
update during mitigation is the most common error here.
|
|
32
|
+
4. **Learn at G3.** `postmortem-generator` analyses blamelessly and ends with runbook deltas.
|
|
33
|
+
A human signs off that the incident is closed. `REVISE` returns to `document`: the deltas
|
|
34
|
+
are the loop's output, and applying them is what closes it.
|
|
35
|
+
|
|
36
|
+
Entering mid-loop is normal and expected. An incident starts at `respond`; a new service
|
|
37
|
+
starts at `instrument`. Do not replay earlier stages for their own sake.
|
|
38
|
+
|
|
39
|
+
## Verdicts
|
|
40
|
+
|
|
41
|
+
Defined in [`contracts/terminals.json`](../../contracts/terminals.json). G3 emits `PROCEED`,
|
|
42
|
+
`PROCEED WITH CONDITIONS`, `REVISE`, or `BLOCKED`. `PROCEED WITH CONDITIONS` means the
|
|
43
|
+
incident is closed but named follow-ups are outstanding — they travel with the postmortem.
|
|
44
|
+
|
|
45
|
+
## Non-interactive runs
|
|
46
|
+
|
|
47
|
+
Never fabricate incident facts — timings, impact, customer counts, root cause. When the
|
|
48
|
+
timeline is incomplete, emit `BLOCKED: need <the missing facts>` and name them. A confident
|
|
49
|
+
postmortem built on guessed impact is worse than no postmortem.
|
|
50
|
+
|
|
51
|
+
## When a stage's skill is not installed
|
|
52
|
+
|
|
53
|
+
Name the missing skill and skilldrop as its source, do the minimal inline version, and record
|
|
54
|
+
the stage as degraded. During a live incident, prefer the degraded inline version over
|
|
55
|
+
stopping to install anything.
|
|
56
|
+
|
|
57
|
+
## Quality bar
|
|
58
|
+
|
|
59
|
+
- **Every alert has a runbook entry.** An alert that pages someone with no procedure is an interruption, not a signal.
|
|
60
|
+
- **The postmortem ends in runbook deltas.** Analysis with no procedural change is a story about an outage.
|
|
61
|
+
- **Comms match the incident's actual stage.** Detect, mitigate, and resolve have different audiences and different truths.
|
|
62
|
+
- **Blameless means blameless.** Naming a person is a defect in the postmortem; naming a missing guardrail is the point.
|
|
63
|
+
|
|
64
|
+
## Anti-patterns to avoid
|
|
65
|
+
|
|
66
|
+
- ❌ **Writing the runbook before the observability plan.** Procedures for alerts that do not exist, and none for the alerts that do.
|
|
67
|
+
- ❌ **Skipping `learn` because the incident was small.** Small incidents are where the cheap runbook deltas are.
|
|
68
|
+
- ❌ **Guessing impact numbers to finish the postmortem.** State the gap; a postmortem's value is entirely in its accuracy.
|
|
69
|
+
- ❌ **Replaying `instrument` during a live incident.** Enter at `respond`; the loop is not a checklist to complete in order.
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$comment": "RFC-0028. The only loop whose failures are irreversible and live. Its feedback edge is real and already documented in the repo: postmortem-generator emits runbook deltas phrased as edits for runbook-generator.",
|
|
3
|
+
"name": "operate",
|
|
4
|
+
"version": "0.1.0",
|
|
5
|
+
"description": "Take a shipped service through detection, response, and learning — instrument it, write the runbook, communicate the incident, then feed the postmortem's deltas back into the runbook. Use when the user is preparing to run a service, is in an incident, or is writing a postmortem.",
|
|
6
|
+
"entrypoint": "LOOP.md",
|
|
7
|
+
"kind": "loop",
|
|
8
|
+
"cap": 3,
|
|
9
|
+
"stages": [
|
|
10
|
+
{
|
|
11
|
+
"id": "instrument",
|
|
12
|
+
"type": "generate",
|
|
13
|
+
"intent": "Decide what is measured and what pages a human. You cannot respond to what you never detected.",
|
|
14
|
+
"skills": ["observability-plan"]
|
|
15
|
+
},
|
|
16
|
+
{
|
|
17
|
+
"id": "document",
|
|
18
|
+
"type": "generate",
|
|
19
|
+
"intent": "Write the procedure the on-call follows at 3am, per alert the previous stage defined.",
|
|
20
|
+
"skills": ["runbook-generator"]
|
|
21
|
+
},
|
|
22
|
+
{
|
|
23
|
+
"id": "respond",
|
|
24
|
+
"type": "generate",
|
|
25
|
+
"intent": "Communicate during the incident, to the audience that needs it, at the stage the incident is actually in.",
|
|
26
|
+
"skills": ["incident-comms"]
|
|
27
|
+
},
|
|
28
|
+
{
|
|
29
|
+
"id": "learn",
|
|
30
|
+
"type": "verify",
|
|
31
|
+
"intent": "Analyse blamelessly and emit runbook deltas. An incident that changes no procedure has not been learned from.",
|
|
32
|
+
"skills": ["postmortem-generator"],
|
|
33
|
+
"gate": {
|
|
34
|
+
"id": "G3",
|
|
35
|
+
"kind": "human",
|
|
36
|
+
"verdicts": ["PROCEED", "PROCEED WITH CONDITIONS", "REVISE", "BLOCKED"],
|
|
37
|
+
"revise_to": "document"
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
]
|
|
41
|
+
}
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: ship-a-draft
|
|
3
|
+
description: Take raw mess to a stakeholder-ready artifact by wrapping any skilldrop generator in the two passes either side of it — structured intake before, critique and machine-residue scrub after. Use when the user has notes, a transcript, or a ticket and wants a finished document rather than a first draft.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# ship-a-draft
|
|
7
|
+
|
|
8
|
+
A **wrapper**, not a lifecycle loop. Its centre stage is whichever generator the user actually
|
|
9
|
+
needs — an ADR, a design doc, a runbook, a deck, an exec summary. The wrapper contributes the
|
|
10
|
+
two passes every generator otherwise leaves to chance: collect the input properly before, and
|
|
11
|
+
check the argument and the surface after.
|
|
12
|
+
|
|
13
|
+
## Stages
|
|
14
|
+
|
|
15
|
+
| # | Stage | Type | Skills | Gate |
|
|
16
|
+
|---|---|---|---|---|
|
|
17
|
+
| 1 | `intake` | generate | [`brief-intake`](../../skills/brief-intake/SKILL.md) | — |
|
|
18
|
+
| 2 | `draft` | generate | any generator (`*`) | — |
|
|
19
|
+
| 3 | `critique` | verify | [`doc-critique`](../../skills/doc-critique/SKILL.md) | **G4** review |
|
|
20
|
+
| 4 | `polish` | verify | [`output-hygiene`](../../skills/output-hygiene/SKILL.md) | — |
|
|
21
|
+
|
|
22
|
+
## How to run this wrapper
|
|
23
|
+
|
|
24
|
+
1. **Pick the generator first.** The brief is shaped *for a target*, so `draft` is chosen
|
|
25
|
+
before `intake` runs, not after. `brief-intake`'s own routing table maps trigger phrases to
|
|
26
|
+
targets; use it.
|
|
27
|
+
2. **Collect once.** Run `brief-intake`. Every field is tagged `[explicit]` / `[implied]` /
|
|
28
|
+
`[inferred]` / `[missing]`, and its "Missing for downstream" section predicts what the
|
|
29
|
+
chosen generator will refuse to start without. Resolve those before drafting.
|
|
30
|
+
3. **Draft.** Run the chosen generator on the brief. It is a normal skilldrop skill with its
|
|
31
|
+
own quality bar — this wrapper does not override it.
|
|
32
|
+
4. **Critique at G4.** Run `doc-critique`, which dispatches to the same rubric the generator
|
|
33
|
+
was held to. `MAJOR REWRITE` returns to `intake` (not to `draft` — a rewrite usually means
|
|
34
|
+
the input was wrong, not the prose). `WRONG ARTIFACT` leaves the wrapper entirely.
|
|
35
|
+
5. **Polish last.** Run `output-hygiene` only once the argument is settled. It is a surface
|
|
36
|
+
pass; running it on a draft that is about to be rewritten wastes it.
|
|
37
|
+
|
|
38
|
+
## Verdicts
|
|
39
|
+
|
|
40
|
+
Defined in [`contracts/terminals.json`](../../contracts/terminals.json). G4 emits the critique
|
|
41
|
+
vocabulary. `SHIP WITH CHANGES` carries its changes forward to `polish`; it does not mean the
|
|
42
|
+
changes are optional.
|
|
43
|
+
|
|
44
|
+
## When a stage's skill is not installed
|
|
45
|
+
|
|
46
|
+
Name the missing skill and skilldrop as its source, do the minimal inline version of that
|
|
47
|
+
stage, and say the stage ran degraded. Do not skip G4 — an unreviewed artifact is the failure
|
|
48
|
+
mode this wrapper exists to prevent.
|
|
49
|
+
|
|
50
|
+
## Quality bar
|
|
51
|
+
|
|
52
|
+
- **The generator is chosen before intake runs.** A brief collected for no particular target is a summary, and downstream will reject it for missing fields.
|
|
53
|
+
- **`polish` runs after the argument is settled, never before.** Scrubbing prose that is about to be rewritten is wasted work and hides the rewrite.
|
|
54
|
+
- **A `[missing]` tag is resolved or stated, never silently filled.** Fabricating a goal, an owner, or a decision corrupts every downstream artifact.
|
|
55
|
+
- **Every run ends by naming what was not touched.** `output-hygiene`'s "Not touched" section is part of the deliverable, not an appendix.
|
|
56
|
+
|
|
57
|
+
## Anti-patterns to avoid
|
|
58
|
+
|
|
59
|
+
- ❌ **Running `polish` as the whole review.** Clean prose with a broken argument still fails; that is what G4 is for.
|
|
60
|
+
- ❌ **Skipping `intake` because the input "is already structured."** A Slack thread that looks organized is still untagged — nobody downstream can tell what was inferred.
|
|
61
|
+
- ❌ **Looping `critique` → `draft` instead of `critique` → `intake`.** Re-drafting from the same incomplete brief reproduces the same gaps with new words.
|
|
62
|
+
- ❌ **Treating `WRONG ARTIFACT` as a severe `MAJOR REWRITE`.** It is a redirect: the user wanted a different document, and revising this one cannot get there.
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$comment": "RFC-0028. This wrapper is docs/knowledge-work-pipeline.mmd promoted from a hand-maintained diagram into the machine-readable source that diagram is now generated from. It is a wrapper, not a loop: the generator at its centre is chosen at run time from whichever artifact the user actually wants.",
|
|
3
|
+
"name": "ship-a-draft",
|
|
4
|
+
"version": "0.1.0",
|
|
5
|
+
"description": "Take raw mess to a stakeholder-ready artifact by wrapping any skilldrop generator in the two passes either side of it — structured intake before, critique and machine-residue scrub after. Use when the user has notes, a transcript, or a ticket and wants a finished document rather than a first draft.",
|
|
6
|
+
"entrypoint": "LOOP.md",
|
|
7
|
+
"kind": "wrapper",
|
|
8
|
+
"cap": 3,
|
|
9
|
+
"stages": [
|
|
10
|
+
{
|
|
11
|
+
"id": "intake",
|
|
12
|
+
"type": "generate",
|
|
13
|
+
"intent": "Collect the raw input once, into the shape the chosen generator expects, tagging every field explicit / implied / inferred / missing.",
|
|
14
|
+
"skills": ["brief-intake"]
|
|
15
|
+
},
|
|
16
|
+
{
|
|
17
|
+
"id": "draft",
|
|
18
|
+
"type": "generate",
|
|
19
|
+
"intent": "Run the generator the brief was shaped for. Any artifact skill is legal here — that choice is the wrapper's whole point.",
|
|
20
|
+
"skills": ["*"]
|
|
21
|
+
},
|
|
22
|
+
{
|
|
23
|
+
"id": "critique",
|
|
24
|
+
"type": "verify",
|
|
25
|
+
"intent": "Review the draft against the same rubric the generator was held to.",
|
|
26
|
+
"skills": ["doc-critique"],
|
|
27
|
+
"gate": {
|
|
28
|
+
"id": "G4",
|
|
29
|
+
"kind": "review",
|
|
30
|
+
"verdicts": ["SHIP IT", "SHIP WITH CHANGES", "MAJOR REWRITE", "WRONG ARTIFACT", "BLOCKED"],
|
|
31
|
+
"revise_to": "intake"
|
|
32
|
+
}
|
|
33
|
+
},
|
|
34
|
+
{
|
|
35
|
+
"id": "polish",
|
|
36
|
+
"type": "verify",
|
|
37
|
+
"intent": "Strip what the machine left behind before the artifact leaves the building. Surface pass only — never a substitute for the critique above.",
|
|
38
|
+
"skills": ["output-hygiene"]
|
|
39
|
+
}
|
|
40
|
+
]
|
|
41
|
+
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "skilldrop-cli",
|
|
3
|
-
"version": "0.11.
|
|
4
|
-
"description": "Portable AI-agent skills for the deliverables knowledge workers ship
|
|
3
|
+
"version": "0.11.7",
|
|
4
|
+
"description": "Portable AI-agent skills for the deliverables knowledge workers ship \u2014 diagrams, ADRs, PRDs, runbooks, decks, reviews \u2014 installable into Claude Code, Cursor, Kiro, and any IDE that takes custom instructions. One command per skill or per role-based pack.",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "Sanjay Ananthanarayan",
|
|
7
7
|
"url": "https://github.com/sananthanarayan"
|
|
@@ -13,6 +13,8 @@
|
|
|
13
13
|
"bin/",
|
|
14
14
|
"skills/",
|
|
15
15
|
"agents/",
|
|
16
|
+
"loops/",
|
|
17
|
+
"contracts/",
|
|
16
18
|
"packs.json",
|
|
17
19
|
"model-routing.json"
|
|
18
20
|
],
|
|
@@ -14,6 +14,9 @@
|
|
|
14
14
|
"related": [
|
|
15
15
|
"figma-diagrams"
|
|
16
16
|
],
|
|
17
|
+
"handoff": [
|
|
18
|
+
{ "to": "figma-diagrams", "when": "the diagram needs to live where designers work", "purpose": "Push the rendered diagram into Figma.", "fallback": "If figma-diagrams is absent, leave the Mermaid source and say it needs manual import; never fabricate a Figma URL." }
|
|
19
|
+
],
|
|
17
20
|
"tags": [
|
|
18
21
|
"diagrams",
|
|
19
22
|
"mermaid",
|
|
@@ -6,6 +6,9 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["feature-implement-loop", "postmortem-generator", "user-story-splitter"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "feature-implement-loop", "when": "the defect is reproduced and scoped", "purpose": "Fix the triaged defect through the same capped loop a story gets.", "fallback": "If feature-implement-loop is absent, fix inline with a regression test that fails before the fix." }
|
|
11
|
+
],
|
|
9
12
|
"tags": ["bug-triage", "bug-report", "ticket", "qa", "repro", "severity"],
|
|
10
13
|
"model": { "tier": "standard", "rationale": "Extraction plus judgment calls (severity vs priority, hypothesis ranking) — same shape as brief-intake: above light, below heavy." }
|
|
11
14
|
}
|
|
@@ -6,6 +6,9 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["architecture-diagrams"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "architecture-diagrams", "when": "the design is written and needs rendering", "purpose": "Render the prose as a diagram that must not disagree with it.", "fallback": "If architecture-diagrams is absent, emit Mermaid inline and check every node against a claim in the doc." }
|
|
11
|
+
],
|
|
9
12
|
"tags": ["design-doc", "documentation", "engineering", "review"],
|
|
10
13
|
"model": { "tier": "standard", "rationale": "Synthesizes a design doc from a brief. Escalates to opus on big or genuinely contested inputs." }
|
|
11
14
|
}
|
|
@@ -6,6 +6,9 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["design-doc", "devils-advocate", "doc-critique", "pre-merge-review"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "pre-merge-review", "when": "the code exists and the question is whether it can merge", "purpose": "Judge the diff that now exists against a mechanical gate.", "fallback": "If pre-merge-review is absent, run the repo's own lint and tests and honour the exit code; do not self-certify." }
|
|
11
|
+
],
|
|
9
12
|
"tags": ["dev-workflow", "implementation", "tdd", "acceptance-criteria", "adversarial", "self-correcting", "code-generation"],
|
|
10
13
|
"model": { "tier": "standard", "rationale": "Code + test generation against acceptance criteria. The adversarial pass delegates to devils-advocate (heavy) where available; the loop itself is generation." }
|
|
11
14
|
}
|
|
@@ -6,6 +6,9 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["postmortem-generator", "runbook-generator"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "postmortem-generator", "when": "the incident is resolved", "purpose": "Analyse blamelessly and emit runbook deltas.", "fallback": "If postmortem-generator is absent, write the timeline, the contributing factors, and the procedural changes inline." }
|
|
11
|
+
],
|
|
9
12
|
"tags": ["incident", "communication", "status-page", "outage", "stakeholder", "sre"],
|
|
10
13
|
"model": { "tier": "standard", "rationale": "Audience-segmented message generation under a strict don't-retract discipline. Same shape as exec-summary/audience-profile — translation and altitude, not adversarial reasoning." }
|
|
11
14
|
}
|
|
@@ -6,6 +6,11 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["capacity-cost-model", "design-doc", "prd-draft", "test-plan-generator", "threat-model"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "design-doc", "when": "the quality targets are set", "purpose": "Design against the stated numbers rather than against taste.", "fallback": "If design-doc is absent, restate each target beside the design choice that serves it." },
|
|
11
|
+
{ "to": "threat-model", "when": "the design has a trust boundary worth attacking", "purpose": "Attack the design before it is ratified.", "fallback": "If threat-model is absent, list the trust boundaries and one abuse case per boundary inline." },
|
|
12
|
+
{ "to": "test-plan-generator", "when": "the targets need verifying, not just stating", "purpose": "Turn each quality target into a coverage entry.", "fallback": "If test-plan-generator is absent, name the test that would falsify each target." }
|
|
13
|
+
],
|
|
9
14
|
"tags": ["nfr", "requirements", "slo", "performance", "availability", "quality-attributes"],
|
|
10
15
|
"model": { "tier": "standard", "rationale": "Rubric-driven sweep with archetype defaults; the judgment is calibrating targets to business reality. Bounded by the catalog; escalate via ambiguous-input on contested SLOs." }
|
|
11
16
|
}
|
|
@@ -6,6 +6,10 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["capacity-cost-model", "incident-comms", "nfr-spec", "postmortem-generator", "runbook-generator", "success-metrics"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "runbook-generator", "when": "the alerts are defined and each needs a procedure", "purpose": "Write the procedure the on-call follows per alert.", "fallback": "If runbook-generator is absent, write one numbered procedure per alert inline." },
|
|
11
|
+
{ "to": "incident-comms", "when": "detection fired and an audience needs telling", "purpose": "Communicate at the stage the incident is actually in.", "fallback": "If incident-comms is absent, state the stage, the impact, and the next update time inline." }
|
|
12
|
+
],
|
|
9
13
|
"tags": ["observability", "slo", "sli", "alerting", "monitoring", "sre"],
|
|
10
14
|
"model": { "tier": "standard", "rationale": "Methodology synthesis against fixed SRE practices (golden signals, burn-rate alerting, pillar split). SLO calibration needs judgment but is bounded; escalate via ambiguous-input on contested reliability targets." }
|
|
11
15
|
}
|
|
@@ -15,6 +15,9 @@
|
|
|
15
15
|
"doc-critique",
|
|
16
16
|
"ai-usage-policy"
|
|
17
17
|
],
|
|
18
|
+
"handoff": [
|
|
19
|
+
{ "to": "doc-critique", "when": "the surface is clean and the draft is still weak", "purpose": "The fault is the argument, not the residue.", "fallback": "If doc-critique is absent, name the weakest claim and what evidence it needs." }
|
|
20
|
+
],
|
|
18
21
|
"tags": [
|
|
19
22
|
"hygiene",
|
|
20
23
|
"cleanup",
|
|
@@ -6,6 +6,9 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["runbook-generator"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "runbook-generator", "when": "the postmortem produced runbook deltas", "purpose": "Apply the deltas as edits to the existing runbook.", "fallback": "If runbook-generator is absent, phrase each delta as a concrete before/after edit so a human can apply it." }
|
|
11
|
+
],
|
|
9
12
|
"tags": ["postmortem", "incident", "rca", "sre", "blameless", "outage"],
|
|
10
13
|
"model": { "tier": "standard", "rationale": "Synthesizes a structured doc from incident notes. Contributing-factor chains need judgment but are bounded; escalate via large-input on huge scrollbacks." }
|
|
11
14
|
}
|
|
@@ -6,6 +6,11 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["brief-intake", "bug-triage", "business-case", "design-doc", "nfr-spec", "success-metrics", "user-story-splitter"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "nfr-spec", "when": "the functional requirements are agreed", "purpose": "Set the quality targets the design will be judged against.", "fallback": "If nfr-spec is absent, state latency, availability and scale targets inline as numbers, not adjectives." },
|
|
11
|
+
{ "to": "user-story-splitter", "when": "the requirements are ready to become units of work", "purpose": "Split into vertically-sliced stories with acceptance criteria.", "fallback": "If user-story-splitter is absent, slice inline and give each story acceptance criteria a test can assert." },
|
|
12
|
+
{ "to": "design-doc", "when": "the what is agreed and the how is open", "purpose": "Design the system that satisfies these requirements.", "fallback": "If design-doc is absent, write the approach, the alternatives, and the trade-offs inline." }
|
|
13
|
+
],
|
|
9
14
|
"tags": ["prd", "requirements", "product", "discovery", "moscow", "non-goals"],
|
|
10
15
|
"model": { "tier": "standard", "rationale": "Synthesizes a structured requirements doc from a brief. The solution-language discipline needs care; bounded by the template. Escalate via ambiguous-input on contested scope." }
|
|
11
16
|
}
|
|
@@ -6,6 +6,9 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["feature-implement-loop", "devils-advocate", "council-review", "doc-critique"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "council-review", "when": "the blocker is a design disagreement, not a defect", "purpose": "Adjudicate the disagreement outside the diff.", "fallback": "If council-review is absent, state each position and its strongest counter inline, and name the crux the decision turns on." }
|
|
11
|
+
],
|
|
9
12
|
"tags": ["dev-workflow", "code-review", "pre-merge", "quality-gate", "subagents", "production-readiness"],
|
|
10
13
|
"model": { "tier": "standard", "rationale": "Coordination: runs a deterministic gate script, dispatches the (heavy) reviewer subagents, and renders a rule-based go/no-go. The adversarial reasoning is delegated to the panel, so the skill itself is orchestration, not deep judgment." }
|
|
11
14
|
}
|
|
@@ -6,6 +6,9 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["brief-intake", "decision-log", "prd-draft"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "brief-intake", "when": "the interview is done and the notes are raw", "purpose": "Collect the transcript into a tagged brief before any generator sees it.", "fallback": "If brief-intake is absent, tag each captured field [explicit]/[implied]/[inferred]/[missing] inline and say which downstream skill the brief is shaped for." }
|
|
11
|
+
],
|
|
9
12
|
"tags": ["discovery", "interviews", "requirements", "elicitation", "stakeholders", "user-research"],
|
|
10
13
|
"model": { "tier": "standard", "rationale": "Question banks are rubric-shaped, but ranking by design impact and deriving falsification conditions for the specific feature is synthesis — above light." }
|
|
11
14
|
}
|
|
@@ -6,6 +6,10 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["business-case", "okr-cascade", "prfaq", "tech-comparison-matrix"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "tech-comparison-matrix", "when": "the options are named and need comparing on stated criteria", "purpose": "Score the named options against weighted criteria.", "fallback": "If tech-comparison-matrix is absent, build a plain criteria-by-option table inline and state the weights." },
|
|
11
|
+
{ "to": "business-case", "when": "the direction is chosen and needs costing before approval", "purpose": "Cost the chosen option against a do-nothing baseline.", "fallback": "If business-case is absent, state option 0 and the three cost layers (build, run, opportunity) inline." }
|
|
12
|
+
],
|
|
9
13
|
"tags": ["strategy", "swot", "tows", "five-forces", "pestle", "competitive-analysis", "market-analysis"],
|
|
10
14
|
"model": { "tier": "heavy", "rationale": "Framework selection plus evidenced multi-factor judgment ending in a ranked, committal verdict. Cheaper models fill cells with generic filler, skip the TOWS crossings, and refuse to take a side. Never downgrade." }
|
|
11
15
|
}
|
|
@@ -6,6 +6,10 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["architecture-diagrams", "prd-draft", "reverse-architecture", "success-metrics", "user-story-splitter"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "prd-draft", "when": "a friction point on the journey is worth fixing", "purpose": "Turn the named friction into numbered requirements.", "fallback": "If prd-draft is absent, write the requirements inline as numbered, testable statements and note that prd-draft in skilldrop would structure them." },
|
|
11
|
+
{ "to": "success-metrics", "when": "the fix needs a measure before it is built", "purpose": "Design the measurement for the journey step being changed.", "fallback": "If success-metrics is absent, state one baseline and one target per fixed step inline." }
|
|
12
|
+
],
|
|
9
13
|
"tags": ["journey-map", "customer-experience", "ux", "touchpoints", "mermaid", "personas"],
|
|
10
14
|
"model": { "tier": "standard", "rationale": "Structured synthesis into a fixed four-row stage model plus bounded ranking judgment. Escalate via ambiguous-input when the persona or outcome is contested or research inputs conflict." }
|
|
11
15
|
}
|
|
@@ -6,6 +6,9 @@
|
|
|
6
6
|
"deps": { "npm": [], "pip": [] },
|
|
7
7
|
"env": { "required": [], "optional": [] },
|
|
8
8
|
"related": ["feature-implement-loop"],
|
|
9
|
+
"handoff": [
|
|
10
|
+
{ "to": "feature-implement-loop", "when": "a story has acceptance criteria a test can assert", "purpose": "Implement the slice through a capped generate-verify loop.", "fallback": "If feature-implement-loop is absent, implement inline but still challenge the result and cap the rounds at three." }
|
|
11
|
+
],
|
|
9
12
|
"tags": ["user-stories", "agile", "backlog", "acceptance-criteria", "planning", "sprint"],
|
|
10
13
|
"model": { "tier": "standard", "rationale": "Decomposes an epic into INVEST slices with testable ACs. Structured synthesis; escalation rules cover large or contradictory PRDs." }
|
|
11
14
|
}
|