@adia-ai/a2ui-corpus 0.7.23 → 0.7.25

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 CHANGED
@@ -1,5 +1,18 @@
1
1
  # Changelog — @adia-ai/a2ui-corpus
2
2
 
3
+ ## [0.7.25] — 2026-07-03
4
+
5
+ ### Changed
6
+ - **`catalog-a2ui_0_9.json` regenerated — registers `accordion-ui`'s new `variant` prop.** The generator catalog was rebuilt from the component yaml SoT after `accordion.yaml` + `accordion-item.yaml` gained the `variant="flat|contained"` attribute, so the published catalog exposes it to the gen-UI pipeline. Chunks + `chunk-embeddings.json` byte-stable — the 3 new `accordion-variant-*` `data-chunk` markers on the primitive's own demo page are bare (no `data-chunk-domain`), so the harvester's `annotatedOnly` gate correctly excludes them as dev-overlay-only, not corpus content (verified: `chunks/_index.json` unique_names unchanged at 394, no re-embed needed). Substantive v0.7.25 work shipped in `@adia-ai/web-components` — see `packages/web-components/CHANGELOG.md#0725--2026-07-03`.
7
+
8
+ ### Maintenance
9
+ - **Doc-comment path reference corrected** (`docs/specs/...` → `.claude/docs/specs/...`) in `scripts/chunk-library.js` — propagated from the repo-wide `docs/` → `.claude/docs/` migration (2026-07-01); no functional change.
10
+
11
+ ## [0.7.24] — 2026-07-01
12
+
13
+ ### Changed
14
+ - **`catalog-a2ui_0_9.json` + `catalog-a2ui_0_9_rules.txt` regenerated — registers `display-field-ui`.** The generator catalog was rebuilt from the component yaml SoT after the new `display-field/display-field.yaml` landed, so the published catalog exposes `display-field-ui` (120 → 121 components) to the gen-UI pipeline. Chunks + `chunk-embeddings.json` byte-stable (no new annotated chunks; no re-embed). Substantive v0.7.24 work shipped in `@adia-ai/web-components` — see `packages/web-components/CHANGELOG.md#0724--2026-07-01`.
15
+
3
16
  ## [0.7.23] — 2026-06-30
4
17
 
5
18
  ### Changed
@@ -405,7 +418,7 @@ Patterns shipped: card-ui header/section/footer anatomy; row-ui header pattern;
405
418
  - **`chunk-embeddings.json` regenerated to match the re-harvested chunks.** 230 chunks re-embedded (1536-d `text-embedding-3-small`); restores `check:embeddings-fresh` to green — the retrieval index had drifted 6.6 days stale relative to `chunks/_index.json`, predating this cut but surfaced by the dashboard chunk re-harvest above.
406
419
 
407
420
  ### Maintenance
408
- - **Lockstep version bump only for non-dashboard chunks.** No other source changes in this package; bumped to maintain the 9-package version coherence enforced by `scripts/release/check-lockstep.mjs`. Substantive v0.6.15 work also shipped in `@adia-ai/web-components` — `installIconLoaders` shape-detects malformed flat globs (FB-07), `icons-phosphor.js` surfaces silent-fail diagnostics (FB-08), and docs/skill examples corrected (FB-09). See `packages/web-components/CHANGELOG.md#0615--2026-05-21` for details.
421
+ - **Lockstep version bump only for non-dashboard chunks.** No other source changes in this package; bumped to maintain the 9-package version coherence enforced by `scripts/release/check-lockstep.mjs`. Substantive v0.6.15 work also shipped in `@adia-ai/web-components` — `installIconLoaders` shape-detects malformed flat globs (FB-07), `icons-phosphor.js` surfaces silent-fail diagnostics (FB-08), and .claude/docs/skill examples corrected (FB-09). See `packages/web-components/CHANGELOG.md#0615--2026-05-21` for details.
409
422
 
410
423
  ## [0.6.14] — 2026-05-21
411
424
 
@@ -734,7 +747,7 @@ Corpus regen via `npm run harvest:chunks`: 222 → 230 chunks (+8); chunk index
734
747
 
735
748
  Expected impact: Haiku free-form coverage on the 100-intent held-out set lifts from 91% (post-v0.5.2 §125+§126) → ~98-99% (matching Opus's §127 ceiling). Empirical verification in v0.5.3 §145 rebaseline check (paired re-eval).
736
749
 
737
- Per the §127 verdict report (`docs/reports/free-form-haiku-vs-opus-2026-05-13.md`) — closing the coverage gap via chunk authoring is the right lever; model swap to Opus (5× cost) was rejected by the §127 decision rule. §143 ships the rejected-Opus's path-forward.
750
+ Per the §127 verdict report (`.claude/docs/reports/free-form-haiku-vs-opus-2026-05-13.md`) — closing the coverage gap via chunk authoring is the right lever; model swap to Opus (5× cost) was rejected by the §127 decision rule. §143 ships the rejected-Opus's path-forward.
738
751
  ## [0.5.2] - 2026-05-13
739
752
 
740
753
  ### Changed — Catalog-text structural sweep on 5 under-substituted chunks (§125, v0.5.2)
@@ -824,7 +837,7 @@ Hand-authored `corpus/patterns/<domain>/*.{json,yaml}` (~225 files) and `corpus/
824
837
  - **`scripts/ingest.js`** retired — pattern-ingestion phase of the legacy pipeline; chunks-only post-§64.
825
838
  - **`scripts/build-pattern-index.mjs`** retired — produced the `patterns/_index.json` files no consumer reads post-§64.
826
839
 
827
- Companion docs link-rot fix in `docs/journal/2026/04/2026-04-27.md` (one markdown link to `scripts/run-pipeline.mjs` unwrapped to plain text with retired-2026-05-12 annotation).
840
+ Companion docs link-rot fix in `.claude/docs/journal/2026/04/2026-04-27.md` (one markdown link to `scripts/run-pipeline.mjs` unwrapped to plain text with retired-2026-05-12 annotation).
828
841
 
829
842
  ### Added — `settings-admin-page` chunk + Mode A annotation (§63, v0.4.6)
830
843
 
@@ -935,7 +948,7 @@ The harvester is repo-tooling (`scripts/build/`), not a corpus package member, b
935
948
  - **§42 nested-expand-then-transpile pass** — after collection, recursively expands `<!-- nested: <name> -->` placeholders in annotated chunks, then transpiles the expanded HTML to A2UI templates via `transpileHTML(html, { mode: 'instant' })`.
936
949
  - **§45 source-aware tier-1 expansion fix** — replaces §42's "first wins" canonical-html rule with directory-aware selection. **Bug**: `auth-card-content` has 24 instances; the 404 page sorted alphabetically first, so EVERY auth chunk silently inlined 404 page content from §41 landing through §45 discovery (smoke tests only checked retrieval strategy, not template content). **Fix**: Tier 1 exact directory match → Tier 2 deepest common directory prefix → Tier 3 alphabetical. Without it, `apps/user-flow/app/auth/sign-in/` shares depth with `apps/user-flow/app/auth/sign-in/mfa/` and tie-break would pick wrong sibling.
937
950
 
938
- See root [CHANGELOG.md `[Unreleased]`](../../../CHANGELOG.md) for the cross-cutting arc narrative + [docs/journal/2026/05/2026-05-12.md](../../../docs/journal/2026/05/2026-05-12.md) §§ 36-51 for per-§ details.
951
+ See root [CHANGELOG.md `[Unreleased]`](../../../CHANGELOG.md) for the cross-cutting arc narrative + [.claude/docs/journal/2026/05/2026-05-12.md](../../../.claude/docs/journal/2026/05/2026-05-12.md) §§ 36-51 for per-§ details.
939
952
  ## [0.4.3] - 2026-05-11
940
953
 
941
954
  ### Changed
@@ -961,7 +974,7 @@ See root [CHANGELOG.md `[Unreleased]`](../../../CHANGELOG.md) for the cross-cutt
961
974
 
962
975
  ### Lockstep
963
976
 
964
- 9-package coordinated PATCH cut to v0.4.2 (per [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy)). Internal `@adia-ai/*` dep ranges stay at `^0.4.0` (patch-cut asymmetry — `^0.4.0` covers `0.4.x` under semver). Rides alongside `@adia-ai/web-components@0.4.2` (input-ui type=number rewrite) and `@adia-ai/web-modules@0.4.2` (editor-sidebar width mirror). See root [CHANGELOG.md `## [0.4.2]`](../../../CHANGELOG.md) for the cut narrative.
977
+ 9-package coordinated PATCH cut to v0.4.2 (per [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy)). Internal `@adia-ai/*` dep ranges stay at `^0.4.0` (patch-cut asymmetry — `^0.4.0` covers `0.4.x` under semver). Rides alongside `@adia-ai/web-components@0.4.2` (input-ui type=number rewrite) and `@adia-ai/web-modules@0.4.2` (editor-sidebar width mirror). See root [CHANGELOG.md `## [0.4.2]`](../../../CHANGELOG.md) for the cut narrative.
965
978
  ## [0.4.1] - 2026-05-10
966
979
 
967
980
  ### Changed
@@ -972,7 +985,7 @@ See root [CHANGELOG.md `[Unreleased]`](../../../CHANGELOG.md) for the cross-cutt
972
985
 
973
986
  ### Added
974
987
 
975
- - `docs/reports/chunk-reconcile-triage-2026-05-10.md` — triage doc documenting that all current `audit:chunk-reconcile` findings (9 fingerprint collisions + 19 near-duplicates + 10 cross-source) are intentional outcomes of the onb/reg alignment work + foundational shared chunks.
988
+ - `.claude/docs/reports/chunk-reconcile-triage-2026-05-10.md` — triage doc documenting that all current `audit:chunk-reconcile` findings (9 fingerprint collisions + 19 near-duplicates + 10 cross-source) are intentional outcomes of the onb/reg alignment work + foundational shared chunks.
976
989
  ## [0.4.0] - 2026-05-10
977
990
 
978
991
  ### Ride-along (no corpus changes)
@@ -1032,7 +1045,7 @@ The catalog is consumed by `@adia-ai/a2ui-retrieval` for protocol-vocabulary com
1032
1045
  Corpus chunks, fragments, compositions, and patterns are byte-identical to v0.3.3. The only change is the regenerated catalog manifest.
1033
1046
  ## [0.3.3] - 2026-05-07
1034
1047
 
1035
- **Lockstep cut.** All 9 published `@adia-ai/*` packages now share version `0.3.3`, governed by [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy). Internal `@adia-ai/*` ranges stay at `^0.3.0` (patch-cut asymmetry — caret floats `0.3.x`).
1048
+ **Lockstep cut.** All 9 published `@adia-ai/*` packages now share version `0.3.3`, governed by [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy). Internal `@adia-ai/*` ranges stay at `^0.3.0` (patch-cut asymmetry — caret floats `0.3.x`).
1036
1049
 
1037
1050
  ### Added
1038
1051
 
@@ -1067,7 +1080,7 @@ Corpus chunks, fragments, compositions, and patterns are byte-identical to v0.3.
1067
1080
  ## [0.3.2] - 2026-05-06
1068
1081
 
1069
1082
  **9-package lockstep patch cut to v0.3.2.** All lockstep members share
1070
- one version per [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy).
1083
+ one version per [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy).
1071
1084
  Internal `@adia-ai/*` dep ranges unchanged at `^0.3.0`.
1072
1085
 
1073
1086
  ### Added
@@ -1094,7 +1107,7 @@ Internal `@adia-ai/*` dep ranges unchanged at `^0.3.0`.
1094
1107
  - `version`: `0.3.1` → `0.3.2`.
1095
1108
  ## [0.3.1] - 2026-05-06
1096
1109
 
1097
- **9-package lockstep patch cut.** All 9 published `@adia-ai/*` packages bump 0.3.0 → 0.3.1 per [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy). Internal `@adia-ai/*` dep ranges remain at `^0.3.0` (covers `0.3.1` under semver — patch-cut asymmetry).
1110
+ **9-package lockstep patch cut.** All 9 published `@adia-ai/*` packages bump 0.3.0 → 0.3.1 per [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy). Internal `@adia-ai/*` dep ranges remain at `^0.3.0` (covers `0.3.1` under semver — patch-cut asymmetry).
1098
1111
 
1099
1112
  This package itself ships **no source changes** in v0.3.1. The cut bumps version only — substantive content lives in [`@adia-ai/web-components`](https://github.com/adiahealth/gen-ui-kit/releases/tag/web-components-v0.3.1) (folder-per-trait restructure; barrel API unchanged).
1100
1113
 
@@ -1104,7 +1117,7 @@ This package itself ships **no source changes** in v0.3.1. The cut bumps version
1104
1117
  - Internal `@adia-ai/*` dep ranges: unchanged at `^0.3.0` (covers `0.3.1` under semver — patch-cut asymmetry).
1105
1118
  ## [0.3.0] - 2026-05-05
1106
1119
 
1107
- **9-package lockstep cut.** All 9 published `@adia-ai/*` packages bump 0.2.5 → 0.3.0 per [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy). Internal `@adia-ai/*` dep ranges bump `^0.2.0` → `^0.3.0`.
1120
+ **9-package lockstep cut.** All 9 published `@adia-ai/*` packages bump 0.2.5 → 0.3.0 per [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy). Internal `@adia-ai/*` dep ranges bump `^0.2.0` → `^0.3.0`.
1108
1121
 
1109
1122
  The lockstep policy expanded from 8 to 9 packages with this cut — `@adia-ai/llm` joins as a 9th member, and `@adia-ai/a2ui-utils` was renamed to `@adia-ai/a2ui-runtime`. Both are BREAKING for npm consumers (acceptable under pre-1.0 semver).
1110
1123
 
@@ -1119,7 +1132,7 @@ This package itself ships **no source changes** in v0.3.0. The cut bumps version
1119
1132
  `a2ui-corpus` source is byte-identical to `0.2.5`. The cut bumps version only — corpus has no `@adia-ai/*` dependencies so no dep-range updates either.
1120
1133
  ## [0.2.5] - 2026-05-04
1121
1134
 
1122
- **Lockstep cut + catalog regen for `<fields-ui>` primitive.** All 8 published `@adia-ai/*` packages bump 0.2.4 → 0.2.5 per [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy). Patch cut — **no BREAKING changes**.
1135
+ **Lockstep cut + catalog regen for `<fields-ui>` primitive.** All 8 published `@adia-ai/*` packages bump 0.2.4 → 0.2.5 per [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy). Patch cut — **no BREAKING changes**.
1123
1136
 
1124
1137
  ### Changed
1125
1138
 
@@ -1128,7 +1141,7 @@ This package itself ships **no source changes** in v0.3.0. The cut bumps version
1128
1141
  - Per-element `fields/fields.a2ui.json` written by `scripts/build/components.mjs`.
1129
1142
  ## [0.2.4] - 2026-05-04
1130
1143
 
1131
- **Lockstep cut + catalog regen for `<demo-toggle-ui>` primitive.** All 8 published `@adia-ai/*` packages bump 0.2.3 → 0.2.4 per [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy). Patch cut — no breaking changes.
1144
+ **Lockstep cut + catalog regen for `<demo-toggle-ui>` primitive.** All 8 published `@adia-ai/*` packages bump 0.2.3 → 0.2.4 per [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy). Patch cut — no breaking changes.
1132
1145
 
1133
1146
  ### Changed
1134
1147
 
@@ -1150,7 +1163,7 @@ the generated `_catalog.json` consumed by
1150
1163
 
1151
1164
  **Lockstep cut.** All 8 published `@adia-ai/*` packages bump
1152
1165
  0.2.2 → 0.2.3 per
1153
- [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy).
1166
+ [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy).
1154
1167
  Patch cut — no breaking changes.
1155
1168
 
1156
1169
  ### Changed
@@ -1162,7 +1175,7 @@ Patch cut — no breaking changes.
1162
1175
  `@adia-ai/a2ui-corpus` source is byte-identical to `0.2.2`. The cut bumps version only.
1163
1176
  ## [0.2.2] - 2026-05-02
1164
1177
 
1165
- **Lockstep cut.** All 8 published `@adia-ai/*` packages bump 0.2.1 → 0.2.2 per [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy). Patch cut — no breaking changes.
1178
+ **Lockstep cut.** All 8 published `@adia-ai/*` packages bump 0.2.1 → 0.2.2 per [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy). Patch cut — no breaking changes.
1166
1179
 
1167
1180
  ### Changed
1168
1181
 
@@ -1175,7 +1188,7 @@ Patch cut — no breaking changes.
1175
1188
  ---
1176
1189
  ## [0.2.1] - 2026-05-02
1177
1190
 
1178
- **Lockstep cut + chunk-corpus reorganization mega-arc + trait registry regenerated from web-components SoT.** All 8 published `@adia-ai/*` packages bump 0.2.0 → 0.2.1 per [`docs/specs/package-architecture.md` § 15](../../../docs/specs/package-architecture.md#15-versioning-policy). Patch cut — no breaking changes.
1191
+ **Lockstep cut + chunk-corpus reorganization mega-arc + trait registry regenerated from web-components SoT.** All 8 published `@adia-ai/*` packages bump 0.2.0 → 0.2.1 per [`.claude/docs/specs/package-architecture.md` § 15](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy). Patch cut — no breaking changes.
1179
1192
 
1180
1193
  ### Changed
1181
1194
 
@@ -1236,12 +1249,12 @@ New `scripts/build/under-harvest-audit.mjs` flags pages under `site/pages/{patte
1236
1249
  - **`patterns/layout/weather-widget.json`** — renamed `Metric` → `Stat` (no `<metric-ui>` exists; `Stat` is the canonical metric/value/change/trend primitive).
1237
1250
  - Smoke side-effect: zettel score bumped 91 → 92; smoke validation flipped from `valid=false score=98/91` → `valid=true score=100/92`. The registry gaps were tripping validation upstream.
1238
1251
 
1239
- Per-finding triage in [`docs/reports/playground-examples-review-2026-05-02.md`](../../../docs/reports/playground-examples-review-2026-05-02.md).
1252
+ Per-finding triage in [`.claude/docs/reports/playground-examples-review-2026-05-02.md`](../../../.claude/docs/reports/playground-examples-review-2026-05-02.md).
1240
1253
  ## [0.2.0] - 2026-05-02
1241
1254
 
1242
1255
  **Lockstep cut.** All 8 published `@adia-ai/*` packages now share one
1243
- version, governed by [`docs/specs/package-architecture.md` § 15
1244
- (Versioning Policy)](../../../docs/specs/package-architecture.md#15-versioning-policy).
1256
+ version, governed by [`.claude/docs/specs/package-architecture.md` § 15
1257
+ (Versioning Policy)](../../../.claude/docs/specs/package-architecture.md#15-versioning-policy).
1245
1258
 
1246
1259
  This release also formalizes corpus's role as **the catalog's home** —
1247
1260
  spec § 3 first-principle 3 was rewritten in v0.6.0 of the spec to
@@ -1489,11 +1502,11 @@ existing pattern/fragment/composition surface unchanged.
1489
1502
 
1490
1503
  ### Convention reference
1491
1504
 
1492
- - Spec: [`docs/specs/genui-chunk-marker.md`](../../../docs/specs/genui-chunk-marker.md)
1505
+ - Spec: [`.claude/docs/specs/genui-chunk-marker.md`](../../../.claude/docs/specs/genui-chunk-marker.md)
1493
1506
  (Draft v0.1.0) — three attributes (`data-chunk`, `data-chunk-kind`,
1494
1507
  `data-chunk-slot`); naming conventions per cluster; visual marker
1495
1508
  rules; harvester contract.
1496
- - Inventory: [`docs/specs/genui-chunk-inventory-001.md`](../../../docs/specs/genui-chunk-inventory-001.md)
1509
+ - Inventory: [`.claude/docs/specs/genui-chunk-inventory-001.md`](../../../.claude/docs/specs/genui-chunk-inventory-001.md)
1497
1510
  — full list with intent labels + review status.
1498
1511
  ## [0.0.2] - 2026-04-27
1499
1512
 
package/README.md CHANGED
@@ -61,7 +61,7 @@ hand-authored ungrounded JSON lives in `corpus/`.
61
61
  > retrievable equivalents were either (a) already represented in the
62
62
  > chunks corpus via annotated `data-chunk-*` regions, or (b) deemed
63
63
  > non-grounded under the locked rule and DELETE'd in §73 Mode-C triage
64
- > (target for v0.4.7). See [`docs/journal/2026/05/2026-05-12.md`](../../../docs/journal/2026/05/2026-05-12.md)
64
+ > (target for v0.4.7). See [`.claude/docs/journal/2026/05/2026-05-12.md`](../../../.claude/docs/journal/2026/05/2026-05-12.md)
65
65
  > §§ 36-§42, §65, §72 for the multi-arc retirement narrative.
66
66
 
67
67
  ## Layout
@@ -243,7 +243,7 @@ When adding coverage for a new intent:
243
243
  2. **Tag the reusable region** — add `data-chunk="<slug>"` +
244
244
  `data-chunk-kind="<kind>"` (block / page / panel / field) on the
245
245
  element. The harvester extracts the bounding HTML on the next
246
- build. See `docs/specs/genui-chunk-marker.md` for the marker
246
+ build. See `.claude/docs/specs/genui-chunk-marker.md` for the marker
247
247
  convention.
248
248
  3. **Harvest + ingest** — `npm run harvest:chunks` writes
249
249
  `chunks/<slug>.json` and refreshes `_index.json`. `npm run pipeline`
@@ -156,6 +156,15 @@
156
156
  "description": "Allow multiple panels to be open simultaneously",
157
157
  "type": "boolean",
158
158
  "default": false
159
+ },
160
+ "variant": {
161
+ "description": "Visual posture, inherited by child accordion-item-ui elements unless a\nchild sets its own [variant]. `flat` (default) renders items with no\nchrome — settings pages, FAQ blocks, anywhere the accordion sits\ndirectly on the page canvas. `contained` gives every item a bounded\nsurface (background + border + radius spanning header and open body,\nplus a divider between them when open) — the composition to reach for\nwhen nesting the accordion inside <card-ui>.",
162
+ "type": "string",
163
+ "enum": [
164
+ "flat",
165
+ "contained"
166
+ ],
167
+ "default": "flat"
159
168
  }
160
169
  },
161
170
  "required": [
@@ -297,6 +306,15 @@
297
306
  "text": {
298
307
  "description": "Header text — the clickable label that toggles the section.",
299
308
  "type": "string"
309
+ },
310
+ "variant": {
311
+ "description": "Per-item posture override. Items normally inherit their host\naccordion-ui's [variant] — set this directly on ONE item only to\nopt it out of (`flat`) or into (`contained`) the host's posture.",
312
+ "type": "string",
313
+ "enum": [
314
+ "flat",
315
+ "contained"
316
+ ],
317
+ "default": "flat"
300
318
  }
301
319
  },
302
320
  "required": [
@@ -339,6 +357,9 @@
339
357
  "body": {
340
358
  "description": "The section's collapsible content. Renders below the header; hidden when `[open]` is unset. Author-fills with prose, lists, embedded forms, or any rich markup the panel needs."
341
359
  },
360
+ "caret": {
361
+ "description": "The disclosure indicator icon. Auto-stamped (a caret-down icon-ui)\nwhen absent — under BOTH the default header and an authored\n[slot=\"header\"]. Author your own [slot=\"caret\"] element (even empty)\nto opt out of the auto-stamp; no separate attribute needed."
362
+ },
342
363
  "header": {
343
364
  "description": "Custom header content. By default `[text]` renders as a plain header\nlabel, but a `[slot=\"header\"]` override lets consumers author rich\nheaders (icon + title + action buttons + caret)."
344
365
  }
@@ -354,7 +375,24 @@
354
375
  ]
355
376
  },
356
377
  "tag": "accordion-item-ui",
357
- "tokens": {},
378
+ "tokens": {
379
+ "--accordion-item-bg": {
380
+ "description": "Item surface background.",
381
+ "default": "transparent"
382
+ },
383
+ "--accordion-item-body-pt": {
384
+ "description": "Open body top padding.",
385
+ "default": 0
386
+ },
387
+ "--accordion-item-border": {
388
+ "description": "Item surface border (full shorthand — mirrors --card-border).",
389
+ "default": "none"
390
+ },
391
+ "--accordion-item-divider": {
392
+ "description": "Border between header and open body when expanded.",
393
+ "default": "none"
394
+ }
395
+ },
358
396
  "traits": [],
359
397
  "version": 1
360
398
  }
@@ -3006,7 +3044,7 @@
3006
3044
  },
3007
3045
  "BillingOverview": {
3008
3046
  "title": "BillingOverview",
3009
- "description": "Module-tier billing dashboard that stitches the seven Wave A+B\nbilling primitives into the canonical \"all-billing-on-one-page\"\nsurface — current plan + status header, a KPI strip (monthly\nspend · seats · next invoice), an optional dunning banner when the\naccount is past-due, a plan-picker section for in-app plan changes,\na payment-method-list section, and an invoice-history section.\n\nData-driven via the `account` property — an aggregate snapshot of\nthe customer's billing state ({plan, status, billingCycle,\ncurrentSpend, seats, nextInvoiceDate, paymentMethods[],\ninvoices[], dunning?}). The composite stamps a fixed five-region\nskeleton once on first connect — header · kpis · dunning ·\nplan-picker · payment-methods · invoice-history — then mutates\nper-region nodes via id-keyed in-place diff on every property\nchange. Children primitives (plan-picker, payment-method-list,\ninvoice-history, alert-ui) are stamped as composed tags; this\ncomposite owns the orchestration, not the row chrome.\n\nHigher-level account-action event surfaces consumer-actionable\nintents from descendant primitives. Children carrying\n[data-account-action=\"X\"] or descendant events\n(`plan-action`, `payment-action`, `invoice-action`, `dunning-action`)\nare normalised into a single `account-action` event with\n`detail.action` ∈ {change-plan, add-payment-method, pay-now,\ndownload-invoice, update-card, retry, custom}. The composite\ndoes NOT mutate the data source; consumers wire `account-action`\nagainst their billing backend.\n\nDisplay surface. Extends UIElement, not UIFormElement — child\nprimitives are individually form-bearing (plan-picker,\npayment-method-list) while the host is not.\n\nSpec: docs/specs/implementation-ready/SPEC-004-billing-overview.md.\n",
3047
+ "description": "Module-tier billing dashboard that stitches the seven Wave A+B\nbilling primitives into the canonical \"all-billing-on-one-page\"\nsurface — current plan + status header, a KPI strip (monthly\nspend · seats · next invoice), an optional dunning banner when the\naccount is past-due, a plan-picker section for in-app plan changes,\na payment-method-list section, and an invoice-history section.\n\nData-driven via the `account` property — an aggregate snapshot of\nthe customer's billing state ({plan, status, billingCycle,\ncurrentSpend, seats, nextInvoiceDate, paymentMethods[],\ninvoices[], dunning?}). The composite stamps a fixed five-region\nskeleton once on first connect — header · kpis · dunning ·\nplan-picker · payment-methods · invoice-history — then mutates\nper-region nodes via id-keyed in-place diff on every property\nchange. Children primitives (plan-picker, payment-method-list,\ninvoice-history, alert-ui) are stamped as composed tags; this\ncomposite owns the orchestration, not the row chrome.\n\nHigher-level account-action event surfaces consumer-actionable\nintents from descendant primitives. Children carrying\n[data-account-action=\"X\"] or descendant events\n(`plan-action`, `payment-action`, `invoice-action`, `dunning-action`)\nare normalised into a single `account-action` event with\n`detail.action` ∈ {change-plan, add-payment-method, pay-now,\ndownload-invoice, update-card, retry, custom}. The composite\ndoes NOT mutate the data source; consumers wire `account-action`\nagainst their billing backend.\n\nDisplay surface. Extends UIElement, not UIFormElement — child\nprimitives are individually form-bearing (plan-picker,\npayment-method-list) while the host is not.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-004-billing-overview.md.\n",
3010
3048
  "type": "object",
3011
3049
  "allOf": [
3012
3050
  {
@@ -7317,7 +7355,7 @@
7317
7355
  },
7318
7356
  "ConfirmDialog": {
7319
7357
  "title": "ConfirmDialog",
7320
- "description": "Non-destructive yes/no confirmation dialog — a thin composite over\n<modal-ui> that pre-stamps the canonical confirm shape: header (title\n+ optional icon), body (description + optional rich slot), and\nfooter (cancel + confirm buttons). Wires Cancel-default focus,\nconfirm / cancel / close events, and the [loading] in-flight state.\n\nUse confirm-dialog-ui for benign questions: \"Save changes?\", \"Switch\ntheme?\", \"Apply preset?\". For irreversible destructive operations\n(delete account, drop database, deploy to prod) use <alert-dialog-ui>\ninstead — it carries role=\"alertdialog\", danger chrome, and the\noptional typed-name speed-bump.\n\nComposed primitive: <modal-ui> owns the native <dialog>, focus trap,\nbackdrop, and Escape-dismiss. confirm-dialog-ui decorates; it does\nnot reimplement.\n\nSpec: docs/specs/implementation-ready/SPEC-049-confirm-dialog-yes-no.md.\n",
7358
+ "description": "Non-destructive yes/no confirmation dialog — a thin composite over\n<modal-ui> that pre-stamps the canonical confirm shape: header (title\n+ optional icon), body (description + optional rich slot), and\nfooter (cancel + confirm buttons). Wires Cancel-default focus,\nconfirm / cancel / close events, and the [loading] in-flight state.\n\nUse confirm-dialog-ui for benign questions: \"Save changes?\", \"Switch\ntheme?\", \"Apply preset?\". For irreversible destructive operations\n(delete account, drop database, deploy to prod) use <alert-dialog-ui>\ninstead — it carries role=\"alertdialog\", danger chrome, and the\noptional typed-name speed-bump.\n\nComposed primitive: <modal-ui> owns the native <dialog>, focus trap,\nbackdrop, and Escape-dismiss. confirm-dialog-ui decorates; it does\nnot reimplement.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-049-confirm-dialog-yes-no.md.\n",
7321
7359
  "type": "object",
7322
7360
  "allOf": [
7323
7361
  {
@@ -7678,7 +7716,7 @@
7678
7716
  },
7679
7717
  "DashboardLayout": {
7680
7718
  "title": "DashboardLayout",
7681
- "description": "Module-tier dashboard-body composite. Crystallizes the recurring\n\"toolbar + KPI grid + chart area + table\" dashboard layout into a\nsingle primitive with four named regions (toolbar / kpis / charts /\ntable) plus an optional aside column. Each region is filled by\nconsumer-supplied <card-ui>s; the composite owns band sizing,\nresponsive breakpoints, and a [density] knob that propagates to\nevery descendant primitive via the parametric --a-density cascade.\n\nSits inside an <admin-page-body>; replaces the hand-rolled\n<col-ui gap=\"4\"> + nested <grid-ui> + <card-ui> chains every\nanalytics consumer reinvents today. Per ADR-0033 (Light-DOM\nsubstrate) — slot= attributes are decorative metadata; CSS rules\nmatch `:scope > [slot=\"X\"]` to position bands in DOM order.\n\nSpec: docs/specs/implementation-ready/SPEC-018-dashboard-layout.md.\n",
7719
+ "description": "Module-tier dashboard-body composite. Crystallizes the recurring\n\"toolbar + KPI grid + chart area + table\" dashboard layout into a\nsingle primitive with four named regions (toolbar / kpis / charts /\ntable) plus an optional aside column. Each region is filled by\nconsumer-supplied <card-ui>s; the composite owns band sizing,\nresponsive breakpoints, and a [density] knob that propagates to\nevery descendant primitive via the parametric --a-density cascade.\n\nSits inside an <admin-page-body>; replaces the hand-rolled\n<col-ui gap=\"4\"> + nested <grid-ui> + <card-ui> chains every\nanalytics consumer reinvents today. Per ADR-0033 (Light-DOM\nsubstrate) — slot= attributes are decorative metadata; CSS rules\nmatch `:scope > [slot=\"X\"]` to position bands in DOM order.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-018-dashboard-layout.md.\n",
7682
7720
  "type": "object",
7683
7721
  "allOf": [
7684
7722
  {
@@ -8243,7 +8281,7 @@
8243
8281
  },
8244
8282
  "DateRangeSelector": {
8245
8283
  "title": "DateRangeSelector",
8246
- "description": "Page-level \"current time window\" chooser for dashboards. A module-tier\ncomposite that pairs a preset chip-row (Today / 7d / 30d / 90d / QTD /\nYTD / Custom) with an embedded <date-range-picker-ui> and broadcasts\nthe active range to every range-aware panel on the page.\n\nOne chooser, one event bus, every panel follows. The composite owns\nthe range value, resolves preset keys to ISO 8601 from/to pairs, and\nemits a `range-change` CustomEvent on the configured broadcast target\n(default `document`). It also writes `data-range-from` /\n`data-range-to` to that target so CSS-only subscribers can match\nattribute selectors.\n\nUse for dashboard toolbars (typically <dashboard-layout-ui slot=\"toolbar\">\nor <admin-page-header slot=\"action\">). For card-local per-panel\ncomparison overlays, set [broadcast=\"self\"] so the secondary instance\nscopes to its host.\n\nSpec: docs/specs/implementation-ready/SPEC-019-date-range-selector-global.md.\n",
8284
+ "description": "Page-level \"current time window\" chooser for dashboards. A module-tier\ncomposite that pairs a preset chip-row (Today / 7d / 30d / 90d / QTD /\nYTD / Custom) with an embedded <date-range-picker-ui> and broadcasts\nthe active range to every range-aware panel on the page.\n\nOne chooser, one event bus, every panel follows. The composite owns\nthe range value, resolves preset keys to ISO 8601 from/to pairs, and\nemits a `range-change` CustomEvent on the configured broadcast target\n(default `document`). It also writes `data-range-from` /\n`data-range-to` to that target so CSS-only subscribers can match\nattribute selectors.\n\nUse for dashboard toolbars (typically <dashboard-layout-ui slot=\"toolbar\">\nor <admin-page-header slot=\"action\">). For card-local per-panel\ncomparison overlays, set [broadcast=\"self\"] so the secondary instance\nscopes to its host.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-019-date-range-selector-global.md.\n",
8247
8285
  "type": "object",
8248
8286
  "allOf": [
8249
8287
  {
@@ -9053,6 +9091,189 @@
9053
9091
  "version": 1
9054
9092
  }
9055
9093
  },
9094
+ "DisplayField": {
9095
+ "title": "DisplayField",
9096
+ "description": "Display-only labeled value — a field-shaped read-out for a static or masked value (e.g. a card on file \"•••• 4242\"), or a labeled slot that hosts a third-party element (a Stripe Element iframe) under a proper caption. Unlike field-ui it wraps NO interactive control: no focus, no contenteditable, no form participation, no [for]/id-minting. The label names the whole field for assistive tech via role=\"group\" + aria-labelledby, so a slotted foreign element (iframe) is announced with its caption. Reach for field-ui + input-ui when the value is EDITABLE; stat-ui for a prominent metric/KPI; description-list-ui for many read-only key/value pairs at once.",
9097
+ "type": "object",
9098
+ "allOf": [
9099
+ {
9100
+ "$ref": "#/$defs/ComponentCommon"
9101
+ },
9102
+ {
9103
+ "$ref": "#/$defs/CatalogComponentCommon"
9104
+ }
9105
+ ],
9106
+ "properties": {
9107
+ "component": {
9108
+ "const": "DisplayField"
9109
+ },
9110
+ "hint": {
9111
+ "description": "Optional caption rendered below the value in subtle style (e.g. \"Expires 12/26\"). Wired into the field's aria-describedby.",
9112
+ "type": "string",
9113
+ "default": ""
9114
+ },
9115
+ "icon": {
9116
+ "description": "Optional leading icon name shown beside the value (e.g. a lock or card-brand glyph). Lazily creates a single icon-ui child.",
9117
+ "type": "string",
9118
+ "default": ""
9119
+ },
9120
+ "label": {
9121
+ "description": "The field caption. Names the whole field for assistive tech.",
9122
+ "type": "string",
9123
+ "default": ""
9124
+ },
9125
+ "value": {
9126
+ "description": "The static value text to display (e.g. \"•••• 4242\"). Ignored when the default slot already carries content — slot a foreign element OR set value=, not both.",
9127
+ "type": "string",
9128
+ "default": ""
9129
+ },
9130
+ "variant": {
9131
+ "description": "Cosmetic value treatment. `default` renders the value in the UI font; `masked` switches to the code/mono family with tabular numerals and light letter-spacing so masked strings (\"•••• 4242\") align cleanly. Tokens only — no layout change.",
9132
+ "type": "string",
9133
+ "enum": [
9134
+ "default",
9135
+ "masked"
9136
+ ],
9137
+ "default": "default"
9138
+ }
9139
+ },
9140
+ "required": [
9141
+ "component",
9142
+ "label"
9143
+ ],
9144
+ "unevaluatedProperties": false,
9145
+ "x-adiaui": {
9146
+ "anti_patterns": [
9147
+ {
9148
+ "description": "Using input-ui[readonly] to render a static masked value. A readonly input still carries contenteditable/focus semantics and tab-stops; a display read-out should not be a control.",
9149
+ "right": "<display-field-ui label=\"Card on file\" value=\"•••• 4242\" variant=\"masked\"></display-field-ui>\n",
9150
+ "rule": "A non-editable masked value is display-field-ui, not a readonly input.",
9151
+ "wrong": "<input-ui readonly value=\"•••• 4242\"></input-ui>\n"
9152
+ }
9153
+ ],
9154
+ "category": "form",
9155
+ "composes": [
9156
+ "icon-ui"
9157
+ ],
9158
+ "events": {},
9159
+ "examples": [
9160
+ {
9161
+ "description": "A masked \"card on file\" read-out with a leading lock icon and an expiry hint.",
9162
+ "a2ui": "[\n {\n \"id\": \"root\",\n \"component\": \"DisplayField\",\n \"label\": \"Card on file\",\n \"value\": \"•••• •••• •••• 4242\",\n \"variant\": \"masked\",\n \"icon\": \"lock\",\n \"hint\": \"Expires 12/26\"\n }\n]",
9163
+ "name": "card-on-file"
9164
+ },
9165
+ {
9166
+ "description": "A labeled slot hosting a third-party element (e.g. a Stripe Element mount).",
9167
+ "a2ui": "[\n {\n \"id\": \"root\",\n \"component\": \"DisplayField\",\n \"label\": \"Card number\",\n \"children\": [\"mount\"]\n },\n { \"id\": \"mount\", \"component\": \"Text\", \"text\": \"[Stripe Element mounts here]\" }\n]",
9168
+ "name": "foreign-element-slot"
9169
+ }
9170
+ ],
9171
+ "keywords": [
9172
+ "display field",
9173
+ "readonly",
9174
+ "read-only",
9175
+ "masked",
9176
+ "mask",
9177
+ "static value",
9178
+ "card on file",
9179
+ "last four",
9180
+ "value",
9181
+ "readout",
9182
+ "stripe element",
9183
+ "iframe slot",
9184
+ "non-editable"
9185
+ ],
9186
+ "name": "UIDisplayField",
9187
+ "related": [
9188
+ "field",
9189
+ "input",
9190
+ "stat",
9191
+ "description-list"
9192
+ ],
9193
+ "slots": {
9194
+ "default": {
9195
+ "description": "The value content. Slot a third-party element here — a Stripe Element iframe mount, or rich markup — and it takes the value region under the label, replacing the [value] attribute. The host's role=\"group\" + aria-labelledby names it for assistive tech."
9196
+ },
9197
+ "hint": {
9198
+ "description": "The hint caption below the value. Auto-stamped from the [hint] attribute; wired into aria-describedby."
9199
+ },
9200
+ "icon": {
9201
+ "description": "The leading icon (a single icon-ui). Auto-stamped from the [icon] attribute."
9202
+ },
9203
+ "label": {
9204
+ "description": "The caption element. Auto-stamped from the [label] attribute; slot your own [slot=\"label\"] child to override with richer markup. It is the group's accessible name (the aria-labelledby target)."
9205
+ },
9206
+ "value": {
9207
+ "description": "The static value element. Auto-stamped from the [value] attribute; suppressed when the default slot carries foreign content."
9208
+ }
9209
+ },
9210
+ "states": [
9211
+ {
9212
+ "description": "Default, non-interactive read-out.",
9213
+ "name": "idle"
9214
+ }
9215
+ ],
9216
+ "status": "stable",
9217
+ "synonyms": {
9218
+ "masked": [
9219
+ "display field",
9220
+ "field",
9221
+ "value"
9222
+ ],
9223
+ "readout": [
9224
+ "display field",
9225
+ "stat",
9226
+ "field"
9227
+ ],
9228
+ "value": [
9229
+ "display field",
9230
+ "field",
9231
+ "stat"
9232
+ ]
9233
+ },
9234
+ "tag": "display-field-ui",
9235
+ "tokens": {
9236
+ "--display-field-gap": {
9237
+ "description": "Vertical gap between the label, value, and hint rows."
9238
+ },
9239
+ "--display-field-hint-color": {
9240
+ "description": "Hint foreground color."
9241
+ },
9242
+ "--display-field-hint-size": {
9243
+ "description": "Hint font size."
9244
+ },
9245
+ "--display-field-icon-gap": {
9246
+ "description": "Horizontal gap between the leading icon and the value."
9247
+ },
9248
+ "--display-field-label-color": {
9249
+ "description": "Label foreground color."
9250
+ },
9251
+ "--display-field-label-size": {
9252
+ "description": "Label font size."
9253
+ },
9254
+ "--display-field-label-weight": {
9255
+ "description": "Label font weight."
9256
+ },
9257
+ "--display-field-masked-font": {
9258
+ "description": "Font family applied to a masked value."
9259
+ },
9260
+ "--display-field-masked-tracking": {
9261
+ "description": "Letter-spacing applied to a masked value."
9262
+ },
9263
+ "--display-field-value-color": {
9264
+ "description": "Value foreground color."
9265
+ },
9266
+ "--display-field-value-size": {
9267
+ "description": "Value font size."
9268
+ },
9269
+ "--display-field-value-weight": {
9270
+ "description": "Value font weight."
9271
+ }
9272
+ },
9273
+ "traits": [],
9274
+ "version": 1
9275
+ }
9276
+ },
9056
9277
  "Divider": {
9057
9278
  "title": "Divider",
9058
9279
  "description": "Horizontal or vertical divider with optional label — a semantic\nrule between content groups. Set [vertical] for column dividers\n(typically inside <row-ui>); set [label] for a labeled-rule pattern\nwhere the divider carries a short caption (e.g. \"OR\" between auth\nmethods, \"Today\" between message groups). Distinct from\n<hr data-nav-divider> (which is a CSS hook used by <nav-ui> for nav\nsection separation, not a primitive).\n",
@@ -10290,7 +10511,7 @@
10290
10511
  },
10291
10512
  "Feed": {
10292
10513
  "title": "Feed",
10293
- "description": "Shared top-layer feed channel. Per docs/specs/feed-channel.md (SPEC-FEED-CHANNEL-001). Per-position singletons mounted lazily into document.body via Popover API; consumers post via the static API (`UIFeed.post()`) or the global 'feed' CustomEvent.",
10514
+ "description": "Shared top-layer feed channel. Per .claude/docs/specs/feed-channel.md (SPEC-FEED-CHANNEL-001). Per-position singletons mounted lazily into document.body via Popover API; consumers post via the static API (`UIFeed.post()`) or the global 'feed' CustomEvent.",
10294
10515
  "type": "object",
10295
10516
  "allOf": [
10296
10517
  {
@@ -12801,7 +13022,7 @@
12801
13022
  },
12802
13023
  "IntegrationsPage": {
12803
13024
  "title": "IntegrationsPage",
12804
- "description": "Module-tier Settings page composite — a searchable, category-grouped\ngrid of <integration-card-ui> tiles (SPEC-062). Owns the\n`integrations` array, the search-filter state, the category /\nstatus grouping, the responsive grid breakpoints, and the empty-state\ncopy. Card-level events (`connect` / `configure` / `disconnect` /\n`retry`) bubble up unchanged with `provider` in detail; the page also\nemits `search` (debounced) and a top-bar `filter-change` when the\nuser picks a status chip.\n\nLives in `packages/web-modules/settings/integrations-page/` per the\nthree-tier architecture — composes multiple primitives, holds layout\nresponsibility, consumed by the settings shell. Replaces the\nhand-rolled `settings/integrations` HTML template per consumer.\n\nSpec: docs/specs/implementation-ready/SPEC-063-integrations-page.md\n",
13025
+ "description": "Module-tier Settings page composite — a searchable, category-grouped\ngrid of <integration-card-ui> tiles (SPEC-062). Owns the\n`integrations` array, the search-filter state, the category /\nstatus grouping, the responsive grid breakpoints, and the empty-state\ncopy. Card-level events (`connect` / `configure` / `disconnect` /\n`retry`) bubble up unchanged with `provider` in detail; the page also\nemits `search` (debounced) and a top-bar `filter-change` when the\nuser picks a status chip.\n\nLives in `packages/web-modules/settings/integrations-page/` per the\nthree-tier architecture — composes multiple primitives, holds layout\nresponsibility, consumed by the settings shell. Replaces the\nhand-rolled `settings/integrations` HTML template per consumer.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-063-integrations-page.md\n",
12805
13026
  "type": "object",
12806
13027
  "allOf": [
12807
13028
  {
@@ -13073,7 +13294,7 @@
13073
13294
  },
13074
13295
  "InvoiceDetail": {
13075
13296
  "title": "InvoiceDetail",
13076
- "description": "Module-tier page composite that renders a single invoice — header\n(number + status badge + dates), line-items table, totals block,\ncustomer + remit-to blocks, and a slot-driven action toolbar.\nThe canonical invoice layout shared by billing-enabled products\nso totals math, status-badge color mapping, and action-toolbar\norder do not drift across surfaces.\n\nData-driven via the `invoice` property OR a `data-stream-src`\nendpoint. The composite stamps a six-region skeleton once on\nfirst connect — header · meta · parties · lines · totals ·\nfooter — then mutates per-region nodes via id-keyed in-place\ndiff on every property change. The status badge color maps\nfrom `invoice.status` (paid → success, past-due → warning,\nvoid → muted, open/draft → default). Action buttons are\nconsumer-slotted into `header-actions` per spec OD-002 (always\nslot, never stamp a default toolbar).\n\nPrint-friendly: an internal `@media print` branch hides the\naction toolbar + zeroes the page padding. The composite is a\ndisplay surface — extends UIElement, not UIFormElement.\n\nSpec: docs/specs/implementation-ready/SPEC-007-invoice-detail-page.md.\n",
13297
+ "description": "Module-tier page composite that renders a single invoice — header\n(number + status badge + dates), line-items table, totals block,\ncustomer + remit-to blocks, and a slot-driven action toolbar.\nThe canonical invoice layout shared by billing-enabled products\nso totals math, status-badge color mapping, and action-toolbar\norder do not drift across surfaces.\n\nData-driven via the `invoice` property OR a `data-stream-src`\nendpoint. The composite stamps a six-region skeleton once on\nfirst connect — header · meta · parties · lines · totals ·\nfooter — then mutates per-region nodes via id-keyed in-place\ndiff on every property change. The status badge color maps\nfrom `invoice.status` (paid → success, past-due → warning,\nvoid → muted, open/draft → default). Action buttons are\nconsumer-slotted into `header-actions` per spec OD-002 (always\nslot, never stamp a default toolbar).\n\nPrint-friendly: an internal `@media print` branch hides the\naction toolbar + zeroes the page padding. The composite is a\ndisplay surface — extends UIElement, not UIFormElement.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-007-invoice-detail-page.md.\n",
13077
13298
  "type": "object",
13078
13299
  "allOf": [
13079
13300
  {
@@ -13347,7 +13568,7 @@
13347
13568
  },
13348
13569
  "InvoiceHistory": {
13349
13570
  "title": "InvoiceHistory",
13350
- "description": "Canonical billing-list composite — a pre-configured <table-ui> with\ninvoice-shaped columns (number, issued, due, amount, status, actions),\nstatus-badge cell renderer (paid/open/past-due/void/draft → semantic\nbadge variant), currency cell renderer, optional search + filter\nchips via <table-toolbar-ui>, and a row-click that navigates to the\ninvoice detail page.\n\nWraps <table-ui> with billing-shaped columns + cell renderers + a\nCSV-export toolbar. Consumer passes invoices[]; the composite owns\ncolumn shape, status-to-badge mapping, currency formatting, date\nformatting, and navigation. Sibling to SPEC-007 (invoice detail).\n\nEach invoice record: {id, number, status, issuedAt, dueAt, amount,\ncurrency}. status MUST be one of \"draft\" | \"open\" | \"paid\" |\n\"past-due\" | \"void\"; unknown values fall back to a neutral badge.\n\nSpec: docs/specs/implementation-ready/SPEC-008-invoice-history-table.md.\n",
13571
+ "description": "Canonical billing-list composite — a pre-configured <table-ui> with\ninvoice-shaped columns (number, issued, due, amount, status, actions),\nstatus-badge cell renderer (paid/open/past-due/void/draft → semantic\nbadge variant), currency cell renderer, optional search + filter\nchips via <table-toolbar-ui>, and a row-click that navigates to the\ninvoice detail page.\n\nWraps <table-ui> with billing-shaped columns + cell renderers + a\nCSV-export toolbar. Consumer passes invoices[]; the composite owns\ncolumn shape, status-to-badge mapping, currency formatting, date\nformatting, and navigation. Sibling to SPEC-007 (invoice detail).\n\nEach invoice record: {id, number, status, issuedAt, dueAt, amount,\ncurrency}. status MUST be one of \"draft\" | \"open\" | \"paid\" |\n\"past-due\" | \"void\"; unknown values fall back to a neutral badge.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-008-invoice-history-table.md.\n",
13351
13572
  "type": "object",
13352
13573
  "allOf": [
13353
13574
  {
@@ -15797,7 +16018,7 @@
15797
16018
  },
15798
16019
  "NotificationPreferences": {
15799
16020
  "title": "NotificationPreferences",
15800
- "description": "Page-level Settings composite: a matrix of notification types (rows)\n× delivery channels (columns: in-app, email, SMS) with a binary\n<check-ui> in each cell and an optional <switch-ui> column-header\nmaster toggle for bulk-flipping a channel across every row.\n\nForm-bearing — the composite extends UIFormElement and serializes its\ncurrent preferences shape as JSON on `value`. Per first-principle #2\n(\"save is the consumer's job\"), the composite does NOT mutate the\npassed-in `preferences` array; it emits a typed `change` event per\ncell toggle and a `bulk-toggle` event per column-header switch, and\nexposes the staged JSON via the form value so a host <form> submit\ncarries it through ElementInternals.\n\nChannels are columns; types are rows (the smaller-set / larger-set\ninvariant — channels are 3-5 in the wild, types are 10-50). Layout\nrenders as a semantic ARIA grid (`role=\"table\"`/`row`/`cell`/\n`rowheader`/`columnheader`) — NOT native `<table>` (per the HTML\nparser strip rule, table-content tags would foster-parent out of a\ncustom-element subtree).\n\nSpec: docs/specs/implementation-ready/SPEC-064-notification-preferences.md.\n",
16021
+ "description": "Page-level Settings composite: a matrix of notification types (rows)\n× delivery channels (columns: in-app, email, SMS) with a binary\n<check-ui> in each cell and an optional <switch-ui> column-header\nmaster toggle for bulk-flipping a channel across every row.\n\nForm-bearing — the composite extends UIFormElement and serializes its\ncurrent preferences shape as JSON on `value`. Per first-principle #2\n(\"save is the consumer's job\"), the composite does NOT mutate the\npassed-in `preferences` array; it emits a typed `change` event per\ncell toggle and a `bulk-toggle` event per column-header switch, and\nexposes the staged JSON via the form value so a host <form> submit\ncarries it through ElementInternals.\n\nChannels are columns; types are rows (the smaller-set / larger-set\ninvariant — channels are 3-5 in the wild, types are 10-50). Layout\nrenders as a semantic ARIA grid (`role=\"table\"`/`row`/`cell`/\n`rowheader`/`columnheader`) — NOT native `<table>` (per the HTML\nparser strip rule, table-content tags would foster-parent out of a\ncustom-element subtree).\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-064-notification-preferences.md.\n",
15801
16022
  "type": "object",
15802
16023
  "allOf": [
15803
16024
  {
@@ -17382,7 +17603,7 @@
17382
17603
  },
17383
17604
  "PaymentMethodForm": {
17384
17605
  "title": "PaymentMethodForm",
17385
- "description": "Form-participating composite for capturing a payment method —\ncard number, expiry, CVC, name on card, billing address (optional),\nand country. The form chrome + structured validation + a single\nnormalized emit event; it does NOT integrate with Stripe Elements\nor a tokenization SDK directly (consumer responsibility).\n\nEach sub-field is a <field-ui> wrapper around an <input-ui> (or\n<select-ui> for country). Card number is Luhn-validated; expiry is\nparsed as MM/YY with month + year bounds; CVC is 3-4 digits.\nBrand detection (visa / mastercard / amex / discover) runs against\na small regex map and surfaces via the `change` event detail.\n\nForm value is a JSON-encoded payload of normalized field values\nserialized through ElementInternals under [name] (default\n\"paymentMethod\"). On submit, the host fires\n`submit-payment-method` with a flat detail\n`{ token, last4, brand, expMonth, expYear, name, country }`.\n`token` is a synthetic local-mode token (sha-like opaque string);\nconsumers integrating with a real processor handle tokenization\nin their own submit listener using `last4` / `brand` / etc.\n\nSpec: docs/specs/implementation-ready/SPEC-009-payment-method-form.md.\n",
17606
+ "description": "Form-participating composite for capturing a payment method —\ncard number, expiry, CVC, name on card, billing address (optional),\nand country. The form chrome + structured validation + a single\nnormalized emit event; it does NOT integrate with Stripe Elements\nor a tokenization SDK directly (consumer responsibility).\n\nEach sub-field is a <field-ui> wrapper around an <input-ui> (or\n<select-ui> for country). Card number is Luhn-validated; expiry is\nparsed as MM/YY with month + year bounds; CVC is 3-4 digits.\nBrand detection (visa / mastercard / amex / discover) runs against\na small regex map and surfaces via the `change` event detail.\n\nForm value is a JSON-encoded payload of normalized field values\nserialized through ElementInternals under [name] (default\n\"paymentMethod\"). On submit, the host fires\n`submit-payment-method` with a flat detail\n`{ token, last4, brand, expMonth, expYear, name, country }`.\n`token` is a synthetic local-mode token (sha-like opaque string);\nconsumers integrating with a real processor handle tokenization\nin their own submit listener using `last4` / `brand` / etc.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-009-payment-method-form.md.\n",
17386
17607
  "type": "object",
17387
17608
  "allOf": [
17388
17609
  {
@@ -17685,7 +17906,7 @@
17685
17906
  },
17686
17907
  "PaymentMethodList": {
17687
17908
  "title": "PaymentMethodList",
17688
- "description": "Compound billing primitive that renders the user's saved payment\nmethods (cards, bank accounts, wallets) as a vertical list with one\nrow designated as the default. Each row shows a brand mark, the\nlast-4 / account identifier, an optional expiry, and per-row actions\n(set-default / edit / remove). A trailing \"Add payment method\" CTA\nemits `add` so consumers can route the consumer flow.\n\nDefault is a strict 1-of-N radiogroup — exactly one row carries the\ndefault state when the list is non-empty. The primitive does NOT\nmutate the data source; all changes flow as events (`change`,\n`add`, `remove`, `select`) and the consumer applies the side\neffect against their billing API.\n\nSpec: docs/specs/implementation-ready/SPEC-010-payment-method-list.md.\n",
17909
+ "description": "Compound billing primitive that renders the user's saved payment\nmethods (cards, bank accounts, wallets) as a vertical list with one\nrow designated as the default. Each row shows a brand mark, the\nlast-4 / account identifier, an optional expiry, and per-row actions\n(set-default / edit / remove). A trailing \"Add payment method\" CTA\nemits `add` so consumers can route the consumer flow.\n\nDefault is a strict 1-of-N radiogroup — exactly one row carries the\ndefault state when the list is non-empty. The primitive does NOT\nmutate the data source; all changes flow as events (`change`,\n`add`, `remove`, `select`) and the consumer applies the side\neffect against their billing API.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-010-payment-method-list.md.\n",
17689
17910
  "type": "object",
17690
17911
  "allOf": [
17691
17912
  {
@@ -18066,7 +18287,7 @@
18066
18287
  },
18067
18288
  "PlanPicker": {
18068
18289
  "title": "PlanPicker",
18069
- "description": "A form-participating chooser of one of N billing plans. The canonical\nplan-card grid used by both in-app upgrade modals and marketing\npricing pages (SPEC-012 composes this primitive as its core), so\nbenefit copy, pricing strings, recommendation highlighting, and the\nbilling-cycle toggle never drift between surfaces.\n\nEach plan record carries a stable id, name, optional tagline + icon,\na per-cycle price object, a feature list, and optional flags\n(recommended, rank, disabled). One plan may carry recommended:true\n(accent border + tinted bg + shadow); a host-level `current` id\nmarks the user's current plan (muted bg, \"Current plan\" tag, no\nChoose CTA, contextual \"Upgrade\"/\"Downgrade\" labels on siblings).\n\nLayout is grid by default (marketing surfaces) and `layout=\"list\"`\nfor in-app settings panels. The optional `cycle-toggle` boolean\nrenders an internal <segmented-ui> that swaps prices between\nmonthly and annual cycles in place across every card.\n\nSpec: docs/specs/implementation-ready/SPEC-011-plan-picker-in-app-upgrade.md.\n",
18290
+ "description": "A form-participating chooser of one of N billing plans. The canonical\nplan-card grid used by both in-app upgrade modals and marketing\npricing pages (SPEC-012 composes this primitive as its core), so\nbenefit copy, pricing strings, recommendation highlighting, and the\nbilling-cycle toggle never drift between surfaces.\n\nEach plan record carries a stable id, name, optional tagline + icon,\na per-cycle price object, a feature list, and optional flags\n(recommended, rank, disabled). One plan may carry recommended:true\n(accent border + tinted bg + shadow); a host-level `current` id\nmarks the user's current plan (muted bg, \"Current plan\" tag, no\nChoose CTA, contextual \"Upgrade\"/\"Downgrade\" labels on siblings).\n\nLayout is grid by default (marketing surfaces) and `layout=\"list\"`\nfor in-app settings panels. The optional `cycle-toggle` boolean\nrenders an internal <segmented-ui> that swaps prices between\nmonthly and annual cycles in place across every card.\n\nSpec: .claude/docs/specs/implementation-ready/SPEC-011-plan-picker-in-app-upgrade.md.\n",
18070
18291
  "type": "object",
18071
18292
  "allOf": [
18072
18293
  {
@@ -24838,7 +25059,7 @@
24838
25059
  },
24839
25060
  "ThemePanel": {
24840
25061
  "title": "ThemePanel",
24841
- "description": "Module-tier appearance-preferences control surface. Owns the three knobs\nof the AdiaUI theming contract: [theme=<slug>] named themes,\n--a-density / --a-radius-k parametric overrides, and color-scheme\nlight/dark switching, plus optional localStorage persistence behind a\nsmall attribute API.\n\nDrops into any consumer's <popover-ui slot=\"content\"> (the canonical\ncomposition) or directly into a sidebar section. Eight named themes\nship by default; section visibility flips on/off via boolean attributes\n([parametric], [presets], [scheme-toggle]).\n\nPromoted from the duplicated <div id=\"theme-panel\"> block in site/ and\nplaygrounds/admin-shell/ — see docs/specs/theme-panel-module.md.\n",
25062
+ "description": "Module-tier appearance-preferences control surface. Owns the three knobs\nof the AdiaUI theming contract: [theme=<slug>] named themes,\n--a-density / --a-radius-k parametric overrides, and color-scheme\nlight/dark switching, plus optional localStorage persistence behind a\nsmall attribute API.\n\nDrops into any consumer's <popover-ui slot=\"content\"> (the canonical\ncomposition) or directly into a sidebar section. Eight named themes\nship by default; section visibility flips on/off via boolean attributes\n([parametric], [presets], [scheme-toggle]).\n\nPromoted from the duplicated <div id=\"theme-panel\"> block in site/ and\nplaygrounds/admin-shell/ — see .claude/docs/specs/theme-panel-module.md.\n",
24842
25063
  "type": "object",
24843
25064
  "allOf": [
24844
25065
  {
@@ -8,11 +8,13 @@
8
8
  - Child of <accordion-ui> — places one collapsible section with header + body.
9
9
  - Toggle behavior: click anywhere on the row toggles, unless inside [slot='actions'] or [data-no-toggle].
10
10
  - For single-button disclosures (one expanding panel without a list) use <details>/<summary> or compose <button-ui> + <section-ui>.
11
+ - An item inherits its host accordion-ui's [variant]; set variant="flat" or variant="contained" directly on ONE item to override just that item against the host.
11
12
 
12
13
  ## Accordion
13
14
  - Hosts <accordion-item-ui> children. One or more sections may be open simultaneously (set single= to enforce only-one-open).
14
15
  - For tab-switched panels (always exactly one open) use <tabs-ui>; accordion supports zero-open and multi-open.
15
16
  - Item ordering is DOM-order; no auto-sort.
17
+ - Set variant="contained" for a bounded per-item surface (background, border, radius, and an open-state divider) — the composition to reach for when nesting inside <card-ui>. Default variant="flat" (no chrome) suits settings pages and FAQ blocks sitting on the page canvas.
16
18
 
17
19
  ## ActionItem
18
20
  - Child of <action-list-ui> — one inline-action row with icon + label + optional shortcut + optional sublabel.
@@ -229,6 +231,11 @@
229
231
  - Do not use for editable forms — use <fields-ui> instead.
230
232
  - Pairs render as label + value on the same row by default; use vertical variant for narrow panes.
231
233
 
234
+ ## DisplayField
235
+ - Use for a display-ONLY labeled value — a masked card number, a 'card on file' read-out, an account id — anywhere a value reads as a field but must not be editable.
236
+ - To host a third-party element (a Stripe Element iframe) under a label, slot it as the default child instead of setting value=. The label names it via role=group + aria-labelledby.
237
+ - For an editable field use field-ui + input-ui; for a prominent KPI use stat-ui; for many read-only pairs at once use description-list-ui.
238
+
232
239
  ## Divider
233
240
  - Use to separate visually distinct sections within a container; horizontal default, vertical via orientation='vertical'.
234
241
  - Inside menus / popovers use <menu-divider-ui> instead; it has menu-specific token spacing.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@adia-ai/a2ui-corpus",
3
- "version": "0.7.23",
3
+ "version": "0.7.25",
4
4
  "type": "module",
5
5
  "description": "AdiaUI A2UI training corpus \u2014 canonical v0.9 catalog + chunks + eval fixtures + feedback + gap registry. Consumed by the compose engine's retrieval layer + the MCP pipeline.",
6
6
  "exports": {
@@ -8,7 +8,7 @@
8
8
  * - packages/a2ui/mcp/server.js — exposes search_chunks / get_chunk / lookup_chunk tools
9
9
  * - packages/a2ui/compose/strategies/zettel/chunk-synthesizer.js — Phase C.2
10
10
  *
11
- * Spec: docs/specs/genui-chunk-marker.md (Draft v0.1.0).
11
+ * Spec: .claude/docs/specs/genui-chunk-marker.md (Draft v0.1.0).
12
12
  */
13
13
 
14
14
  import { readFileSync, readdirSync, existsSync } from 'node:fs';