wdi-method 0.6.30 → 0.6.32

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.
Files changed (43) hide show
  1. package/CHANGELOG.md +129 -0
  2. package/NOTICE +7 -2
  3. package/README.md +16 -11
  4. package/bin/wdi-method.js +396 -87
  5. package/kit/.constitution/method/document/architecture-guide.md +217 -209
  6. package/kit/.constitution/method/document/bmad-skill-register.md +107 -104
  7. package/kit/.constitution/method/document/corpus-guide.md +522 -517
  8. package/kit/.constitution/method/document/decision-guide.md +236 -216
  9. package/kit/.constitution/method/document/delivery-flow-guide.md +20 -0
  10. package/kit/.constitution/method/document/prd-guide.md +245 -245
  11. package/kit/.constitution/method/document/templates/design-system.md +96 -66
  12. package/kit/.constitution/method/document/templates/experience.md +62 -0
  13. package/kit/.constitution/method/document/templates/structure-codebase.md +131 -129
  14. package/kit/.constitution/method/document/templates/ux.md +78 -76
  15. package/kit/.constitution/method/document/ux-guide.md +161 -115
  16. package/kit/.constitution/method/method-glossary.md +3 -0
  17. package/kit/.constitution/method/scripts/validate.py +3375 -3200
  18. package/kit/.constitution/method/structure-guide.md +204 -202
  19. package/kit/.constitution/method/why/README.md +1 -1
  20. package/kit/.constitution/method/why/artifact-map.md +158 -157
  21. package/kit/.constitution/method/why/portability.md +19 -2
  22. package/kit/skills/wdi-autopilot/SKILL.md +32 -19
  23. package/kit/skills/wdi-blueprint/SKILL.md +271 -264
  24. package/kit/skills/wdi-build/SKILL.md +28 -19
  25. package/kit/skills/wdi-component/SKILL.md +179 -174
  26. package/kit/skills/wdi-daily-autopilot/SKILL.md +24 -13
  27. package/kit/skills/wdi-daily-what-to-build/SKILL.md +9 -6
  28. package/kit/skills/wdi-daily-what-to-test/SKILL.md +2 -0
  29. package/kit/skills/wdi-decision/SKILL.md +206 -203
  30. package/kit/skills/wdi-explain-to-me/SKILL.md +2 -0
  31. package/kit/skills/wdi-help/SKILL.md +130 -125
  32. package/kit/skills/wdi-init/SKILL.md +10 -5
  33. package/kit/skills/wdi-problem/SKILL.md +114 -108
  34. package/kit/skills/wdi-product/SKILL.md +167 -162
  35. package/kit/skills/wdi-prune-or-archive/SKILL.md +2 -0
  36. package/kit/skills/wdi-reconcile/SKILL.md +170 -169
  37. package/kit/skills/wdi-upgrade/SKILL.md +234 -215
  38. package/kit/skills/wdi-ux/SKILL.md +187 -169
  39. package/kit-overlay/AGENTS.md +15 -2
  40. package/kit-overlay/portability.md +19 -2
  41. package/lib/platforms.mjs +420 -248
  42. package/package.json +1 -1
  43. package/scaffold/.control/registry/index.yaml +2 -1
@@ -1,245 +1,245 @@
1
- ---
2
- status: Accepted
3
- ---
4
-
5
- # PRD Guide
6
-
7
- **Loaded when:** writing, updating, or validating a PRD
8
-
9
- A PRD states what the product promises a user for one functional area. It does not describe how the
10
- system behaves — that is `SRS-<pc>.md` — and it does not describe how it is built — that is
11
- `SDD-<pc>.md`. When a sentence here could only be checked by reading code, it is in the wrong file.
12
-
13
- ## Home and life cycle
14
-
15
- - One PRD per **initiative / functional area**. It MUST live at `.what/_prd/<initiative>/prd.md`,
16
- with `addendum.md` beside it. Set through `prd_output_path` and `run_folder_pattern` in
17
- `_bmad/custom/bmad-prd.toml`.
18
- - A PRD is a **living document**. It MUST NOT be frozen, archived, or superseded when a release
19
- ships.
20
- - Memlog MUST go to `.control/memlog/prd-<slug>.md` via `--path`, with the slug matching the folder.
21
- `--workspace` MUST NOT be used; it would leave a `.memlog.md` inside `.what/`.
22
- - `run_folder_pattern` ships as `ISI-slug-inisiatif`, which is deliberately unusable. A PRD found in
23
- a folder by that name means the override was never pointed at a real initiative slug; `wdi-product`
24
- check 1 catches it, and it MUST be moved before G2.
25
-
26
- ## Update, or a new PRD
27
-
28
- This is the decision the guide exists for, and the default is **Update**.
29
-
30
- | Situation | What to do |
31
- |---|---|
32
- | Behaviour of an existing promise changes | Update |
33
- | A promise turns out to be wrong and must be withdrawn | Update — and the withdrawal MUST be visible in Revision History, not silently deleted. This is the one mandated history line in the method, and it survives because it is **business** history read by someone outside the room, not a record that a document changed |
34
- | A new feature that a reader would expect to find in this PRD | Update |
35
- | The next release extends what this PRD already promises | Update. A release is never a reason on its own |
36
- | A functional area a reader would not think to look for here | New PRD |
37
-
38
- The test is the reader, not the calendar: **would someone looking for this promise open this
39
- document?** If yes, it belongs here however large the change. A PRD MUST NOT be split because it
40
- grew long — length is what `addendum.md` and feature grouping are for. It is split only when the two
41
- areas have different readers, different stakeholders, or no shared vocabulary.
42
-
43
- When a split is genuinely right, the existing PRD MUST keep its own IDs. `FR-N` never moves between
44
- PRDs; the sequence is global to the product.
45
-
46
- ## One home, and what `.what/<pc>/` may take from it
47
-
48
- A PRD is the **reference** the blueprint and each component work from, not a quarry. `.what/<pc>/` is distilled from it — the
49
- same promise restated as behaviour, at the altitude a builder needs — and the PRD stays the one place
50
- that promise lives.
51
-
52
- - One PRD per initiative. Its content MUST NOT be split into pieces spread across `.what/<pc>/`, and
53
- a fragment MUST NOT be moved out of it. A promise with two homes drifts, and the copy people read
54
- is whichever they open first.
55
- - `.what/<pc>/` MUST cite the `FR`/`NFR` it realises by ID rather than restating its text. A use case
56
- saying what the system does is derivation; a use case reproducing the PRD's paragraph is a second
57
- copy.
58
- - One initiative MAY span several Product Components, and one component MAY serve several PRDs. That
59
- is why neither can absorb the other — `corpus-guide.md` owns the two-axis rule.
60
- - When the distillation proves a promise cannot be behaved into, the PRD changes first, through
61
- `wdi-product` intent `update`. The SRS MUST NOT narrow it quietly.
62
-
63
- ## Revision History
64
-
65
- - Every `update` run MUST add **exactly one row**, appended at the bottom — one row per **pass**, never
66
- one per correction.
67
- - Rows MUST be written for someone who was not in the room — a client, a sponsor, an auditor. State
68
- what the promise now is, not which section was edited. "Payment retries now cap at three attempts,
69
- down from unlimited, because support could not explain the charges" is a row. "Updated §4.2" is
70
- not.
71
- - The `Releases affected` column names the releases whose promise changed. It MUST match
72
- `target_release` on the affected `CAP` entries.
73
- - A row MUST NOT be edited after the run that wrote it. A correction is a new row.
74
-
75
- The boundary against the memlog matters and MUST NOT be collapsed:
76
-
77
- | | Memlog | Revision History |
78
- |---|---|---|
79
- | Records | Every decision, change, override, assumption inside a run | What changed for the reader |
80
- | Written | Continuously, by `memlog.py`, append-only | Once per run, by hand |
81
- | Read by | The next run, and audits | Anyone opening the PRD |
82
- | Lives in | `.control/memlog/` | The PRD itself |
83
-
84
- Neither MUST be written in place of the other. A PRD whose only change record is the memlog is
85
- unreadable to the people it was written for.
86
-
87
- ## Release lives in the registry
88
-
89
- Release MUST NOT be expressed through this document's folder name, title, or frontmatter. It is
90
- carried by:
91
-
92
- | Field | Answers |
93
- |---|---|
94
- | `CAP.target_release` | Which release this capability is planned for. **The only place a promise's release is written** |
95
- | `specs.yaml` `release` | Which release a spec of work belongs to — the execution side |
96
-
97
- An `FR` MUST NOT carry a release of its own. It inherits one from its `CAP`, the same way it reaches
98
- its `BG`: each child names only its parent. A capability whose requirements genuinely land in
99
- different releases is two capabilities, and MUST be split rather than annotated.
100
-
101
- Naming a release in prose as context MAY happen; the registry is what binds.
102
-
103
- ## Numbering
104
-
105
- `BG-N` is allocated from `.control/registry/goals.yaml`; `CAP-N`, `FR-N`, `NFR-N`, and `UJ-N` from this initiative's own `.control/registry/requirements-<slug>.yaml` — one file, one writer, one gate
106
- and MUST NOT restart at 1. The chain runs `BG → CAP → FR/NFR → UC → DEC → Ticket → Test`, and each
107
- child names only its parent:
108
-
109
- - Each feature in §3 MUST declare its `CAP-N` and the `BG-N` it serves.
110
- - Each `FR` MUST declare its `capability`. Its goal is reached *through* the capability and MUST NOT
111
- be restated on the FR.
112
- - Each `NFR` attaches to `BG` directly — it does not pass through `CAP`.
113
-
114
- `chain-links` checks both links. An FR with no capability is a promise nobody asked for.
115
-
116
- ## `FR`/`NFR` text lives in the registry, not in this document
117
-
118
- The PRD cites `FR-N`/`NFR-N` under each feature's **Realizes:** line. It MUST NOT also write the
119
- statement, the proof of done, or the enforcer in prose — those fields live on the id's own row in
120
- `requirements-<slug>.yaml`, and landing them there is part of `wdi-product` producing this PRD, not a
121
- follow-up. A promise written in both places is one fact with two homes, and the copy a reader trusts
122
- is whichever they open first.
123
-
124
- Every `FR` MUST carry **exactly one** proof of done: a sentence a Product Owner can check without opening
125
- the code. It is what lets one `FR` become one testable unit of work, and it is why a spec is ideally one
126
- `FR`.
127
-
128
- **The double proof of done stays repealed.** A business sentence *and* a technical restatement naming
129
- status codes, limits, and payloads meant writing the same acceptance twice, in two vocabularies that
130
- then drifted. The technical form is represented by the **test name** recorded in `specs.yaml`, where it
131
- is checked mechanically (`ticket-has-test`) instead of read.
132
-
133
- A technical detail that genuinely has to be written down belongs in `addendum.md` or in the SDD, not in
134
- a second proof of done — and not in this document's prose either.
135
-
136
- ## Wording versus promise — two different journeys
137
-
138
- The distinction this guide exists to protect, and the one that produced three corrections that ended
139
- "reported but not fixed":
140
-
141
- | What changes | Route |
142
- |---|---|
143
- | The **wording** of an `FR` — a wrong cross-reference, a retired term, a word no longer consistent with an `applied` decision, while **the promise is the same** | The skill already at work fixes it directly. Recorded in the memlog, and **one** Revision History row per pass, not per correction |
144
- | The **promise** of an `FR` — scope changes, the proof of done changes, an `FR` is retired or born | `wdi-product` intent `update`, and the change-control matrix in `delivery-flow-guide.md` says which gates reopen |
145
-
146
- The guard against abuse is already in the Revision History rule: a row is written for someone who was not in
147
- the room. A wording correction produces no row a client would find interesting, and that is precisely the
148
- evidence it was not a change of promise.
149
-
150
- Treating a wording fix as a promise change is not caution — it is what made three corrections queue behind a
151
- gate and then get dropped.
152
-
153
- ## `owns:` — one entity, one writer
154
-
155
- A domain entity MUST have exactly one owner authorised to write it. Usually that is a Product Component,
156
- declared as `owns:` on its row in `components.yaml`; an `FR` from another PRD that needs to change the entity
157
- MUST point at the owner's `FR` through `defers_to`, rather than promising to write it itself. `entity-one-writer` checks this.
158
-
159
- **A few entities belong to no Product Component at all** — a product-wide setting, the trace of one shared
160
- outbound channel. Those are owned by `_platform` through `platform_owns`, and the test for when that is
161
- legitimate lives in `corpus-guide.md`. `_platform` has no `FR`, so an `FR` writing a platform-owned entity is
162
- **not** asked for a `defers_to`; what binds instead is the shape documented in `cross-cutting.md`. Reaching
163
- for `_platform` because the owner is hard to decide is the one use of it that the test refuses.
164
-
165
- This is not theoretical: two PRDs have already collided semantically over one shared numbering series. Two
166
- `FR` claiming write authority over the same entity, with neither pointing at the other, is a defect at the
167
- moment it is written — not at the moment the code disagrees.
168
-
169
- ## Sections that stop being optional
170
-
171
- BMad's Adapt-In Menu is conditional by design. Two clusters MUST always be present here, and are in
172
- the Essential Spine rather than the Adapt-In menu for exactly that reason:
173
-
174
- | Cluster | Section | Why it is required |
175
- |---|---|---|
176
- | **Cross-Cutting NFRs** | §6 | G2 passes on numbered FR **and NFR**. Each NFR MUST name `enforced_by` — an `AD-N`, a `DEC-`, or a test name. An NFR nothing enforces is decoration (`nfr-has-enforcer`) |
177
- | **Constraints and Guardrails** | §7 | A constraint found at G4 costs a decision that one sentence here would have prevented |
178
-
179
- Constraints MUST state only the delta beyond `.what/_product-brief/brief.md`, and MUST say "none
180
- beyond the brief" when there is nothing. An absent section reads as "not checked".
181
-
182
- Prerequisites MUST NOT be written as prose. An initiative blocked on another is a `depends_on`
183
- between `CAP` entries.
184
-
185
- ## §1 Why This Initiative is a delta
186
-
187
- BMad's default §1 Vision writes the product's vision from scratch, in the same 2-3 paragraph shape as
188
- the brief's own narrative. On the first PRD a product ever gets, that duplicates `Why` in
189
- `.what/_product-brief/brief.md` almost sentence for sentence — the same defect Executive Summary and
190
- Vision had against each other inside the brief before they were merged.
191
-
192
- §1 states only what THIS initiative changes, adds, or unlocks beyond what the brief's `Why` already
193
- says. A product with a single initiative MAY reduce this to one sentence pointing back to the brief.
194
- The full narrative is never written twice.
195
-
196
- ## Sections dropped from BMad's default, and where each fact actually lives
197
-
198
- Four of BMad's default sections carry no content specific to this PRD, or duplicate a fact this method
199
- already gives a home. Each is dropped rather than left conditional:
200
-
201
- | Dropped section | Where the fact lives instead |
202
- |---|---|
203
- | Document Purpose | Nowhere — it explained what a PRD is in general, true of every PRD, so it held no information specific to this one |
204
- | Glossary | `.control/product-glossary.md`. A term this PRD needs that is not there yet goes through `wdi-question` in the same pass — it is never added to a document-local glossary `wdi-blueprint` will not read at G3 |
205
- | Non-Goals | The product's own Scope Out (`.what/_product-brief/brief.md`), for what the product never does, and §4.2 Out of Scope for MVP, for what this release defers. A third list restating both is the same fact twice |
206
- | Open Questions | `.control/questions/`, the moment the question is found — not batched into a section read once at Finalize |
207
- | Assumptions Index | `.control/questions/assumptions.md`, through `wdi-question`, before G2. The inline `[ASSUMPTION]` tag stays as a marker for the conversation that produced it; it is not also an index entry |
208
-
209
- A reader who wants all of these assembled with the PRD's own content reads the generated deliverable —
210
- see below — rather than a hand-maintained index inside this document.
211
-
212
- ## The generated deliverable
213
-
214
- A complete, self-contained copy for a reader who should not need to open the registry or
215
- `.control/questions/` lives at `.what-rendered/_prd/<slug>/prd.md` — written by `/wdi-report render prd`,
216
- which runs `validate.py --generate`. It assembles this PRD's own prose verbatim, the
217
- Vision from the brief's `Why` plus §1's delta, the `FR`/`NFR` rows from `requirements-<slug>.yaml`, the
218
- Glossary terms this PRD actually uses, Non-Goals from the brief's Scope Out and §4.2, and the open
219
- rows from `.control/questions/` that cite one of this PRD's ids. Nobody writes to it by hand.
220
-
221
- ## What goes to `addendum.md`
222
-
223
- `addendum.md` is **not** a change log — Revision History is. It holds depth that belongs downstream
224
- or earned its place but does not fit the narrative: rejected-alternative rationale, options matrices,
225
- mechanism and transport decisions, technical how, in-depth personas, sizing data.
226
-
227
- Content MUST be captured there *during* the conversation when the user volunteers it, not swept
228
- there at Finalize. What in the addendum turns out to bind a later document MUST be written into that
229
- document by the skill owning its layer, rather than cited from the addendum forever.
230
-
231
- Audit and override information MUST NOT go to the addendum; it belongs in the memlog.
232
-
233
- ## Passing G2
234
-
235
- - Every `[ASSUMPTION]` still unresolved at Finalize MUST be filed through `wdi-question` before the gate
236
- opens — into `assumptions.md` by default, and into `blocking.md` only through the three tests that file
237
- states. Filing one as blocking "to be safe" is the habit that produced 146 ids.
238
- - `bmad-review` runs automatically through `doc_standards` on `prd.md` and `addendum.md`. It MUST
239
- have run before the gate — a Product Owner's 45 minutes are for deciding, not proofreading.
240
- - The gate reads `prd.md` and `EXPERIENCE.md` together. A PRD that passes while the experience side
241
- is missing has answered only half of what G2 decides.
242
- - Solution shape MUST NOT appear. If a sentence names a framework, a table, or a transport, it belongs in
243
- `addendum.md` or in the spine.
244
- - Invoke through `wdi-product`, never `bmad-prd` directly — the wrapper is what checks the rules on this
245
- page and lands the memlog.
1
+ ---
2
+ status: Accepted
3
+ ---
4
+
5
+ # PRD Guide
6
+
7
+ **Loaded when:** writing, updating, or validating a PRD
8
+
9
+ A PRD states what the product promises a user for one functional area. It does not describe how the
10
+ system behaves — that is `SRS-<pc>.md` — and it does not describe how it is built — that is
11
+ `SDD-<pc>.md`. When a sentence here could only be checked by reading code, it is in the wrong file.
12
+
13
+ ## Home and life cycle
14
+
15
+ - One PRD per **initiative / functional area**. It MUST live at `.what/_prd/<initiative>/prd.md`,
16
+ with `addendum.md` beside it. Set through `prd_output_path` and `run_folder_pattern` in
17
+ `_bmad/custom/bmad-prd.toml`.
18
+ - A PRD is a **living document**. It MUST NOT be frozen, archived, or superseded when a release
19
+ ships.
20
+ - Memlog MUST go to `.control/memlog/prd-<slug>.md` via `--path`, with the slug matching the folder.
21
+ `--workspace` MUST NOT be used; it would leave a `.memlog.md` inside `.what/`.
22
+ - `run_folder_pattern` ships as `ISI-slug-inisiatif`, which is deliberately unusable. A PRD found in
23
+ a folder by that name means the override was never pointed at a real initiative slug; `wdi-product`
24
+ check 1 catches it, and it MUST be moved before G2.
25
+
26
+ ## Update, or a new PRD
27
+
28
+ This is the decision the guide exists for, and the default is **Update**.
29
+
30
+ | Situation | What to do |
31
+ |---|---|
32
+ | Behaviour of an existing promise changes | Update |
33
+ | A promise turns out to be wrong and must be withdrawn | Update — and the withdrawal MUST be visible in Revision History, not silently deleted. This is the one mandated history line in the method, and it survives because it is **business** history read by someone outside the room, not a record that a document changed |
34
+ | A new feature that a reader would expect to find in this PRD | Update |
35
+ | The next release extends what this PRD already promises | Update. A release is never a reason on its own |
36
+ | A functional area a reader would not think to look for here | New PRD |
37
+
38
+ The test is the reader, not the calendar: **would someone looking for this promise open this
39
+ document?** If yes, it belongs here however large the change. A PRD MUST NOT be split because it
40
+ grew long — length is what `addendum.md` and feature grouping are for. It is split only when the two
41
+ areas have different readers, different stakeholders, or no shared vocabulary.
42
+
43
+ When a split is genuinely right, the existing PRD MUST keep its own IDs. `FR-N` never moves between
44
+ PRDs; the sequence is global to the product.
45
+
46
+ ## One home, and what `.what/<pc>/` may take from it
47
+
48
+ A PRD is the **reference** the blueprint and each component work from, not a quarry. `.what/<pc>/` is distilled from it — the
49
+ same promise restated as behaviour, at the altitude a builder needs — and the PRD stays the one place
50
+ that promise lives.
51
+
52
+ - One PRD per initiative. Its content MUST NOT be split into pieces spread across `.what/<pc>/`, and
53
+ a fragment MUST NOT be moved out of it. A promise with two homes drifts, and the copy people read
54
+ is whichever they open first.
55
+ - `.what/<pc>/` MUST cite the `FR`/`NFR` it realises by ID rather than restating its text. A use case
56
+ saying what the system does is derivation; a use case reproducing the PRD's paragraph is a second
57
+ copy.
58
+ - One initiative MAY span several Product Components, and one component MAY serve several PRDs. That
59
+ is why neither can absorb the other — `corpus-guide.md` owns the two-axis rule.
60
+ - When the distillation proves a promise cannot be behaved into, the PRD changes first, through
61
+ `wdi-product` intent `update`. The SRS MUST NOT narrow it quietly.
62
+
63
+ ## Revision History
64
+
65
+ - Every `update` run MUST add **exactly one row**, appended at the bottom — one row per **pass**, never
66
+ one per correction.
67
+ - Rows MUST be written for someone who was not in the room — a client, a sponsor, an auditor. State
68
+ what the promise now is, not which section was edited. "Payment retries now cap at three attempts,
69
+ down from unlimited, because support could not explain the charges" is a row. "Updated §4.2" is
70
+ not.
71
+ - The `Releases affected` column names the releases whose promise changed. It MUST match
72
+ `target_release` on the affected `CAP` entries.
73
+ - A row MUST NOT be edited after the run that wrote it. A correction is a new row.
74
+
75
+ The boundary against the memlog matters and MUST NOT be collapsed:
76
+
77
+ | | Memlog | Revision History |
78
+ |---|---|---|
79
+ | Records | Every decision, change, override, assumption inside a run | What changed for the reader |
80
+ | Written | Continuously, by `memlog.py`, append-only | Once per run, by hand |
81
+ | Read by | The next run, and audits | Anyone opening the PRD |
82
+ | Lives in | `.control/memlog/` | The PRD itself |
83
+
84
+ Neither MUST be written in place of the other. A PRD whose only change record is the memlog is
85
+ unreadable to the people it was written for.
86
+
87
+ ## Release lives in the registry
88
+
89
+ Release MUST NOT be expressed through this document's folder name, title, or frontmatter. It is
90
+ carried by:
91
+
92
+ | Field | Answers |
93
+ |---|---|
94
+ | `CAP.target_release` | Which release this capability is planned for. **The only place a promise's release is written** |
95
+ | `specs.yaml` `release` | Which release a spec of work belongs to — the execution side |
96
+
97
+ An `FR` MUST NOT carry a release of its own. It inherits one from its `CAP`, the same way it reaches
98
+ its `BG`: each child names only its parent. A capability whose requirements genuinely land in
99
+ different releases is two capabilities, and MUST be split rather than annotated.
100
+
101
+ Naming a release in prose as context MAY happen; the registry is what binds.
102
+
103
+ ## Numbering
104
+
105
+ `BG-N` is allocated from `.control/registry/goals.yaml`; `CAP-N`, `FR-N`, `NFR-N`, and `UJ-N` from this initiative's own `.control/registry/requirements-<slug>.yaml` — one file, one writer, one gate
106
+ and MUST NOT restart at 1. The chain runs `BG → CAP → FR/NFR → UC → DEC → Ticket → Test`, and each
107
+ child names only its parent:
108
+
109
+ - Each feature in §3 MUST declare its `CAP-N` and the `BG-N` it serves.
110
+ - Each `FR` MUST declare its `capability`. Its goal is reached *through* the capability and MUST NOT
111
+ be restated on the FR.
112
+ - Each `NFR` attaches to `BG` directly — it does not pass through `CAP`.
113
+
114
+ `chain-links` checks both links. An FR with no capability is a promise nobody asked for.
115
+
116
+ ## `FR`/`NFR` text lives in the registry, not in this document
117
+
118
+ The PRD cites `FR-N`/`NFR-N` under each feature's **Realizes:** line. It MUST NOT also write the
119
+ statement, the proof of done, or the enforcer in prose — those fields live on the id's own row in
120
+ `requirements-<slug>.yaml`, and landing them there is part of `wdi-product` producing this PRD, not a
121
+ follow-up. A promise written in both places is one fact with two homes, and the copy a reader trusts
122
+ is whichever they open first.
123
+
124
+ Every `FR` MUST carry **exactly one** proof of done: a sentence a Product Owner can check without opening
125
+ the code. It is what lets one `FR` become one testable unit of work, and it is why a spec is ideally one
126
+ `FR`.
127
+
128
+ **The double proof of done stays repealed.** A business sentence *and* a technical restatement naming
129
+ status codes, limits, and payloads meant writing the same acceptance twice, in two vocabularies that
130
+ then drifted. The technical form is represented by the **test name** recorded in `specs.yaml`, where it
131
+ is checked mechanically (`ticket-has-test`) instead of read.
132
+
133
+ A technical detail that genuinely has to be written down belongs in `addendum.md` or in the SDD, not in
134
+ a second proof of done — and not in this document's prose either.
135
+
136
+ ## Wording versus promise — two different journeys
137
+
138
+ The distinction this guide exists to protect, and the one that produced three corrections that ended
139
+ "reported but not fixed":
140
+
141
+ | What changes | Route |
142
+ |---|---|
143
+ | The **wording** of an `FR` — a wrong cross-reference, a retired term, a word no longer consistent with an `applied` decision, while **the promise is the same** | The skill already at work fixes it directly. Recorded in the memlog, and **one** Revision History row per pass, not per correction |
144
+ | The **promise** of an `FR` — scope changes, the proof of done changes, an `FR` is retired or born | `wdi-product` intent `update`, and the change-control matrix in `delivery-flow-guide.md` says which gates reopen |
145
+
146
+ The guard against abuse is already in the Revision History rule: a row is written for someone who was not in
147
+ the room. A wording correction produces no row a client would find interesting, and that is precisely the
148
+ evidence it was not a change of promise.
149
+
150
+ Treating a wording fix as a promise change is not caution — it is what made three corrections queue behind a
151
+ gate and then get dropped.
152
+
153
+ ## `owns:` — one entity, one writer
154
+
155
+ A domain entity MUST have exactly one owner authorised to write it. Usually that is a Product Component,
156
+ declared as `owns:` on its row in `components.yaml`; an `FR` from another PRD that needs to change the entity
157
+ MUST point at the owner's `FR` through `defers_to`, rather than promising to write it itself. `entity-one-writer` checks this.
158
+
159
+ **A few entities belong to no Product Component at all** — a product-wide setting, the trace of one shared
160
+ outbound channel. Those are owned by `_platform` through `platform_owns`, and the test for when that is
161
+ legitimate lives in `corpus-guide.md`. `_platform` has no `FR`, so an `FR` writing a platform-owned entity is
162
+ **not** asked for a `defers_to`; what binds instead is the shape documented in `cross-cutting.md`. Reaching
163
+ for `_platform` because the owner is hard to decide is the one use of it that the test refuses.
164
+
165
+ This is not theoretical: two PRDs have already collided semantically over one shared numbering series. Two
166
+ `FR` claiming write authority over the same entity, with neither pointing at the other, is a defect at the
167
+ moment it is written — not at the moment the code disagrees.
168
+
169
+ ## Sections that stop being optional
170
+
171
+ BMad's Adapt-In Menu is conditional by design. Two clusters MUST always be present here, and are in
172
+ the Essential Spine rather than the Adapt-In menu for exactly that reason:
173
+
174
+ | Cluster | Section | Why it is required |
175
+ |---|---|---|
176
+ | **Cross-Cutting NFRs** | §6 | G2 passes on numbered FR **and NFR**. Each NFR MUST name `enforced_by` — an `AD-N`, a `DEC-`, or a test name. An NFR nothing enforces is decoration (`nfr-has-enforcer`) |
177
+ | **Constraints and Guardrails** | §7 | A constraint found at G4 costs a decision that one sentence here would have prevented |
178
+
179
+ Constraints MUST state only the delta beyond `.what/_product-brief/brief.md`, and MUST say "none
180
+ beyond the brief" when there is nothing. An absent section reads as "not checked".
181
+
182
+ Prerequisites MUST NOT be written as prose. An initiative blocked on another is a `depends_on`
183
+ between `CAP` entries.
184
+
185
+ ## §1 Why This Initiative is a delta
186
+
187
+ BMad's default §1 Vision writes the product's vision from scratch, in the same 2-3 paragraph shape as
188
+ the brief's own narrative. On the first PRD a product ever gets, that duplicates `Why` in
189
+ `.what/_product-brief/brief.md` almost sentence for sentence — the same defect Executive Summary and
190
+ Vision had against each other inside the brief before they were merged.
191
+
192
+ §1 states only what THIS initiative changes, adds, or unlocks beyond what the brief's `Why` already
193
+ says. A product with a single initiative MAY reduce this to one sentence pointing back to the brief.
194
+ The full narrative is never written twice.
195
+
196
+ ## Sections dropped from BMad's default, and where each fact actually lives
197
+
198
+ Four of BMad's default sections carry no content specific to this PRD, or duplicate a fact this method
199
+ already gives a home. Each is dropped rather than left conditional:
200
+
201
+ | Dropped section | Where the fact lives instead |
202
+ |---|---|
203
+ | Document Purpose | Nowhere — it explained what a PRD is in general, true of every PRD, so it held no information specific to this one |
204
+ | Glossary | `.control/product-glossary.md`. A term this PRD needs that is not there yet goes through `wdi-question` in the same pass — it is never added to a document-local glossary `wdi-blueprint` will not read at G3 |
205
+ | Non-Goals | The product's own Scope Out (`.what/_product-brief/brief.md`), for what the product never does, and §4.2 Out of Scope for MVP, for what this release defers. A third list restating both is the same fact twice |
206
+ | Open Questions | `.control/questions/`, the moment the question is found — not batched into a section read once at Finalize |
207
+ | Assumptions Index | `.control/questions/assumptions.md`, through `wdi-question`, before G2. The inline `[ASSUMPTION]` tag stays as a marker for the conversation that produced it; it is not also an index entry |
208
+
209
+ A reader who wants all of these assembled with the PRD's own content reads the generated deliverable —
210
+ see below — rather than a hand-maintained index inside this document.
211
+
212
+ ## The generated deliverable
213
+
214
+ A complete, self-contained copy for a reader who should not need to open the registry or
215
+ `.control/questions/` lives at `.what-rendered/_prd/<slug>/prd.md` — written by `/wdi-report render prd`,
216
+ which runs `validate.py --generate`. It assembles this PRD's own prose verbatim, the
217
+ Vision from the brief's `Why` plus §1's delta, the `FR`/`NFR` rows from `requirements-<slug>.yaml`, the
218
+ Glossary terms this PRD actually uses, Non-Goals from the brief's Scope Out and §4.2, and the open
219
+ rows from `.control/questions/` that cite one of this PRD's ids. Nobody writes to it by hand.
220
+
221
+ ## What goes to `addendum.md`
222
+
223
+ `addendum.md` is **not** a change log — Revision History is. It holds depth that belongs downstream
224
+ or earned its place but does not fit the narrative: rejected-alternative rationale, options matrices,
225
+ mechanism and transport decisions, technical how, in-depth personas, sizing data.
226
+
227
+ Content MUST be captured there *during* the conversation when the user volunteers it, not swept
228
+ there at Finalize. What in the addendum turns out to bind a later document MUST be written into that
229
+ document by the skill owning its layer, rather than cited from the addendum forever.
230
+
231
+ Audit and override information MUST NOT go to the addendum; it belongs in the memlog.
232
+
233
+ ## Passing G2
234
+
235
+ - Every `[ASSUMPTION]` still unresolved at Finalize MUST be filed through `wdi-question` before the gate
236
+ opens — into `assumptions.md` by default, and into `blocking.md` only through the three tests that file
237
+ states. Filing one as blocking "to be safe" is the habit that produced 146 ids.
238
+ - `bmad-review` runs automatically through `doc_standards` on `prd.md` and `addendum.md`. It MUST
239
+ have run before the gate — a Product Owner's 45 minutes are for deciding, not proofreading.
240
+ - The gate reads `prd.md` and the experience together — `.what/experience.md` for what holds across components, the run's `EXPERIENCE.md` for the rest. A PRD that passes while the experience side
241
+ is missing has answered only half of what G2 decides.
242
+ - Solution shape MUST NOT appear. If a sentence names a framework, a table, or a transport, it belongs in
243
+ `addendum.md` or in the spine.
244
+ - Invoke through `wdi-product`, never `bmad-prd` directly — the wrapper is what checks the rules on this
245
+ page and lands the memlog.