baldart 3.14.0 → 3.15.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +70 -15
- package/VERSION +1 -1
- package/framework/.claude/agents/api-perf-cost-auditor.md +47 -10
- package/framework/.claude/agents/coder.md +61 -10
- package/framework/.claude/agents/prd-card-writer.md +29 -19
- package/framework/.claude/agents/security-reviewer.md +1 -1
- package/framework/.claude/skills/bug/references/logging-patterns.md +45 -8
- package/framework/.claude/skills/new/SKILL.md +180 -86
- package/framework/.claude/skills/prd/SKILL.md +30 -2
- package/framework/.claude/skills/prd/assets/card-template.yml +43 -26
- package/framework/.claude/skills/prd/assets/epic-template.yml +3 -2
- package/framework/.claude/skills/prd/assets/prd-template.md +90 -14
- package/framework/.claude/skills/prd/assets/state-template.md +18 -0
- package/framework/.claude/skills/prd/references/api-perf-gate.md +102 -52
- package/framework/.claude/skills/prd/references/audit-phase.md +13 -13
- package/framework/.claude/skills/prd/references/discovery-phase.md +214 -28
- package/framework/.claude/skills/prd/references/prd-writing-phase.md +65 -23
- package/framework/.claude/skills/prd/references/research-phase.md +22 -4
- package/framework/.claude/skills/prd/references/ui-design-phase.md +115 -3
- package/framework/.claude/skills/prd/references/validation-phase.md +2 -2
- package/framework/docs/PROJECT-CONFIGURATION.md +41 -1
- package/framework/templates/baldart.config.template.yml +25 -0
- package/package.json +1 -1
- package/src/commands/configure.js +72 -0
- package/src/commands/update.js +13 -1
- package/src/utils/git.js +6 -1
|
@@ -72,8 +72,118 @@ la feature prima di scrivere qualsiasi documento.
|
|
|
72
72
|
|
|
73
73
|
**Gate:** state file exists on disk AND all tasks created AND context loaded.
|
|
74
74
|
|
|
75
|
-
**Immediately proceed to Step
|
|
76
|
-
and
|
|
75
|
+
**Immediately proceed to Step 1.6** — do NOT stop here. Show the kickoff message
|
|
76
|
+
and ask the mockup intake question in the same turn.
|
|
77
|
+
|
|
78
|
+
## Step 1.6 — Mockup Intake (MANDATORY)
|
|
79
|
+
|
|
80
|
+
Runs between Kickoff (Step 1) and Discovery (Step 2). Cannot be skipped.
|
|
81
|
+
|
|
82
|
+
**Purpose:** detect whether the user already has mockups for this feature, archive
|
|
83
|
+
them as canonical artefacts, and feed the visual analysis into Discovery alongside
|
|
84
|
+
the codebase context from `/cont`. The Step 3 (UI Design) decision tree consumes the
|
|
85
|
+
result.
|
|
86
|
+
|
|
87
|
+
### 1.6.1 — Ask
|
|
88
|
+
|
|
89
|
+
After the kickoff output (Step 1, point 7), append this question to the SAME message:
|
|
90
|
+
|
|
91
|
+
```
|
|
92
|
+
### Domanda — Mockup
|
|
93
|
+
|
|
94
|
+
Hai dei mockup a disposizione per questa feature?
|
|
95
|
+
|
|
96
|
+
- **Sì** → posso analizzarli prima di iniziare la discovery, così le domande
|
|
97
|
+
saranno calibrate su quello che è già definito visivamente.
|
|
98
|
+
- **No** → procediamo con la discovery standard; se serve, in Step 3 genero
|
|
99
|
+
io 3 opzioni di design.
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
**STOP.** Display Progress Bar (row `1.6 Mockup intake: 🔄`) and wait for the user.
|
|
103
|
+
|
|
104
|
+
### 1.6.2 — Answer = "No"
|
|
105
|
+
|
|
106
|
+
- Update state file `## UI Design`: `mockups.status: none`.
|
|
107
|
+
- Mark progress bar row `1.6 ✅ (no mockups)`.
|
|
108
|
+
- **Immediately proceed to Step 2** in the same turn. No further STOP.
|
|
109
|
+
|
|
110
|
+
### 1.6.3 — Answer = "Sì"
|
|
111
|
+
|
|
112
|
+
Append this follow-up to the SAME message:
|
|
113
|
+
|
|
114
|
+
```
|
|
115
|
+
Perfetto. In che forma me li passi?
|
|
116
|
+
|
|
117
|
+
- **Immagini in chat** — incollale direttamente nel prossimo messaggio.
|
|
118
|
+
- **Path locali** — incolla i percorsi (assoluti o relativi al repo) e li copio
|
|
119
|
+
in `${paths.prd_dir}/<slug>/mockups/`.
|
|
120
|
+
- **Misti** — entrambe le cose.
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
- Update state file `## UI Design`: `mockups.status: requested`, `mockups.format: pending`.
|
|
124
|
+
- **STOP.** Wait for the user.
|
|
125
|
+
|
|
126
|
+
### 1.6.4 — Mockup reception & archival
|
|
127
|
+
|
|
128
|
+
When the user replies with the mockups:
|
|
129
|
+
|
|
130
|
+
1. **Detect format** and update `mockups.format` ∈ {`chat-images`, `local-paths`, `mixed`}.
|
|
131
|
+
2. **For each local path provided:**
|
|
132
|
+
- Resolve to absolute path. If file does not exist: ask the user to confirm/correct
|
|
133
|
+
(do not silently skip).
|
|
134
|
+
- Ensure `${paths.prd_dir}/<slug>/mockups/` exists (create if missing).
|
|
135
|
+
- Copy the file into that directory, preserving filename. On collision (file with
|
|
136
|
+
same name already there): append numeric suffix (`<name>-2.png`).
|
|
137
|
+
- Record both paths in state: `mockups.original_paths[]` and `mockups.canonical_paths[]`.
|
|
138
|
+
3. **For chat images:** record in state `mockups.original_paths[]` as `chat://image-N`
|
|
139
|
+
(the images remain in the conversation context window).
|
|
140
|
+
4. Update `mockups.status: provided` (or `partial` only if the user explicitly says
|
|
141
|
+
"ho solo questi 2 ma servono anche altri").
|
|
142
|
+
|
|
143
|
+
### 1.6.5 — Mockup analysis (MANDATORY before Discovery)
|
|
144
|
+
|
|
145
|
+
Analyze ALL provided mockups (visual analysis for chat images, Read for copied files
|
|
146
|
+
that are textual like HTML/SVG). Populate `## UI Design` in the state file using the
|
|
147
|
+
**Mockup analysis schema** (see appendix at the end of this file).
|
|
148
|
+
|
|
149
|
+
When `features.has_design_system: true`, BLOCKING reads of `${paths.design_system}/INDEX.md`
|
|
150
|
+
and `${paths.design_system}/tokens-reference.md` apply BEFORE running the alignment
|
|
151
|
+
check — same protocol as Step 3 (UI Design). Flag every hardcoded value (hex / shadow /
|
|
152
|
+
radius / spacing) that conflicts with a known token as a violation in
|
|
153
|
+
`mockup_analysis.design_system_alignment.violations[]`.
|
|
154
|
+
|
|
155
|
+
### 1.6.6 — Output and handoff to Discovery
|
|
156
|
+
|
|
157
|
+
After analysis is complete, present to the user:
|
|
158
|
+
|
|
159
|
+
```
|
|
160
|
+
Mockup acquisiti e analizzati: N schermate identificate.
|
|
161
|
+
|
|
162
|
+
Schermate: <list>
|
|
163
|
+
Flusso utente inferito: <one-line summary>
|
|
164
|
+
Componenti riconosciuti: N (X riusati dal registry, Y nuovi)
|
|
165
|
+
Stati visibili: <empty/loading/error/success per schermata se rilevanti>
|
|
166
|
+
Allineamento design system: <aligned | N violations to resolve in Step 3>
|
|
167
|
+
Gap da chiarire in discovery: <list of ambiguities, max 5>
|
|
168
|
+
|
|
169
|
+
Ora entro in **Discovery** — le domande saranno calibrate su quanto già definito
|
|
170
|
+
nei mockup. Le ambiguità rilevate diventeranno domande mirate.
|
|
171
|
+
|
|
172
|
+
<Progress Bar>
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
- Mark progress bar row `1.6 ✅` (or `🔄` if `partial`).
|
|
176
|
+
- **Immediately proceed to Step 2** in the same turn.
|
|
177
|
+
|
|
178
|
+
### Coordination with `/cont`
|
|
179
|
+
|
|
180
|
+
The `/cont` skill invoked in Step 1.5 runs synchronously and completes before the
|
|
181
|
+
kickoff output. The mockup intake question is asked in the same message; if the user
|
|
182
|
+
answers "Sì", the STOP gives the codebase context time to settle in conversation
|
|
183
|
+
history while we wait. When the mockups arrive, the visual analysis combines with the
|
|
184
|
+
already-loaded codebase context to inform Discovery dimension selection (especially
|
|
185
|
+
dimension 5 UI impact and partially dimension 2 User journey, both of which can be
|
|
186
|
+
pre-populated from `mockup_analysis`).
|
|
77
187
|
|
|
78
188
|
## Step 2 — Discovery Question Loop
|
|
79
189
|
|
|
@@ -171,6 +281,16 @@ section of the state file. Mark dimension as covered.
|
|
|
171
281
|
the Change Request flow. After it completes, resume discovery from the
|
|
172
282
|
next uncovered dimension.
|
|
173
283
|
- If user says out-of-scope: note in Discovery Log and continue.
|
|
284
|
+
- **New-Screen Check** (only when `mockups.status` ∈ {`provided`, `partial`}):
|
|
285
|
+
When the user's answer reveals a UI screen NOT present in
|
|
286
|
+
`mockup_analysis.screens[]`, do NOT treat it as a scope expansion. Instead,
|
|
287
|
+
append the screen to `screens_in_scope[]` in the state file with
|
|
288
|
+
`covered_by_mockups: false`. Log inline:
|
|
289
|
+
`Ho rilevato una nuova schermata non presente nei mockup: **<name>**. La
|
|
290
|
+
genero in Step 3 (modalità ibrida) solo per quella schermata.`
|
|
291
|
+
Continue with the next dimension. This is a routine signal for Step 3, not
|
|
292
|
+
a scope expansion — the Scope Expansion Check above still applies for
|
|
293
|
+
non-UI entities (endpoints, roles, collections).
|
|
174
294
|
- Update state file
|
|
175
295
|
- Proceed to next uncovered dimension (back to action 1)
|
|
176
296
|
|
|
@@ -274,30 +394,41 @@ Instead, run the E2E Evaluation Decision Tree and present the result.
|
|
|
274
394
|
**When E2E is REQUIRED or user accepts RECOMMENDED:**
|
|
275
395
|
|
|
276
396
|
1. Identify test scenarios from user stories and acceptance criteria (2-5 scenarios max).
|
|
277
|
-
2. Determine test
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
397
|
+
2. **Determine test personas** by intersecting:
|
|
398
|
+
- The user-stories' `As a <persona>` field, and
|
|
399
|
+
- `identity.audience_segments[]` from `baldart.config.yml` (single source of truth
|
|
400
|
+
for the project's personas — NEVER hardcode persona names in the skill).
|
|
401
|
+
|
|
402
|
+
For each persona that needs E2E coverage, gather credentials using the following
|
|
403
|
+
resolution order:
|
|
404
|
+
|
|
405
|
+
**a. Consult `.baldart/overlays/prd.md`** (if present) for a `## Test Credentials`
|
|
406
|
+
section. If the overlay defines a default credential pattern for the persona
|
|
407
|
+
(e.g. `customer → phone OTP`, `merchant → username/password`), use it and
|
|
408
|
+
log inline: `Credenziali test {{persona}}: caricate da overlay.`
|
|
409
|
+
Do NOT print the actual credential values inline — only confirm the source.
|
|
410
|
+
|
|
411
|
+
**b. Otherwise ASK the user**, ONE question per persona:
|
|
412
|
+
```
|
|
413
|
+
### Domanda — Credenziali test {{persona}}
|
|
414
|
+
|
|
415
|
+
Questa feature richiede test E2E con la persona **{{persona}}**.
|
|
416
|
+
Fornisci le credenziali di test (o un riferimento all'ambiente di test):
|
|
417
|
+
|
|
418
|
+
- Metodo di auth: <es. password / OTP via SMS / magic link / API token>
|
|
419
|
+
- Identificativo: <es. username, email, phone>
|
|
420
|
+
- Secret: <password, OTP source, token — meglio NON incollarlo in chat,
|
|
421
|
+
usa un riferimento al vault>
|
|
422
|
+
- Contesto (se rilevante): <es. tenant, workspace, store, organization>
|
|
423
|
+
```
|
|
424
|
+
**STOP.** Wait for user response. Store the *minimum-necessary* credential
|
|
425
|
+
reference in the state file under `## Test Plan` — prefer a reference to a
|
|
426
|
+
secret manager / 1Password / `.env.test` path over the literal secret.
|
|
427
|
+
|
|
428
|
+
Suggerisci all'utente di consolidare la risposta in `.baldart/overlays/prd.md`
|
|
429
|
+
(sezione `## Test Credentials`) per evitare la stessa domanda ai PRD futuri.
|
|
430
|
+
|
|
431
|
+
**c. Mixed personas:** ripeti b. per ciascuna persona non risolta da a.
|
|
301
432
|
|
|
302
433
|
3. After credentials are gathered, summarize the test plan:
|
|
303
434
|
```
|
|
@@ -305,8 +436,8 @@ Instead, run the E2E Evaluation Decision Tree and present the result.
|
|
|
305
436
|
|
|
306
437
|
E2E: REQUIRED | RECOMMENDED (accettato)
|
|
307
438
|
Scenari: N test scenarios
|
|
308
|
-
|
|
309
|
-
|
|
439
|
+
Personas coinvolte: <list from identity.audience_segments[] involved>
|
|
440
|
+
Sorgente credenziali: [overlay | user-provided | mixed]
|
|
310
441
|
|
|
311
442
|
Scenari pianificati:
|
|
312
443
|
1. [scenario description — maps to US-X / AC-X]
|
|
@@ -315,6 +446,11 @@ Instead, run the E2E Evaluation Decision Tree and present the result.
|
|
|
315
446
|
|
|
316
447
|
4. Mark dimension as covered. Update state file `## Test Plan` section.
|
|
317
448
|
|
|
449
|
+
> **Security note:** the framework MUST NOT contain any real test credential
|
|
450
|
+
> (phone numbers, usernames, passwords, tokens). All credential examples in this
|
|
451
|
+
> file are intentionally generic. Project-specific defaults live in
|
|
452
|
+
> `.baldart/overlays/prd.md` (consumer-owned, not redistributed).
|
|
453
|
+
|
|
318
454
|
### Research Trigger (evaluated at ~75% comprehension)
|
|
319
455
|
|
|
320
456
|
When 6+ non-test dimensions are covered, evaluate complexity signals from
|
|
@@ -357,3 +493,53 @@ Passo alla fase successiva: [UI Design / Scrittura PRD]
|
|
|
357
493
|
|
|
358
494
|
<Progress Bar>
|
|
359
495
|
```
|
|
496
|
+
|
|
497
|
+
---
|
|
498
|
+
|
|
499
|
+
## Appendix — Mockup analysis schema
|
|
500
|
+
|
|
501
|
+
Used by Step 1.6.5. Populate the `## UI Design` section of the state file with this
|
|
502
|
+
structure. Be specific — vague analysis defeats the purpose of skipping Step 3.
|
|
503
|
+
|
|
504
|
+
```yaml
|
|
505
|
+
mockups:
|
|
506
|
+
status: provided | partial | none | requested
|
|
507
|
+
format: chat-images | local-paths | mixed
|
|
508
|
+
original_paths:
|
|
509
|
+
- <user-provided path or chat://image-N>
|
|
510
|
+
canonical_paths:
|
|
511
|
+
- mockups/<file>.png # only for local-paths
|
|
512
|
+
mockup_analysis:
|
|
513
|
+
screens:
|
|
514
|
+
- name: <inferred name, e.g. "Lista ordini">
|
|
515
|
+
mockup_ref: <canonical_path or chat://image-N>
|
|
516
|
+
purpose: <one line — what this screen lets the user do>
|
|
517
|
+
components:
|
|
518
|
+
- <component name from ${paths.design_system}/INDEX.md if matched, else free-form>
|
|
519
|
+
states_visible: [empty, loading, error, success, default]
|
|
520
|
+
copy_excerpts:
|
|
521
|
+
- <verbatim text visible in the mockup, max ~10 strings per screen>
|
|
522
|
+
gaps:
|
|
523
|
+
- <ambiguity to clarify in Discovery, e.g. "filtro per data: range o singola?">
|
|
524
|
+
user_flow:
|
|
525
|
+
- <step 1, e.g. "Utente apre Lista ordini → tap su riga → Dettaglio ordine">
|
|
526
|
+
design_system_alignment:
|
|
527
|
+
status: aligned | violations | not-applicable
|
|
528
|
+
violations:
|
|
529
|
+
- mockup: <screen name>
|
|
530
|
+
kind: hardcoded-color | hardcoded-spacing | hardcoded-shadow | hardcoded-radius | custom-component
|
|
531
|
+
detail: <e.g. "background #FF6A00 — token equivalent: --color-brand-primary">
|
|
532
|
+
fix_in_step_3: <token name or component to swap in>
|
|
533
|
+
```
|
|
534
|
+
|
|
535
|
+
**When NOT to fill a field:**
|
|
536
|
+
- Omit `design_system_alignment` entirely (do NOT write `not-applicable`) when
|
|
537
|
+
`features.has_design_system: false` — the field becomes irrelevant.
|
|
538
|
+
- Omit `copy_excerpts` for screens that have no readable text (icon-only).
|
|
539
|
+
- Omit `states_visible` for screens that show only the default state — do not
|
|
540
|
+
invent states the mockup doesn't show.
|
|
541
|
+
|
|
542
|
+
**Gap discipline:** every entry in `gaps[]` MUST become either a Discovery question
|
|
543
|
+
or an explicit non-question (recorded in Discovery Log as "skipped — outside
|
|
544
|
+
mockup scope"). Gaps that remain unresolved by the end of Discovery block PRD
|
|
545
|
+
writing in Step 4.
|
|
@@ -17,6 +17,11 @@ Mark task 3 as `in_progress`.
|
|
|
17
17
|
- Read `docs/guides/linking-protocol-rollout-v1.md` for the Canonical Ownership Matrix.
|
|
18
18
|
- Identify which existing PRDs, ADRs, reference docs, or backlog cards are canonical
|
|
19
19
|
for this feature area.
|
|
20
|
+
- **Mockup-derived canonical sources** (when `mockups.status` ∈ {`provided`, `partial`}
|
|
21
|
+
in state file): treat `${paths.prd_dir}/<slug>/mockups/` as a canonical visual
|
|
22
|
+
reference. Add a row to the PRD Canonical Sources table:
|
|
23
|
+
`| Mockup originali | ${paths.prd_dir}/<slug>/mockups/ |`. If chat images were
|
|
24
|
+
analyzed without being copied to disk, add: `| Mockup chat | inline in PRD session — see Design Reference section |`.
|
|
20
25
|
3. **Incorporate research findings** (if `## Research Findings` in state file is populated):
|
|
21
26
|
- Reference best practices in data model, API, and architecture decisions.
|
|
22
27
|
- Cite sources in PRD rationale sections.
|
|
@@ -24,42 +29,65 @@ Mark task 3 as `in_progress`.
|
|
|
24
29
|
- If regulatory findings exist: add a dedicated "Compliance Requirements" section.
|
|
25
30
|
- Include a "Research-Informed Decisions" subsection listing decisions influenced
|
|
26
31
|
by research, with brief rationale and source reference.
|
|
27
|
-
3.5. **Schema Verification Gate (MANDATORY if feature touches
|
|
32
|
+
3.5. **Schema Verification Gate (MANDATORY if feature touches the persistence layer)**
|
|
28
33
|
|
|
29
|
-
|
|
30
|
-
|
|
34
|
+
Read `stack.database` from `baldart.config.yml`. If empty AND the feature
|
|
35
|
+
description mentions data persistence, ASK the user which database is in
|
|
36
|
+
use and persist the answer to `baldart.config.yml` (offer `npx baldart
|
|
37
|
+
configure` if multiple keys are missing). Skip this gate when
|
|
38
|
+
`stack.database: none` or the feature is stateless.
|
|
39
|
+
|
|
40
|
+
The vocabulary in this gate adapts to `stack.database`:
|
|
41
|
+
- Firestore / MongoDB / DynamoDB → "collections" / "documents" / "fields"
|
|
42
|
+
- Postgres / Supabase / MySQL / SQLite → "tables" / "rows" / "columns"
|
|
43
|
+
The procedure below uses **{entity}** = collection|table and **{field}** =
|
|
44
|
+
field|column.
|
|
45
|
+
|
|
46
|
+
If any of the following apply: new {entity}, modified {field}s, compound
|
|
47
|
+
queries, or reading/writing existing rows/documents — run this gate before
|
|
48
|
+
writing Section 5 (Data Model).
|
|
31
49
|
|
|
32
50
|
**Procedure:**
|
|
33
|
-
1. Identify every
|
|
34
|
-
2. For each
|
|
51
|
+
1. Identify every {entity} the feature uses or modifies.
|
|
52
|
+
2. For each {entity}: read the project schema registry. The path is
|
|
53
|
+
project-specific — common locations: `${paths.references_dir}/field-registry.json`
|
|
54
|
+
(Firestore-style projects), `${paths.references_dir}/schema.md` (SQL),
|
|
55
|
+
`${paths.references_dir}/collections/*.md` (per-collection markdown), or
|
|
56
|
+
the migrations dir for SQL projects (`migrations/`, `db/migrate/`,
|
|
57
|
+
`prisma/schema.prisma`, `supabase/migrations/`). Resolution order: check
|
|
58
|
+
`.baldart/overlays/prd.md § Schema Registry` first if defined; otherwise
|
|
59
|
+
pick the convention matching `stack.database`.
|
|
35
60
|
3. Build a `## Schema Verification` section in the PRD (see template below).
|
|
36
|
-
4. Mark each field: `✅ existing` | `🆕 new` | `❌ NOT FOUND`.
|
|
37
|
-
5. **GATE**: if ANY field is `❌ NOT FOUND` and NOT marked as `🆕 new`:
|
|
61
|
+
4. Mark each {field}: `✅ existing` | `🆕 new` | `❌ NOT FOUND`.
|
|
62
|
+
5. **GATE**: if ANY {field} is `❌ NOT FOUND` and NOT marked as `🆕 new`:
|
|
38
63
|
- STOP — do not advance to Section 5 (backlog cards).
|
|
39
|
-
- Ask the user: "Is `fieldName` in
|
|
40
|
-
- If new: add full schema definition in PRD Section
|
|
64
|
+
- Ask the user: "Is `{fieldName}` in {entity} `{entityName}` a new {field} or a naming error?"
|
|
65
|
+
- If new: add full schema definition in PRD Section 5 and mark `🆕`.
|
|
41
66
|
- If error: correct the name.
|
|
42
67
|
|
|
43
68
|
**Template `## Schema Verification`** (insert after PRD Acceptance Criteria section):
|
|
44
69
|
|
|
45
70
|
```markdown
|
|
46
71
|
## Schema Verification
|
|
47
|
-
> Source:
|
|
48
|
-
>
|
|
72
|
+
> Source: {schema-registry-path} — verified on {YYYY-MM-DD}
|
|
73
|
+
> Database: {stack.database}
|
|
74
|
+
> Complexity: HIGH | MEDIUM | LOW
|
|
49
75
|
|
|
50
|
-
###
|
|
76
|
+
### {entity}: {entityName}
|
|
51
77
|
|
|
52
|
-
|
|
|
53
|
-
|
|
78
|
+
| {field} | Type | Status | Note |
|
|
79
|
+
|---------|------|--------|------|
|
|
54
80
|
| `fieldName` | string | ✅ existing | — |
|
|
55
|
-
| `newField` | string | 🆕 new | schema in Section
|
|
56
|
-
| `~~oldField~~` | — | ❌ NOT FOUND |
|
|
81
|
+
| `newField` | string | 🆕 new | schema in Section 5 |
|
|
82
|
+
| `~~oldField~~` | — | ❌ NOT FOUND | rename mismatch |
|
|
57
83
|
|
|
58
|
-
###
|
|
59
|
-
- (
|
|
84
|
+
### Open issues
|
|
85
|
+
- (none) — or list of ❌ with required action
|
|
60
86
|
```
|
|
61
87
|
|
|
62
|
-
**
|
|
88
|
+
**Universal fields:** auto-PK/ID, `createdAt`/`created_at`,
|
|
89
|
+
`updatedAt`/`updated_at` are universal in their stack — do not require
|
|
90
|
+
verification.
|
|
63
91
|
|
|
64
92
|
4. Write `docs/prd/<slug>/PRD.md` using the template from `assets/prd-template.md`.
|
|
65
93
|
|
|
@@ -72,13 +100,27 @@ Every PRD MUST include these sections (remove only when genuinely N/A):
|
|
|
72
100
|
- Goals / non-goals
|
|
73
101
|
- Personas
|
|
74
102
|
- User stories
|
|
75
|
-
- Data model (
|
|
103
|
+
- Data model (type definitions matching the language stack, persistence-layer
|
|
104
|
+
schema changes, validation rules, **Database Indexes & Query Optimization
|
|
105
|
+
table** — MANDATORY if any compound query / multi-column index exists. Pick
|
|
106
|
+
the variant matching `stack.database`: Firestore Composite, Postgres B-tree,
|
|
107
|
+
MongoDB compound, DynamoDB GSI/LSI. See `assets/prd-template.md § 5`.)
|
|
76
108
|
- API contract changes (endpoints, request/response, validation)
|
|
109
|
+
- **Design Reference & Mockup Inventory** (if UI impact ≠ N/A — populate from
|
|
110
|
+
`mockups.*`, `mockup_analysis.*`, `step_3_mode`, and `screens_in_scope[]` in
|
|
111
|
+
the state file. Include the screen inventory table, the component mapping
|
|
112
|
+
table when `features.has_design_system: true`, and the source-files
|
|
113
|
+
traceability list. When `mockups.status: none`, the section is still present
|
|
114
|
+
with the table empty and a note "Design generato in Step 3 — vedi design.html".)
|
|
77
115
|
- UI specifications (if applicable — MUST derive from `## UI Element Inventory` in
|
|
78
|
-
state file; include the full inventory table verbatim, reference `design.html` path
|
|
79
|
-
and map each UI element to
|
|
116
|
+
state file; include the full inventory table verbatim, reference `design.html` path
|
|
117
|
+
OR `mockups/` directory when `step_3_mode: skipped`, and map each UI element to
|
|
118
|
+
the requirement it satisfies. Do NOT duplicate the screen list from the Design
|
|
119
|
+
Reference section above — link to it.)
|
|
80
120
|
- i18n specification (dictionary keys, locale files)
|
|
81
|
-
- Acceptance criteria (grouped by area:
|
|
121
|
+
- Acceptance criteria (grouped by area: one group per persona drawn from
|
|
122
|
+
`identity.audience_segments[]`, plus cross-cutting groups: API, i18n,
|
|
123
|
+
Observability if relevant)
|
|
82
124
|
- Edge cases and failure modes (table format)
|
|
83
125
|
- Out of scope
|
|
84
126
|
- Dependencies (table with type and status)
|
|
@@ -42,9 +42,21 @@ Scan discovery answers and codebase-architect findings for these signals:
|
|
|
42
42
|
Trigger as soon as confidence is HIGH (typically at ~75% comprehension).
|
|
43
43
|
|
|
44
44
|
1. **Identify research topics** from the matching signals. Formulate 1-3
|
|
45
|
-
specific research questions.
|
|
46
|
-
|
|
47
|
-
|
|
45
|
+
specific research questions. Build the stack signature dynamically from
|
|
46
|
+
`baldart.config.yml`:
|
|
47
|
+
|
|
48
|
+
```
|
|
49
|
+
stack_signature = "{{stack.framework}} + {{stack.database}} + {{stack.auth_provider}}"
|
|
50
|
+
# Examples it might resolve to:
|
|
51
|
+
# "nextjs + firestore + firebase-auth"
|
|
52
|
+
# "remix + supabase + supabase-auth"
|
|
53
|
+
# "sveltekit + postgres + lucia"
|
|
54
|
+
# If any segment is empty, omit it from the signature.
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
Examples of research questions (substitute {stack_signature} at runtime):
|
|
58
|
+
- S1: "Best practices for implementing [pattern] on a {stack_signature} stack"
|
|
59
|
+
- S2: "Regulatory requirements for [topic] in {{identity.language country}}, implementation checklist"
|
|
48
60
|
- S3: "Integration patterns for [service], comparison of approaches, gotchas"
|
|
49
61
|
- S4: "UX best practices for [pattern], accessibility considerations, mobile"
|
|
50
62
|
- S6: "Trade-offs of [approach A] vs [approach B] for [use case]"
|
|
@@ -58,13 +70,19 @@ Trigger as soon as confidence is HIGH (typically at ~75% comprehension).
|
|
|
58
70
|
prompt: "Research the following topics for a PRD we're writing for feature
|
|
59
71
|
'<slug>'. Context: <1-2 line feature summary>.
|
|
60
72
|
|
|
73
|
+
Project stack (from baldart.config.yml):
|
|
74
|
+
- framework: {{stack.framework or 'unspecified'}}
|
|
75
|
+
- database: {{stack.database or 'unspecified'}}
|
|
76
|
+
- auth_provider: {{stack.auth_provider or 'unspecified'}}
|
|
77
|
+
- deployment: {{stack.deployment or 'unspecified'}}
|
|
78
|
+
|
|
61
79
|
Research questions:
|
|
62
80
|
1. <question>
|
|
63
81
|
2. <question>
|
|
64
82
|
|
|
65
83
|
For each topic, provide:
|
|
66
84
|
- Summary of best practices (with sources)
|
|
67
|
-
- Recommended approach for
|
|
85
|
+
- Recommended approach for the project stack above
|
|
68
86
|
- Key gotchas or anti-patterns to avoid
|
|
69
87
|
- If applicable: regulatory checklist or compliance requirements
|
|
70
88
|
|
|
@@ -1,8 +1,18 @@
|
|
|
1
1
|
# UI Design Phase (Step 3)
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
## Precondition decision tree
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
Read `mockups.status` and `screens_in_scope[]` from the state file `## UI Design`
|
|
6
|
+
section (populated by Step 1.6) plus the UI impact dimension from the discovery
|
|
7
|
+
checklist. Pick exactly one branch:
|
|
8
|
+
|
|
9
|
+
| Condition | Branch | Action |
|
|
10
|
+
|-----------|--------|--------|
|
|
11
|
+
| UI impact = N/A | **Skip totale** | Mark task 2 `completed` ("Skipped — no UI"). `step_3_mode: skipped`. Proceed to PRD Writing Phase. |
|
|
12
|
+
| `mockups.status: none` AND UI impact ≠ N/A | **Full** | Run the standard pipeline 3a → 3b → 3c → 3d as before. `step_3_mode: full`. |
|
|
13
|
+
| `mockups.status` ∈ {`provided`, `partial`} AND UI impact ≠ N/A | **Hybrid** | Per-screen routing (see § Hybrid mode below). `step_3_mode: hybrid` (or `skipped` if every screen is covered AND no `mockup_analysis.design_system_alignment.violations`). |
|
|
14
|
+
|
|
15
|
+
Mark task 2 as `in_progress` for the Full and Hybrid branches.
|
|
6
16
|
|
|
7
17
|
## Delegation to `ui-design` Skill
|
|
8
18
|
|
|
@@ -50,7 +60,7 @@ MISSING — no match found:
|
|
|
50
60
|
|
|
51
61
|
This prevents designing new components when 450+ reusable ones already exist.
|
|
52
62
|
|
|
53
|
-
### Gates (
|
|
63
|
+
### Gates (Full branch)
|
|
54
64
|
|
|
55
65
|
- **After Step 3b:** all 3 polished options open in Safari AND screenshots shown inline.
|
|
56
66
|
**STOP.** Wait for user to choose.
|
|
@@ -59,3 +69,105 @@ This prevents designing new components when 450+ reusable ones already exist.
|
|
|
59
69
|
is populated in the state file with at least 3 elements.
|
|
60
70
|
|
|
61
71
|
Mark task 2 as `completed`. Update state file status to `specs-confirmed`.
|
|
72
|
+
|
|
73
|
+
---
|
|
74
|
+
|
|
75
|
+
## Hybrid mode (Step 1.6 produced mockups)
|
|
76
|
+
|
|
77
|
+
Triggered when `mockups.status` ∈ {`provided`, `partial`}. The principle: the user
|
|
78
|
+
has already done the design work for some screens — don't redo it. Validate, align
|
|
79
|
+
to the design system, approve, and inventory. Generate ONLY the screens not covered.
|
|
80
|
+
|
|
81
|
+
### Build the per-screen routing table
|
|
82
|
+
|
|
83
|
+
1. Construct `screens_in_scope[]` by merging:
|
|
84
|
+
- User Stories from the state file (one row per US that implies a screen).
|
|
85
|
+
- ISA `NAVIGATION` and `DASHBOARD` touchpoints that imply landing screens.
|
|
86
|
+
- The `mockup_analysis.screens[]` list itself (in case the mockups include
|
|
87
|
+
screens the user stories didn't make explicit).
|
|
88
|
+
2. For each entry, set `covered_by_mockups: true` iff the screen matches a
|
|
89
|
+
`mockup_analysis.screens[].name` (case-insensitive substring match is fine —
|
|
90
|
+
when ambiguous, ASK the user "questa schermata `<X>` corrisponde al mockup
|
|
91
|
+
`<Y>`?" and STOP).
|
|
92
|
+
3. Persist `screens_in_scope[]` in the state file `## UI Design` section.
|
|
93
|
+
|
|
94
|
+
### Per-screen execution
|
|
95
|
+
|
|
96
|
+
| `covered_by_mockups` | What runs | Notes |
|
|
97
|
+
|----------------------|-----------|-------|
|
|
98
|
+
| `true` | Component Registry Lookup (adapted) + 3c (approval gate) + 3d (save & inventory) | SKIP 3a (options) and 3b (generation). Use the provided mockup as the canonical reference. |
|
|
99
|
+
| `false` | Subskill `ui-design` 3a + 3b SCOPED TO THIS SCREEN, then 3c + 3d | Pass the screen name + relevant discovery answers + context-primer output. Mockups for OTHER screens already approved are passed as "existing design language to match" so the new screen looks consistent. |
|
|
100
|
+
|
|
101
|
+
### Step 3 sub-flow in Hybrid mode
|
|
102
|
+
|
|
103
|
+
1. **Component Registry Lookup (all screens, before any generation).**
|
|
104
|
+
For each screen — covered OR new — match `mockup_analysis.screens[].components[]`
|
|
105
|
+
(covered) or the inferred component list (new) against
|
|
106
|
+
`${paths.references_dir}/component-registry.md` and, when
|
|
107
|
+
`features.has_design_system: true`, against `${paths.design_system}/INDEX.md`.
|
|
108
|
+
- For covered screens: any component used in a mockup but NOT in the registry
|
|
109
|
+
becomes either (a) a REUSE recommendation if a close match exists, or (b) a
|
|
110
|
+
candidate new primitive — flag in `mockup_analysis.design_system_alignment`.
|
|
111
|
+
- For new screens: passed to `ui-design` as the REUSE list (prevents the
|
|
112
|
+
subskill from inventing new components).
|
|
113
|
+
2. **Generation pass (new screens only).**
|
|
114
|
+
For each new screen, invoke `Skill(ui-design)` with payload:
|
|
115
|
+
```
|
|
116
|
+
feature_slug: <slug>
|
|
117
|
+
scope: single-screen
|
|
118
|
+
screen_name: <X>
|
|
119
|
+
discovery_excerpt: <answers relevant to this screen>
|
|
120
|
+
reuse_components: <list from registry lookup>
|
|
121
|
+
design_language_anchor: mockups/<existing-mockup-1>.png, mockups/<existing-mockup-2>.png
|
|
122
|
+
```
|
|
123
|
+
The subskill produces 3 options for that one screen (its standard 3b output).
|
|
124
|
+
Open in Safari, **STOP**, wait for user to choose.
|
|
125
|
+
3. **Approval gate (all screens, 3c).**
|
|
126
|
+
Present in ONE message:
|
|
127
|
+
- Thumbnail + path for each `covered_by_mockups: true` screen.
|
|
128
|
+
- The user-chosen option for each `generated_in_step_3b: true` screen.
|
|
129
|
+
- All `design_system_alignment.violations[]` consolidated into a "Issues da
|
|
130
|
+
risolvere prima di Step 4" list with the proposed token/component swap.
|
|
131
|
+
Ask explicit confirmation ("confermo", "va bene", "ok"). **STOP.**
|
|
132
|
+
4. **Save & Inventory (all screens, 3d).**
|
|
133
|
+
- For covered screens: copy `mockups/<file>.png` references into the unified
|
|
134
|
+
UI Element Inventory; no `design.html` regeneration needed unless the subskill
|
|
135
|
+
also ran. If at least one new screen was generated, the merged `design.html`
|
|
136
|
+
includes both the new mockups and embeds/links to the existing ones.
|
|
137
|
+
- For all-covered runs (`generated_in_step_3b: false` everywhere): set
|
|
138
|
+
`design.html_path: n/a (mockup-only)` in the state file; the PRD will link
|
|
139
|
+
directly to `${paths.prd_dir}/<slug>/mockups/`.
|
|
140
|
+
- Update `## UI Element Inventory` in the state file with at least one row per
|
|
141
|
+
covered screen + per generated screen.
|
|
142
|
+
|
|
143
|
+
### Hybrid gates
|
|
144
|
+
|
|
145
|
+
- **After per-screen 3b (only if any new screen exists):** all 3 polished options
|
|
146
|
+
per new screen open in Safari AND screenshots shown inline. **STOP.** Wait for
|
|
147
|
+
user choice.
|
|
148
|
+
- **After 3c (approval):** explicit user approval AND every entry in
|
|
149
|
+
`design_system_alignment.violations[]` is either resolved (token/component
|
|
150
|
+
swapped in the inventory) or explicitly waived by the user (logged as such).
|
|
151
|
+
- **After 3d:** UI Element Inventory populated with at least one row per screen in
|
|
152
|
+
`screens_in_scope[]`. `design.html_path` set OR `mockup-only` flag recorded.
|
|
153
|
+
|
|
154
|
+
Mark task 2 as `completed`. Update state file status to `specs-confirmed`.
|
|
155
|
+
|
|
156
|
+
### Canonical example
|
|
157
|
+
|
|
158
|
+
Feature with 5 screens (`Lista ordini`, `Dettaglio ordine`, `Filtri`, `Onboarding`,
|
|
159
|
+
`Stato pagamento`). Mockups provided for 3 of them.
|
|
160
|
+
|
|
161
|
+
```
|
|
162
|
+
screens_in_scope:
|
|
163
|
+
- { name: "Lista ordini", covered_by_mockups: true, generated_in_step_3b: false }
|
|
164
|
+
- { name: "Dettaglio ordine", covered_by_mockups: true, generated_in_step_3b: false }
|
|
165
|
+
- { name: "Filtri", covered_by_mockups: true, generated_in_step_3b: false }
|
|
166
|
+
- { name: "Onboarding", covered_by_mockups: false, generated_in_step_3b: true }
|
|
167
|
+
- { name: "Stato pagamento", covered_by_mockups: false, generated_in_step_3b: true }
|
|
168
|
+
```
|
|
169
|
+
|
|
170
|
+
Result: `ui-design` subskill runs TWICE (one invocation per new screen, each
|
|
171
|
+
producing 3 options). The 3 covered screens skip 3a/3b entirely. The final approval
|
|
172
|
+
gate presents all 5 screens together. `step_3_mode: hybrid`. The PRD links to
|
|
173
|
+
`mockups/` for the 3 covered + `design.html` for the 2 new.
|
|
@@ -16,8 +16,8 @@ Mark task 5 as `in_progress`.
|
|
|
16
16
|
definition (type, nullable, default, indexing notes).
|
|
17
17
|
c. For cards with `estimated_complexity: LOW`:
|
|
18
18
|
- Verify only that `data_fields` has `ts_verified: true` or `status: new`. No grep needed.
|
|
19
|
-
d. If card has `firestore_indexes` but NO `data_fields`: log warning —
|
|
20
|
-
"card touches
|
|
19
|
+
d. If card has `db_indexes` (or legacy `firestore_indexes`) but NO `data_fields`: log warning —
|
|
20
|
+
"card touches the persistence layer (db_indexes present) but missing data_fields block."
|
|
21
21
|
|
|
22
22
|
**Gate**: no field with `status: existing | modified` and `ts_verified: false` can proceed.
|
|
23
23
|
|
|
@@ -131,9 +131,49 @@ stack:
|
|
|
131
131
|
forbidden: []
|
|
132
132
|
testing:
|
|
133
133
|
e2e: "playwright" # or "cypress", or ""
|
|
134
|
+
|
|
135
|
+
# Stack-cardinal scalars (since v3.15.0). Used by /prd, coder,
|
|
136
|
+
# api-perf-cost-auditor, /new, code-reviewer, security-reviewer to branch
|
|
137
|
+
# vocabulary, gate sections, anti-pattern checklists, deploy commands.
|
|
138
|
+
database: "firestore" # firestore|supabase|postgres|mysql|mongodb|dynamodb|sqlite|none|""
|
|
139
|
+
auth_provider: "firebase-auth" # firebase-auth|supabase-auth|clerk|auth0|cognito|nextauth|lucia|custom|none|""
|
|
140
|
+
framework: "nextjs" # nextjs|remix|sveltekit|astro|nuxt|rails|django|fastapi|express|none|""
|
|
141
|
+
deployment: "vercel" # vercel|firebase|aws|gcp|cloudflare|render|fly|self-hosted|none|""
|
|
134
142
|
```
|
|
135
143
|
|
|
136
|
-
Skills propose only `canonical` libraries and refuse `forbidden` ones. Empty
|
|
144
|
+
Skills propose only `canonical` libraries and refuse `forbidden` ones. Empty
|
|
145
|
+
`canonical` = ask the user before proposing a library.
|
|
146
|
+
|
|
147
|
+
**Stack-cardinal scalars (v3.15.0+).** The four scalar keys (`database`,
|
|
148
|
+
`auth_provider`, `framework`, `deployment`) drive stack-aware branching across
|
|
149
|
+
the skill/agent set:
|
|
150
|
+
|
|
151
|
+
- `/prd` Schema Verification Gate picks the registry path matching
|
|
152
|
+
`stack.database` (Firestore field-registry, Prisma schema, SQL migrations,
|
|
153
|
+
Mongo validator).
|
|
154
|
+
- `/prd` Section 5 of the PRD template renders the index variant matching
|
|
155
|
+
`stack.database` (Firestore composite, SQL B-tree, Mongo compound,
|
|
156
|
+
DynamoDB GSI/LSI).
|
|
157
|
+
- `api-perf-gate` keyword scan adds DB-specific anti-patterns only when the
|
|
158
|
+
matching `stack.database` is set; universal patterns always run.
|
|
159
|
+
- `coder.md` Database Index Invariant ships the right migration kind for
|
|
160
|
+
the resolved `stack.database`.
|
|
161
|
+
- `api-perf-cost-auditor` reads the four scalars at session start and cites
|
|
162
|
+
them in every audit header, so the user knows which variant applied.
|
|
163
|
+
- `/new` Production Readiness Checklist picks deploy commands matching
|
|
164
|
+
`stack.deployment` + `stack.database` (firebase deploy, vercel deploy,
|
|
165
|
+
supabase db push, CDK/Terraform apply).
|
|
166
|
+
- `security-reviewer` evaluates access rules per `stack.database`
|
|
167
|
+
(Firestore rules, Supabase RLS, Mongo validators, DynamoDB IAM,
|
|
168
|
+
Postgres RLS+GRANT).
|
|
169
|
+
- `bug/logging-patterns.md` picks the framework-native debug switches
|
|
170
|
+
matching `stack.framework`.
|
|
171
|
+
|
|
172
|
+
**Always-ask contract on empty.** When a scalar is `""` and a skill needs it,
|
|
173
|
+
the skill asks the user once and suggests running `npx baldart configure` to
|
|
174
|
+
persist the answer. Skills NEVER assume a default — empty means "ask".
|
|
175
|
+
`baldart update` flags newly-introduced scalar keys via the schema-drift
|
|
176
|
+
detector and auto-offers `baldart configure`.
|
|
137
177
|
|
|
138
178
|
### 4.5 `features` — explicit booleans gating BLOCKING reads
|
|
139
179
|
|