@atlashub/smartstack-cli 4.74.0 → 4.76.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.
Files changed (121) hide show
  1. package/dist/index.js +152 -31
  2. package/dist/index.js.map +1 -1
  3. package/dist/mcp-entry.mjs +14 -3
  4. package/dist/mcp-entry.mjs.map +1 -1
  5. package/package.json +1 -1
  6. package/templates/agents/ba-reader.md +17 -15
  7. package/templates/agents/ba-writer.md +49 -51
  8. package/templates/skills/apex/SKILL.md +2 -2
  9. package/templates/skills/apex/_shared.md +1 -1
  10. package/templates/skills/apex/references/checks/backend-checks.sh +21 -7
  11. package/templates/skills/apex/references/checks/frontend-checks.sh +26 -0
  12. package/templates/skills/apex/references/checks/infrastructure-checks.sh +47 -10
  13. package/templates/skills/apex/references/checks/seed-checks.sh +47 -7
  14. package/templates/skills/apex/references/core-seed-data.md +20 -18
  15. package/templates/skills/apex/references/frontend-route-wiring-app-tsx.md +3 -0
  16. package/templates/skills/apex/references/post-checks.md +23 -3
  17. package/templates/skills/apex/references/smartstack-api.md +4 -4
  18. package/templates/skills/apex/references/smartstack-frontend.md +54 -8
  19. package/templates/skills/apex/references/smartstack-layers.md +6 -6
  20. package/templates/skills/apex/steps/step-00-init.md +75 -1
  21. package/templates/skills/apex/steps/step-03-execute.md +16 -4
  22. package/templates/skills/apex/steps/step-03b-layer1-seed.md +65 -6
  23. package/templates/skills/apex/steps/step-03c-layer2-backend.md +50 -5
  24. package/templates/skills/apex/steps/step-03d-layer3-frontend.md +226 -4
  25. package/templates/skills/apex/steps/step-04-examine.md +163 -0
  26. package/templates/skills/apex-verify/SKILL.md +110 -0
  27. package/templates/skills/apex-verify/references/audit-rules.md +50 -0
  28. package/templates/skills/apex-verify/steps/step-00-init.md +119 -0
  29. package/templates/skills/apex-verify/steps/step-01-nav-audit.md +92 -0
  30. package/templates/skills/apex-verify/steps/step-02-crud-audit.md +127 -0
  31. package/templates/skills/apex-verify/steps/step-03-perm-audit.md +119 -0
  32. package/templates/skills/apex-verify/steps/step-04-route-audit.md +98 -0
  33. package/templates/skills/apex-verify/steps/step-05-report.md +110 -0
  34. package/templates/skills/application/references/frontend-route-wiring-app-tsx.md +3 -0
  35. package/templates/skills/application/templates-frontend.md +2 -2
  36. package/templates/skills/business-analyse/SKILL.md +17 -3
  37. package/templates/skills/business-analyse/_shared.md +64 -0
  38. package/templates/skills/business-analyse/patterns/suggestion-catalog.md +34 -26
  39. package/templates/skills/business-analyse/questionnaire/01-context.md +13 -9
  40. package/templates/skills/business-analyse/questionnaire/02-stakeholders-scope.md +20 -27
  41. package/templates/skills/business-analyse/questionnaire.md +86 -9
  42. package/templates/skills/business-analyse/references/03-json-schemas.md +221 -0
  43. package/templates/skills/business-analyse/references/03-post-check-validation.md +208 -0
  44. package/templates/skills/business-analyse/references/03-smartstack-entity-guards.md +32 -0
  45. package/templates/skills/business-analyse/references/04-cross-module-validation.md +95 -0
  46. package/templates/skills/business-analyse/references/04-file-allocation.md +162 -0
  47. package/templates/skills/business-analyse/references/04-naming-audit-checks.md +174 -0
  48. package/templates/skills/business-analyse/references/04-semantic-validation-matrix.md +118 -0
  49. package/templates/skills/business-analyse/references/canonical-json-formats.md +7 -3
  50. package/templates/skills/business-analyse/references/domain-research-playbook.md +234 -0
  51. package/templates/skills/business-analyse/references/entity-sourcing-presentation.md +166 -0
  52. package/templates/skills/business-analyse/references/init-resume-logic.md +70 -0
  53. package/templates/skills/business-analyse/references/module-completeness-challenge.md +174 -0
  54. package/templates/skills/business-analyse/references/multi-app-detection.md +149 -0
  55. package/templates/skills/business-analyse/references/portal-classification.md +52 -0
  56. package/templates/skills/business-analyse/references/robustness-checks.md +1 -1
  57. package/templates/skills/business-analyse/references/validation-checklist.md +35 -6
  58. package/templates/skills/business-analyse/schemas/sections/analysis-schema.json +50 -6
  59. package/templates/skills/business-analyse/steps/step-00-init.md +22 -190
  60. package/templates/skills/business-analyse/steps/step-01-cadrage.md +365 -269
  61. package/templates/skills/business-analyse/steps/step-02-structure.md +98 -20
  62. package/templates/skills/business-analyse/steps/step-03-specify.md +810 -229
  63. package/templates/skills/business-analyse/steps/step-04-consolidate.md +509 -278
  64. package/templates/skills/business-analyse-design/SKILL.md +10 -0
  65. package/templates/skills/business-analyse-design/references/screens-post-check.md +221 -0
  66. package/templates/skills/business-analyse-design/references/screens-type-mapping.md +138 -0
  67. package/templates/skills/business-analyse-design/references/smartcomponents-templates.md +225 -0
  68. package/templates/skills/{business-analyse → business-analyse-design}/references/spec-auto-inference.md +117 -117
  69. package/templates/skills/business-analyse-design/steps/step-01-screens.md +36 -162
  70. package/templates/skills/business-analyse-design/steps/step-02-wireframes.md +8 -7
  71. package/templates/skills/business-analyse-design/steps/step-03-navigation.md +89 -42
  72. package/templates/skills/business-analyse-develop/references/compact-loop.md +9 -0
  73. package/templates/skills/business-analyse-develop/references/handoff-quality-gate.md +132 -0
  74. package/templates/skills/business-analyse-develop/references/prd-v3-transformation.md +326 -0
  75. package/templates/skills/business-analyse-develop/references/report-reconciliation.md +140 -0
  76. package/templates/skills/business-analyse-develop/references/report-template.md +142 -0
  77. package/templates/skills/business-analyse-develop/steps/step-01-task.md +5 -177
  78. package/templates/skills/business-analyse-develop/steps/step-02-execute.md +17 -4
  79. package/templates/skills/business-analyse-develop/steps/step-03-commit.md +6 -2
  80. package/templates/skills/business-analyse-develop/steps/step-04-check.md +6 -0
  81. package/templates/skills/business-analyse-develop/steps/step-05-report.md +3 -269
  82. package/templates/skills/business-analyse-handoff/SKILL.md +10 -0
  83. package/templates/skills/business-analyse-handoff/references/agent-handoff-transform-prompt.md +211 -0
  84. package/templates/skills/business-analyse-handoff/references/context-isolation-pattern.md +47 -0
  85. package/templates/skills/business-analyse-handoff/references/handoff-file-inventory.md +49 -0
  86. package/templates/skills/business-analyse-handoff/references/handoff-global-validation.md +142 -0
  87. package/templates/skills/business-analyse-handoff/references/prd-validation-checks.md +125 -0
  88. package/templates/skills/business-analyse-handoff/references/project-index-update.md +98 -0
  89. package/templates/skills/business-analyse-handoff/steps/step-01-transform.md +9 -160
  90. package/templates/skills/business-analyse-handoff/steps/step-02-export.md +10 -99
  91. package/templates/skills/business-analyse-html/SKILL.md +10 -0
  92. package/templates/skills/business-analyse-html/html/ba-interactive.html +504 -97
  93. package/templates/skills/business-analyse-html/html/src/scripts/01-data-init.js +79 -2
  94. package/templates/skills/business-analyse-html/html/src/scripts/02-navigation.js +6 -46
  95. package/templates/skills/business-analyse-html/html/src/scripts/05-render-specs.js +80 -11
  96. package/templates/skills/business-analyse-html/html/src/scripts/06-render-consolidation.js +2 -2
  97. package/templates/skills/business-analyse-html/html/src/scripts/06-render-mockups.js +94 -36
  98. package/templates/skills/business-analyse-html/html/src/scripts/12-render-diagrams.js +162 -0
  99. package/templates/skills/business-analyse-html/html/src/styles/10-diagrams.css +73 -0
  100. package/templates/skills/business-analyse-html/html/src/template.html +2 -0
  101. package/templates/skills/business-analyse-html/references/02-embedded-artifacts-building.md +144 -0
  102. package/templates/skills/business-analyse-html/references/02-feature-data-building.md +143 -0
  103. package/templates/skills/business-analyse-html/references/02-mapping-tables.md +442 -0
  104. package/templates/skills/business-analyse-html/references/02-normalization-helpers.md +139 -0
  105. package/templates/skills/business-analyse-html/references/02-screen-format-detection.md +283 -0
  106. package/templates/skills/business-analyse-html/references/02-self-check-validation.md +199 -0
  107. package/templates/skills/business-analyse-html/references/data-build.md +24 -1
  108. package/templates/skills/business-analyse-html/references/data-mapping.md +119 -17
  109. package/templates/skills/business-analyse-html/steps/step-02-build-data.md +18 -555
  110. package/templates/skills/business-analyse-html/steps/step-04-verify.md +92 -3
  111. package/templates/skills/business-analyse-quick/SKILL.md +807 -0
  112. package/templates/skills/{sketch → business-analyse-quick}/references/domain-heuristics.md +59 -3
  113. package/templates/skills/business-analyse-quick/references/prd-schema.md +268 -0
  114. package/templates/skills/business-analyse-review/SKILL.md +10 -0
  115. package/templates/skills/business-analyse-review/references/review-data-mapping.md +6 -0
  116. package/templates/skills/business-analyse-status/SKILL.md +8 -0
  117. package/templates/skills/dev-start/SKILL.md +143 -307
  118. package/templates/skills/efcore/SKILL.md +13 -0
  119. package/templates/skills/sketch/SKILL.md +15 -153
  120. package/templates/skills/ui-components/SKILL.md +1 -1
  121. package/templates/skills/ui-components/patterns/data-table.md +1 -1
@@ -0,0 +1,283 @@
1
+ ---
2
+ name: 02-screen-format-detection
3
+ description: Detection and normalization logic for screens.json format variants (A, B-CANONICAL, B-LEGACY)
4
+ ---
5
+
6
+ # Screen Format Detection
7
+
8
+ The `screens.json` file can be produced in multiple formats depending on the BA workflow step that generated it. This reference documents the detection logic and normalization for each format variant.
9
+
10
+ ## Format Overview
11
+
12
+ | Format | Structure | Source | Key Fields |
13
+ |--------|-----------|--------|-----------|
14
+ | **A** | `screens[]` (flat) | ba-003 (original BA output) | `screen`, `section`, `columns[]`, `filters[]`, `tabs[]`, `actions[]`, `kpis[]`, `charts[]` |
15
+ | **B-CANONICAL** | `sections[].resources[]` | ba-005+ (design output) | `sectionCode`, `sectionLabel`, `resources[]` with nested structure |
16
+ | **B-LEGACY** | `sections[]` (flat within section) | ba-004 (intermediate step) | `sections[]` with data directly on section, no resources[] nesting |
17
+
18
+ ## Format A: Flat screens[] Array
19
+
20
+ **Detection:** `mod.screens?.screens` array exists and has length > 0.
21
+
22
+ **Schema:**
23
+ ```javascript
24
+ screens: [
25
+ {
26
+ screen: "ScreenName",
27
+ section: "SectionCode",
28
+ sectionLabel: "Section Label",
29
+ description: "...",
30
+ sectionDescription: "...",
31
+ componentType: "SmartTable|SmartForm|Dashboard|Kanban",
32
+ columns: [...], // for table components
33
+ filters: [...], // simple filters
34
+ tabs: [...], // form tabs
35
+ actions: [...], // action buttons
36
+ kpis: [...], // dashboard KPIs
37
+ charts: [...], // dashboard charts
38
+ options: [...], // component options
39
+ permission: "...", // ACL permission
40
+ mockup: "...", // wireframe content
41
+ mockupFormat: "..." // wireframe format
42
+ }
43
+ ]
44
+ ```
45
+
46
+ **Normalization:**
47
+
48
+ Group flat screens by section, then map each to a `{sectionCode, sectionLabel, resources[]}` structure:
49
+
50
+ ```javascript
51
+ if (flatScr.length > 0) {
52
+ // FORMAT A: flat screens[] array (ba-003 style)
53
+ const bySec = {};
54
+ flatScr.forEach(s => {
55
+ const sec = s.section || "default";
56
+ if (!bySec[sec]) bySec[sec] = {
57
+ sectionCode: sec,
58
+ sectionLabel: s.sectionLabel || s.sectionDescription || sec,
59
+ resources: []
60
+ };
61
+ bySec[sec].resources.push({
62
+ code: s.screen || s.name || "",
63
+ label: s.sectionLabel || s.description || s.screen || "",
64
+ type: s.componentType || "unknown",
65
+ columns: (s.columns || []).map(normalizeColumn),
66
+ filters: (s.filters || []).map(normalizeFilter),
67
+ fields: [],
68
+ tabs: (s.tabs || []).map(t => ({
69
+ label: t.label || t.tabLabel || t.code || "",
70
+ fields: (t.fields || []).map(normalizeField)
71
+ })),
72
+ actions: (s.actions || []).map(normalizeAction),
73
+ kpis: (s.kpis || []).map(normalizeKpi),
74
+ charts: (s.charts || []).map(normalizeChart),
75
+ options: s.options || [],
76
+ permission: s.permission || "",
77
+ notes: s.description || s.sectionDescription || ""
78
+ });
79
+ });
80
+ screens = Object.values(bySec);
81
+ }
82
+ ```
83
+
84
+ **Output:** Array of `{sectionCode, sectionLabel, resources[]}` objects (equivalent to B-CANONICAL).
85
+
86
+ ## Format B: Detect Sub-variant (B-CANONICAL vs B-LEGACY)
87
+
88
+ **Detection:** `mod.screens?.sections` array exists and has length > 0.
89
+
90
+ **Decision point:** Check if any section contains `resources[]`:
91
+
92
+ ```javascript
93
+ const hasNestedResources = sectionScr.some(sec => (sec.resources || []).length > 0);
94
+ ```
95
+
96
+ ### Format B-CANONICAL: sections[] with resources[]
97
+
98
+ **Schema:**
99
+ ```javascript
100
+ sections: [
101
+ {
102
+ sectionCode: "SectionCode",
103
+ sectionLabel: "Section Label",
104
+ displayName: "...",
105
+ label: "...",
106
+ id: "...",
107
+ code: "...",
108
+ resources: [
109
+ {
110
+ code: "ResourceCode",
111
+ id: "...",
112
+ label: "Resource Label",
113
+ displayName: "...",
114
+ type: "SmartTable|SmartForm|Dashboard|Kanban",
115
+ componentType: "...",
116
+ layout: "...",
117
+ columns: [...], // normalized column definitions
118
+ filters: [...], // SmartFilter-style filters
119
+ tabs: [...], // form tabs
120
+ actions: [...], // action buttons
121
+ kpis: [...], // KPIs
122
+ charts: [...], // chart definitions
123
+ options: [...], // component options
124
+ permission: "...", // ACL permission
125
+ notes: "...", // description
126
+ description: "..."
127
+ }
128
+ ]
129
+ }
130
+ ]
131
+ ```
132
+
133
+ **Normalization:**
134
+
135
+ ```javascript
136
+ if (hasNestedResources) {
137
+ // FORMAT B-CANONICAL: sections[] with resources[] (ba-005+ style)
138
+ screens = sectionScr.map(sec => ({
139
+ sectionCode: sec.sectionCode || sec.id || sec.code || "",
140
+ sectionLabel: sec.sectionLabel || sec.displayName || sec.label || sec.sectionCode || "",
141
+ resources: (sec.resources || []).map(res => ({
142
+ code: res.code || res.id || "",
143
+ label: res.label || res.displayName || res.code || "",
144
+ type: res.type || res.componentType || res.layout || "unknown",
145
+ columns: (res.columns || []).map(normalizeColumn),
146
+ filters: res.type === 'SmartFilter'
147
+ ? (res.filters || []).map(normalizeSmartFilterField)
148
+ : (res.filters || []).map(normalizeFilter),
149
+ fields: [],
150
+ tabs: (res.tabs || []).map(t => ({
151
+ label: t.label || t.displayName || t.code || t.id || "",
152
+ fields: (t.fields || []).map(normalizeField)
153
+ })),
154
+ actions: (res.actions || []).map(normalizeAction),
155
+ kpis: (res.kpis || []).map(normalizeKpi),
156
+ charts: (res.charts || []).map(normalizeChart),
157
+ options: res.options || [],
158
+ permission: res.permission || "",
159
+ notes: res.notes || res.description || ""
160
+ }))
161
+ }));
162
+ }
163
+ ```
164
+
165
+ **Key feature:** SmartFilter type detected and uses rich filter normalization (`normalizeSmartFilterField`) instead of simple label extraction.
166
+
167
+ ### Format B-LEGACY: sections[] without resources[]
168
+
169
+ **Schema:**
170
+ ```javascript
171
+ sections: [
172
+ {
173
+ id: "SectionId",
174
+ code: "SectionCode",
175
+ sectionCode: "...",
176
+ displayName: "Section Label",
177
+ label: "...",
178
+ layout: "SmartTable|SmartForm|Dashboard",
179
+ componentType: "...",
180
+ columns: [...], // data directly on section
181
+ filters: [...], // simple filters
182
+ tabs: [...], // form tabs
183
+ actions: [...], // action buttons
184
+ kpis: [...], // KPIs
185
+ charts: [...], // chart definitions
186
+ options: [...], // options
187
+ permissions: {view: "..."} or permission: "...",
188
+ description: "...",
189
+ // NO resources[] nesting
190
+ }
191
+ ]
192
+ ```
193
+
194
+ **Normalization:**
195
+
196
+ Group sections by ID/code, then map into `{sectionCode, sectionLabel, resources[]}` structure:
197
+
198
+ ```javascript
199
+ } else {
200
+ // FORMAT B-LEGACY: sections[] without resources[] (ba-004 style)
201
+ const bySec = {};
202
+ sectionScr.forEach(sec => {
203
+ const secId = sec.id || sec.code || sec.sectionCode || "";
204
+ const secLabel = sec.displayName || sec.label || sec.sectionLabel || secId;
205
+ const componentType = sec.layout || sec.componentType || "unknown";
206
+ if (!bySec[secId]) bySec[secId] = {
207
+ sectionCode: secId,
208
+ sectionLabel: secLabel,
209
+ resources: []
210
+ };
211
+ bySec[secId].resources.push({
212
+ code: secId,
213
+ label: secLabel,
214
+ type: componentType,
215
+ columns: (sec.columns || []).map(normalizeColumn),
216
+ filters: (sec.filters || []).map(normalizeFilter),
217
+ fields: [],
218
+ tabs: (sec.tabs || []).map(t => ({
219
+ label: t.displayName || t.label || t.code || t.id || "",
220
+ fields: (t.fields || []).map(normalizeField)
221
+ })),
222
+ actions: (sec.actions || []).map(normalizeAction),
223
+ kpis: (sec.kpis || []).map(normalizeKpi),
224
+ charts: (sec.charts || []).map(normalizeChart),
225
+ options: sec.options || [],
226
+ permission: (typeof sec.permissions === 'object' ? sec.permissions?.view : sec.permission) || "",
227
+ notes: sec.description || ""
228
+ });
229
+ });
230
+ screens = Object.values(bySec);
231
+ }
232
+ ```
233
+
234
+ **Key differences:**
235
+ - Sections have data directly (no `resources[]` nesting)
236
+ - Permissions may be object `{view: "..."}` or simple string
237
+ - One resource per section (grouped by ID)
238
+
239
+ ## Output Normalization
240
+
241
+ All three formats normalize to a **canonical output structure**:
242
+
243
+ ```javascript
244
+ screens: [
245
+ {
246
+ sectionCode: "string",
247
+ sectionLabel: "string",
248
+ resources: [
249
+ {
250
+ code: "string",
251
+ label: "string",
252
+ type: "string",
253
+ columns: [...], // normalized via normalizeColumn()
254
+ filters: [...], // normalized via normalizeFilter() or normalizeSmartFilterField()
255
+ fields: [],
256
+ tabs: [...], // with normalized fields
257
+ actions: [...], // normalized via normalizeAction()
258
+ kpis: [...], // normalized via normalizeKpi()
259
+ charts: [...], // normalized via normalizeChart()
260
+ options: [...],
261
+ permission: "string",
262
+ notes: "string"
263
+ }
264
+ ]
265
+ }
266
+ ]
267
+ ```
268
+
269
+ This canonical form is then used to populate `moduleSpecs[moduleCode].screens` and render in the HTML viewer.
270
+
271
+ ## Detection Flow
272
+
273
+ ```
274
+ mod.screens exists?
275
+ ├─ YES: Do we have mod.screens.screens[] with length > 0?
276
+ │ └─ YES: Format A (flat) → normalize by section → canonical
277
+ │ └─ NO: Continue to B detection
278
+ ├─ Do we have mod.screens.sections[] with length > 0?
279
+ │ └─ YES: Check hasNestedResources (any section.resources[] exists?)
280
+ │ ├─ YES: Format B-CANONICAL → normalize permissions → canonical
281
+ │ └─ NO: Format B-LEGACY → group by ID → canonical
282
+ └─ NO: screens = [] (empty)
283
+ ```
@@ -0,0 +1,199 @@
1
+ ---
2
+ name: 02-self-check-validation
3
+ description: Post-build self-check validation to detect data loss when building FEATURE_DATA
4
+ ---
5
+
6
+ # Self-Check Validation
7
+
8
+ After building `FEATURE_DATA.moduleSpecs` and enriching `anticipatedSections` with section-level use cases and business rules, run this mandatory self-check to detect data loss between the source files and the built object.
9
+
10
+ ## Purpose
11
+
12
+ Ensures that no useCases, businessRules, entities, or screens were lost during the normalization and mapping process. Data loss indicates a bug in the build logic (e.g., missing array handling, failed normalization, wrong field names).
13
+
14
+ ## Execution Timing
15
+
16
+ **AFTER:**
17
+ 1. All `moduleSpecs[moduleCode]` entries are populated
18
+ 2. `anticipatedSections` are enriched with section-level UC/BR
19
+
20
+ **BEFORE:**
21
+ - Proceeding to step-03 (HTML rendering)
22
+
23
+ ## Self-Check Code
24
+
25
+ ```javascript
26
+ // SELF-CHECK: compare source file counts vs FEATURE_DATA counts
27
+ const errors = [];
28
+ FEATURE_DATA.modules.forEach(m => {
29
+ const spec = FEATURE_DATA.moduleSpecs[m.code];
30
+ const source = collected_data.modules[m.code];
31
+ if (!spec) { errors.push(`MISSING moduleSpecs[${m.code}]`); return; }
32
+
33
+ // Check useCases (handle both key conventions)
34
+ const srcUC = (source?.usecases?.useCases || source?.usecases?.usecases || []).length;
35
+ const bltUC = (spec.useCases || []).length;
36
+ if (srcUC > 0 && bltUC === 0)
37
+ errors.push(`${m.code}: useCases EMPTY but source has ${srcUC}`);
38
+
39
+ // Check businessRules (handle both key conventions)
40
+ const srcBR = (source?.rules?.rules || source?.rules?.businessRules || []).length;
41
+ const bltBR = (spec.businessRules || []).length;
42
+ if (srcBR > 0 && bltBR === 0)
43
+ errors.push(`${m.code}: businessRules EMPTY but source has ${srcBR}`);
44
+
45
+ // Check entities
46
+ const srcEnt = (source?.entities?.entities || []).length;
47
+ const bltEnt = (spec.entities || []).length;
48
+ if (srcEnt > 0 && bltEnt === 0)
49
+ errors.push(`${m.code}: entities EMPTY but source has ${srcEnt}`);
50
+
51
+ // Check screens (handle both formats: screens[] and sections[])
52
+ const srcScreens = (source?.screens?.screens || source?.screens?.sections || []).length;
53
+ const bltScreenResources = (spec.screens || []).reduce(
54
+ (acc, s) => acc + (s.resources || []).length, 0);
55
+ if (srcScreens > 0 && bltScreenResources === 0)
56
+ errors.push(`${m.code}: screens EMPTY (0 resources) but source has ${srcScreens} screens/sections`);
57
+
58
+ // Check serialization: [object Object] in useCases steps = BUG
59
+ (spec.useCases || []).forEach(uc => {
60
+ if (uc.steps && uc.steps.includes("[object Object]"))
61
+ errors.push(`${m.code}: UC "${uc.name}" has [object Object] in steps — steps[] contains objects not strings`);
62
+ });
63
+ });
64
+
65
+ if (errors.length > 0) {
66
+ Display("⛔ SELF-CHECK FAILED — data loss detected:");
67
+ errors.forEach(e => Display(" - " + e));
68
+ // FIX: re-map the failing modules from collected_data before continuing
69
+ }
70
+ ```
71
+
72
+ ## Validation Points
73
+
74
+ ### 1. moduleSpecs Structure
75
+
76
+ **Check:** Every module in `FEATURE_DATA.modules` has a corresponding entry in `FEATURE_DATA.moduleSpecs[moduleCode]`.
77
+
78
+ **Failure Symptom:** `MISSING moduleSpecs[${m.code}]`
79
+
80
+ **Fix:** Ensure the build loop populates `moduleSpecs[moduleCode]` for ALL modules.
81
+
82
+ ### 2. useCases Count
83
+
84
+ **Check:** If source file has useCases (`usecases.useCases` or `usecases.usecases`), the built `spec.useCases` array must not be empty.
85
+
86
+ **Failure Symptom:** `${m.code}: useCases EMPTY but source has ${srcUC}`
87
+
88
+ **Common Causes:**
89
+ - Field is `usecases` but code looks for `useCases` (camelCase mismatch)
90
+ - Nested field is `usecases` instead of `useCases` (lowercase variant)
91
+ - Mapping function didn't handle array correctly
92
+
93
+ **Fix:** Check field names in `mod.usecases?.useCases || mod.usecases?.usecases`.
94
+
95
+ ### 3. businessRules Count
96
+
97
+ **Check:** If source file has businessRules (`rules.rules` or `rules.businessRules`), the built `spec.businessRules` array must not be empty.
98
+
99
+ **Failure Symptom:** `${m.code}: businessRules EMPTY but source has ${srcBR}`
100
+
101
+ **Common Causes:**
102
+ - Field is `businessRules` but code looks for `rules` (nested field name mismatch)
103
+ - Rules array is not being mapped correctly
104
+
105
+ **Fix:** Check field names in `mod.rules?.rules || mod.rules?.businessRules`.
106
+
107
+ ### 4. Entities Count
108
+
109
+ **Check:** If source file has entities (`entities.entities`), the built `spec.entities` array must not be empty.
110
+
111
+ **Failure Symptom:** `${m.code}: entities EMPTY but source has ${srcEnt}`
112
+
113
+ **Common Causes:**
114
+ - Mapping didn't iterate over entities array
115
+ - Fallback to `fields[]` when `attributes[]` is missing not working
116
+
117
+ **Fix:** Check the entities mapping includes both `attributes[]` and `fields[]` fallback.
118
+
119
+ ### 5. Screens Count
120
+
121
+ **Check:** If source file has screens (either `screens.screens[]` or `screens.sections[]`), the normalized `spec.screens[].resources[]` must have at least the same number of total resources.
122
+
123
+ **Failure Symptom:** `${m.code}: screens EMPTY (0 resources) but source has ${srcScreens} screens/sections`
124
+
125
+ **Common Causes:**
126
+ - Format detection logic failed (neither Format A nor B found)
127
+ - Screen format detection chose the wrong branch
128
+ - `normalizeColumn`, `normalizeField`, `normalizeFilter` functions not applied
129
+
130
+ **Fix:**
131
+ 1. Verify `mod.screens.screens` or `mod.screens.sections` exists
132
+ 2. Run format detection logic step-by-step
133
+ 3. Ensure screen resources are being pushed into the array
134
+
135
+ ### 6. Serialization Bug: [object Object]
136
+
137
+ **Check:** useCases steps field must be a string (or converted to string via `.join()`). If it contains `[object Object]`, the steps array contains unconverted objects.
138
+
139
+ **Failure Symptom:** `${m.code}: UC "${uc.name}" has [object Object] in steps — steps[] contains objects not strings`
140
+
141
+ **Fix:** Ensure the mapping converts step objects to strings:
142
+ ```javascript
143
+ steps: (uc.mainScenario || uc.steps || []).map(s =>
144
+ typeof s === 'string' ? s : (s.action || s.description || "")
145
+ ).join("\n") // .join() is CRITICAL to convert array to string
146
+ ```
147
+
148
+ ## Resolution Workflow
149
+
150
+ When self-check fails:
151
+
152
+ 1. **Identify failing module** from error message
153
+ 2. **Locate the source file** in `collected_data.modules[m.code]`
154
+ 3. **Compare field structure** between source and mapping code
155
+ 4. **Fix the mapping** (update field names, add fallbacks, fix type conversions)
156
+ 5. **Re-build moduleSpecs** for the failing module
157
+ 6. **Re-run self-check** to verify fix
158
+
159
+ ## Post-Check Actions
160
+
161
+ If self-check **PASSES**:
162
+ - Continue to step-03 (HTML rendering)
163
+ - No further data validation needed
164
+
165
+ If self-check **FAILS** with errors:
166
+ - DO NOT proceed to rendering
167
+ - Fix each error in the module build logic
168
+ - Re-build affected moduleSpecs entries
169
+ - Re-run self-check
170
+
171
+ ## Expected Output
172
+
173
+ ### Success Case
174
+
175
+ No errors array or empty:
176
+ ```
177
+ ✅ Self-check PASSED — all modules have complete data
178
+ ```
179
+
180
+ ### Failure Case
181
+
182
+ Display all errors:
183
+ ```
184
+ ⛔ SELF-CHECK FAILED — data loss detected:
185
+ - Employees: useCases EMPTY but source has 5
186
+ - Employees: UC "Create Employee" has [object Object] in steps — steps[] contains objects not strings
187
+ - Payroll: screens EMPTY (0 resources) but source has 3 screens/sections
188
+ ```
189
+
190
+ ---
191
+
192
+ ## Design Rationale
193
+
194
+ The self-check is **mandatory and blocking** because:
195
+
196
+ 1. **Silent data loss is worse than errors** — empty arrays are valid JavaScript but indicate a bug
197
+ 2. **Hard to debug later** — if screens/UC/BR are missing, the HTML viewer will appear empty but rendering code will work
198
+ 3. **Source of truth is always the collected files** — self-check compares against collected_data, not against user expectations
199
+ 4. **Early detection** — catch bugs in step-02 before they cascade into step-03 rendering
@@ -94,7 +94,8 @@ const FEATURE_DATA = {
94
94
  consolidation: {
95
95
  integrations: master.consolidation.crossModuleInteractions || [],
96
96
  sharedEntities: master.consolidation.sharedEntities || [],
97
- sequenceDiagrams: master.consolidation.e2eFlows || []
97
+ sequenceDiagrams: master.consolidation.e2eFlows || [],
98
+ mermaidDiagrams: master.consolidation.mermaidDiagrams || {}
98
99
  },
99
100
  handoff: {
100
101
  complexity: master.handoff.complexity,
@@ -122,6 +123,28 @@ const FEATURE_DATA = {
122
123
  6. Extract consolidation data (integrations, shared entities, E2E flows)
123
124
  7. Extract handoff section (complexity, strategy, module order, file counts)
124
125
 
126
+ ### consolidation.mermaidDiagrams (Mermaid diagrams)
127
+
128
+ Source: `consolidation.json`.mermaidDiagrams
129
+
130
+ Generated by step-04-consolidate section 5b. Contains pre-built Mermaid diagram definitions
131
+ for rendering in the HTML viewer.
132
+
133
+ ```javascript
134
+ mermaidDiagrams: {
135
+ erd: consolidation.mermaidDiagrams?.erd || null, // ERD string or null
136
+ mcd: consolidation.mermaidDiagrams?.mcd || null, // MCD string or null
137
+ useCases: consolidation.mermaidDiagrams?.useCases || {}, // {moduleCode: mermaid_def}
138
+ stateMachines: consolidation.mermaidDiagrams?.stateMachines || {}, // {entity: mermaid_def}
139
+ sequences: consolidation.mermaidDiagrams?.sequences || {} // {flowName: mermaid_def}
140
+ }
141
+ ```
142
+
143
+ Rendered by `12-render-diagrams.js`:
144
+ - `erd` → inserted in `#dataModelContainer` (consol-datamodel section)
145
+ - `stateMachines` → appended to `#dataModelContainer` per entity
146
+ - `sequences` → appended to consol-flows section
147
+
125
148
  ## EMBEDDED_ARTIFACTS Object
126
149
 
127
150
  > **CRITICAL:** The wireframes object is keyed by moduleCode (NOT a flat array).