@bestagentkits/render 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +29 -0
- package/LICENSE +21 -0
- package/README.md +166 -0
- package/dist/cli.d.ts +18 -0
- package/dist/cli.d.ts.map +1 -0
- package/dist/cli.js +336 -0
- package/dist/cli.js.map +1 -0
- package/dist/diagnostics.d.ts +45 -0
- package/dist/diagnostics.d.ts.map +1 -0
- package/dist/diagnostics.js +57 -0
- package/dist/diagnostics.js.map +1 -0
- package/dist/diagram/adapter.d.ts +71 -0
- package/dist/diagram/adapter.d.ts.map +1 -0
- package/dist/diagram/adapter.js +87 -0
- package/dist/diagram/adapter.js.map +1 -0
- package/dist/errors.d.ts +37 -0
- package/dist/errors.d.ts.map +1 -0
- package/dist/errors.js +42 -0
- package/dist/errors.js.map +1 -0
- package/dist/hash.d.ts +14 -0
- package/dist/hash.d.ts.map +1 -0
- package/dist/hash.js +27 -0
- package/dist/hash.js.map +1 -0
- package/dist/index.d.ts +43 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +25 -0
- package/dist/index.js.map +1 -0
- package/dist/internal/yaml-error.d.ts +14 -0
- package/dist/internal/yaml-error.d.ts.map +1 -0
- package/dist/internal/yaml-error.js +12 -0
- package/dist/internal/yaml-error.js.map +1 -0
- package/dist/ir.d.ts +77 -0
- package/dist/ir.d.ts.map +1 -0
- package/dist/ir.js +20 -0
- package/dist/ir.js.map +1 -0
- package/dist/json.d.ts +23 -0
- package/dist/json.d.ts.map +1 -0
- package/dist/json.js +47 -0
- package/dist/json.js.map +1 -0
- package/dist/registry/actions.d.ts +48 -0
- package/dist/registry/actions.d.ts.map +1 -0
- package/dist/registry/actions.js +274 -0
- package/dist/registry/actions.js.map +1 -0
- package/dist/registry/prop-schema.d.ts +108 -0
- package/dist/registry/prop-schema.d.ts.map +1 -0
- package/dist/registry/prop-schema.js +400 -0
- package/dist/registry/prop-schema.js.map +1 -0
- package/dist/registry/registry.d.ts +47 -0
- package/dist/registry/registry.d.ts.map +1 -0
- package/dist/registry/registry.js +201 -0
- package/dist/registry/registry.js.map +1 -0
- package/dist/registry/roster.d.ts +53 -0
- package/dist/registry/roster.d.ts.map +1 -0
- package/dist/registry/roster.js +692 -0
- package/dist/registry/roster.js.map +1 -0
- package/dist/render/blocks.d.ts +41 -0
- package/dist/render/blocks.d.ts.map +1 -0
- package/dist/render/blocks.js +749 -0
- package/dist/render/blocks.js.map +1 -0
- package/dist/render/charts.d.ts +29 -0
- package/dist/render/charts.d.ts.map +1 -0
- package/dist/render/charts.js +235 -0
- package/dist/render/charts.js.map +1 -0
- package/dist/render/document.d.ts +40 -0
- package/dist/render/document.d.ts.map +1 -0
- package/dist/render/document.js +90 -0
- package/dist/render/document.js.map +1 -0
- package/dist/render/escape.d.ts +46 -0
- package/dist/render/escape.d.ts.map +1 -0
- package/dist/render/escape.js +108 -0
- package/dist/render/escape.js.map +1 -0
- package/dist/render/render.d.ts +52 -0
- package/dist/render/render.d.ts.map +1 -0
- package/dist/render/render.js +216 -0
- package/dist/render/render.js.map +1 -0
- package/dist/render/runtime.d.ts +25 -0
- package/dist/render/runtime.d.ts.map +1 -0
- package/dist/render/runtime.js +451 -0
- package/dist/render/runtime.js.map +1 -0
- package/dist/render/styles.d.ts +15 -0
- package/dist/render/styles.d.ts.map +1 -0
- package/dist/render/styles.js +163 -0
- package/dist/render/styles.js.map +1 -0
- package/dist/render/verify.d.ts +25 -0
- package/dist/render/verify.d.ts.map +1 -0
- package/dist/render/verify.js +168 -0
- package/dist/render/verify.js.map +1 -0
- package/dist/spec/bindings.d.ts +19 -0
- package/dist/spec/bindings.d.ts.map +1 -0
- package/dist/spec/bindings.js +51 -0
- package/dist/spec/bindings.js.map +1 -0
- package/dist/spec/bounds.d.ts +43 -0
- package/dist/spec/bounds.d.ts.map +1 -0
- package/dist/spec/bounds.js +144 -0
- package/dist/spec/bounds.js.map +1 -0
- package/dist/spec/forbidden.d.ts +27 -0
- package/dist/spec/forbidden.d.ts.map +1 -0
- package/dist/spec/forbidden.js +91 -0
- package/dist/spec/forbidden.js.map +1 -0
- package/dist/spec/migrate.d.ts +33 -0
- package/dist/spec/migrate.d.ts.map +1 -0
- package/dist/spec/migrate.js +113 -0
- package/dist/spec/migrate.js.map +1 -0
- package/dist/spec/normalize.d.ts +29 -0
- package/dist/spec/normalize.d.ts.map +1 -0
- package/dist/spec/normalize.js +649 -0
- package/dist/spec/normalize.js.map +1 -0
- package/dist/spec/parse.d.ts +22 -0
- package/dist/spec/parse.d.ts.map +1 -0
- package/dist/spec/parse.js +62 -0
- package/dist/spec/parse.js.map +1 -0
- package/dist/spec/providers.d.ts +30 -0
- package/dist/spec/providers.d.ts.map +1 -0
- package/dist/spec/providers.js +64 -0
- package/dist/spec/providers.js.map +1 -0
- package/dist/spec/validate.d.ts +28 -0
- package/dist/spec/validate.d.ts.map +1 -0
- package/dist/spec/validate.js +68 -0
- package/dist/spec/validate.js.map +1 -0
- package/dist/theme/load-theme.d.ts +55 -0
- package/dist/theme/load-theme.d.ts.map +1 -0
- package/dist/theme/load-theme.js +219 -0
- package/dist/theme/load-theme.js.map +1 -0
- package/dist/theme/presets.d.ts +50 -0
- package/dist/theme/presets.d.ts.map +1 -0
- package/dist/theme/presets.js +304 -0
- package/dist/theme/presets.js.map +1 -0
- package/dist/theme/theme-catalog.d.ts +68 -0
- package/dist/theme/theme-catalog.d.ts.map +1 -0
- package/dist/theme/theme-catalog.js +198 -0
- package/dist/theme/theme-catalog.js.map +1 -0
- package/dist/theme/tokens.d.ts +38 -0
- package/dist/theme/tokens.d.ts.map +1 -0
- package/dist/theme/tokens.js +190 -0
- package/dist/theme/tokens.js.map +1 -0
- package/dist/version.d.ts +12 -0
- package/dist/version.d.ts.map +1 -0
- package/dist/version.js +12 -0
- package/dist/version.js.map +1 -0
- package/package.json +80 -0
|
@@ -0,0 +1,163 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Emitted stylesheets.
|
|
3
|
+
*
|
|
4
|
+
* One base sheet plus per-feature sheets. The compiler emits only the feature
|
|
5
|
+
* sheets a page actually uses, which is both a size win and a correctness
|
|
6
|
+
* property: a page without a carousel cannot ship carousel CSS that a later
|
|
7
|
+
* change could accidentally apply.
|
|
8
|
+
*
|
|
9
|
+
* The sheets are static strings with no interpolation. Everything variable
|
|
10
|
+
* comes from theme tokens, so a spec cannot influence a declaration.
|
|
11
|
+
*/
|
|
12
|
+
export const BASE_CSS = `*,*::before,*::after{box-sizing:border-box}
|
|
13
|
+
html{-webkit-text-size-adjust:100%}
|
|
14
|
+
body{margin:0;background:var(--ak-color-background);color:var(--ak-color-text);font-family:var(--ak-font-body);font-size:var(--ak-font-size-base);line-height:var(--ak-line-height)}
|
|
15
|
+
.ak-skip{position:absolute;left:-9999px;top:0;background:var(--ak-color-surface);color:var(--ak-color-text);padding:calc(var(--ak-space-unit) * 1.5);z-index:10}
|
|
16
|
+
.ak-skip:focus{left:0}
|
|
17
|
+
.ak-shell{max-width:1100px;margin:0 auto;padding:calc(var(--ak-space-unit) * 3) calc(var(--ak-space-unit) * 2) calc(var(--ak-space-unit) * 8)}
|
|
18
|
+
.ak-main{display:block}
|
|
19
|
+
:where(a){color:var(--ak-color-accent)}
|
|
20
|
+
:where(h1,h2,h3,h4,h5,h6){font-family:var(--ak-font-heading);line-height:1.2;margin:0}
|
|
21
|
+
h1{font-size:calc(var(--ak-font-size-base) * 2.1)}
|
|
22
|
+
h2{font-size:calc(var(--ak-font-size-base) * 1.6)}
|
|
23
|
+
h3{font-size:calc(var(--ak-font-size-base) * 1.3)}
|
|
24
|
+
h4,h5,h6{font-size:calc(var(--ak-font-size-base) * 1.1)}
|
|
25
|
+
p{margin:0}
|
|
26
|
+
ul,ol{margin:0;padding-left:1.4em}
|
|
27
|
+
code,kbd{font-family:var(--ak-font-mono)}
|
|
28
|
+
:focus-visible{outline:2px solid var(--ak-color-accent);outline-offset:2px}
|
|
29
|
+
.ak-block + .ak-block{margin-top:calc(var(--ak-space-unit) * 3)}
|
|
30
|
+
[data-density="compact"] .ak-block + .ak-block{margin-top:calc(var(--ak-space-unit) * 2)}
|
|
31
|
+
[data-density="spacious"] .ak-block + .ak-block{margin-top:calc(var(--ak-space-unit) * 4)}
|
|
32
|
+
.ak-stack{display:flex;flex-direction:column;gap:calc(var(--ak-space-unit) * 2)}
|
|
33
|
+
.ak-stack[data-gap="tight"]{gap:var(--ak-space-unit)}
|
|
34
|
+
.ak-stack[data-gap="loose"]{gap:calc(var(--ak-space-unit) * 3)}
|
|
35
|
+
.ak-grid{display:grid;gap:calc(var(--ak-space-unit) * 2);grid-template-columns:repeat(3,minmax(0,1fr))}
|
|
36
|
+
.ak-grid[data-ak-columns="1"],.ak-gallery[data-ak-columns="1"]{grid-template-columns:minmax(0,1fr)}
|
|
37
|
+
.ak-grid[data-ak-columns="2"],.ak-gallery[data-ak-columns="2"]{grid-template-columns:repeat(2,minmax(0,1fr))}
|
|
38
|
+
.ak-grid[data-ak-columns="3"],.ak-gallery[data-ak-columns="3"]{grid-template-columns:repeat(3,minmax(0,1fr))}
|
|
39
|
+
.ak-grid[data-ak-columns="4"],.ak-gallery[data-ak-columns="4"]{grid-template-columns:repeat(4,minmax(0,1fr))}
|
|
40
|
+
.ak-grid[data-ak-columns="5"],.ak-gallery[data-ak-columns="5"]{grid-template-columns:repeat(5,minmax(0,1fr))}
|
|
41
|
+
.ak-grid[data-ak-columns="6"],.ak-gallery[data-ak-columns="6"]{grid-template-columns:repeat(6,minmax(0,1fr))}
|
|
42
|
+
.ak-split{display:grid;gap:calc(var(--ak-space-unit) * 2);grid-template-columns:1fr 1fr}
|
|
43
|
+
.ak-split[data-ratio="wide-left"]{grid-template-columns:2fr 1fr}
|
|
44
|
+
.ak-split[data-ratio="wide-right"]{grid-template-columns:1fr 2fr}
|
|
45
|
+
.ak-muted{color:var(--ak-color-text-muted)}
|
|
46
|
+
.ak-eyebrow,.ak-label{font-family:var(--ak-font-mono);font-size:.78rem;letter-spacing:.08em;text-transform:uppercase;color:var(--ak-color-text-muted)}
|
|
47
|
+
.ak-hero{gap:var(--ak-space-unit);display:flex;flex-direction:column}
|
|
48
|
+
.ak-hero h1{max-width:var(--ak-measure)}
|
|
49
|
+
.ak-hero p{max-width:var(--ak-measure);font-size:calc(var(--ak-font-size-base) * 1.1);color:var(--ak-color-text-muted)}
|
|
50
|
+
.ak-lead{font-size:calc(var(--ak-font-size-base) * 1.15)}
|
|
51
|
+
.ak-caption{font-size:.85rem;color:var(--ak-color-text-muted)}
|
|
52
|
+
.ak-prose{max-width:var(--ak-measure)}
|
|
53
|
+
.ak-card,.ak-surface{background:var(--ak-color-surface);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-medium);padding:calc(var(--ak-space-unit) * 2)}
|
|
54
|
+
.ak-card{display:flex;flex-direction:column;gap:var(--ak-space-unit)}
|
|
55
|
+
.ak-card--elevated,.ak-surface{box-shadow:var(--ak-elevation-card)}
|
|
56
|
+
.ak-section-head{display:flex;flex-direction:column;gap:.35em;margin-bottom:calc(var(--ak-space-unit) * 1.5)}
|
|
57
|
+
.ak-divider{border:0;border-top:var(--ak-border-width) solid var(--ak-color-border);margin:calc(var(--ak-space-unit) * 2) 0;display:flex;align-items:center;gap:var(--ak-space-unit)}
|
|
58
|
+
.ak-spacer{display:block}
|
|
59
|
+
.ak-spacer[data-size="small"]{height:var(--ak-space-unit)}
|
|
60
|
+
.ak-spacer[data-size="medium"]{height:calc(var(--ak-space-unit) * 2)}
|
|
61
|
+
.ak-spacer[data-size="large"]{height:calc(var(--ak-space-unit) * 4)}
|
|
62
|
+
.ak-quote{border-left:3px solid var(--ak-color-accent);padding-left:calc(var(--ak-space-unit) * 2);font-size:calc(var(--ak-font-size-base) * 1.1)}
|
|
63
|
+
.ak-quote cite{display:block;margin-top:.5em;color:var(--ak-color-text-muted);font-size:.9rem;font-style:normal}
|
|
64
|
+
.ak-badge{display:inline-block;padding:.15em .6em;border-radius:999px;border:var(--ak-border-width) solid var(--ak-color-border);background:var(--ak-color-surface-raised);font-size:.78rem;font-family:var(--ak-font-mono)}
|
|
65
|
+
.ak-badge[data-tone="info"]{border-color:var(--ak-color-info);color:var(--ak-color-info)}
|
|
66
|
+
.ak-badge[data-tone="success"]{border-color:var(--ak-color-success);color:var(--ak-color-success)}
|
|
67
|
+
.ak-badge[data-tone="warning"]{border-color:var(--ak-color-warning);color:var(--ak-color-warning)}
|
|
68
|
+
.ak-badge[data-tone="danger"]{border-color:var(--ak-color-danger);color:var(--ak-color-danger)}
|
|
69
|
+
.ak-kbd{display:inline-flex;gap:.2em}
|
|
70
|
+
.ak-kbd kbd{border:var(--ak-border-width) solid var(--ak-color-border);border-bottom-width:2px;border-radius:var(--ak-radius-small);padding:.1em .4em;background:var(--ak-color-surface-raised);font-size:.85em}
|
|
71
|
+
.ak-kv{display:grid;grid-template-columns:max-content minmax(0,1fr);gap:.4em calc(var(--ak-space-unit) * 2);margin:0}
|
|
72
|
+
.ak-kv dt{color:var(--ak-color-text-muted)}
|
|
73
|
+
.ak-kv dd{margin:0}
|
|
74
|
+
.ak-stats{display:grid;gap:calc(var(--ak-space-unit) * 2);grid-template-columns:repeat(auto-fit,minmax(150px,1fr));margin:0;padding:0;list-style:none}
|
|
75
|
+
.ak-stat{background:var(--ak-color-surface);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-medium);padding:calc(var(--ak-space-unit) * 1.5)}
|
|
76
|
+
.ak-stat dt{font-size:.8rem;color:var(--ak-color-text-muted);font-family:var(--ak-font-mono)}
|
|
77
|
+
.ak-stat dd{margin:.2em 0 0;font-size:calc(var(--ak-font-size-base) * 1.5);font-family:var(--ak-font-heading)}
|
|
78
|
+
.ak-steps{counter-reset:ak-step;list-style:none;padding:0;display:flex;flex-direction:column;gap:calc(var(--ak-space-unit) * 1.5)}
|
|
79
|
+
.ak-steps li{counter-increment:ak-step;position:relative;padding-left:calc(var(--ak-space-unit) * 4)}
|
|
80
|
+
.ak-steps li::before{content:counter(ak-step);position:absolute;left:0;top:0;width:24px;height:24px;border-radius:50%;background:var(--ak-color-accent);color:var(--ak-color-accent-contrast);display:flex;align-items:center;justify-content:center;font-family:var(--ak-font-mono);font-size:.8rem}
|
|
81
|
+
.ak-timeline{list-style:none;padding:0;margin:0;border-left:var(--ak-border-width) solid var(--ak-color-border);display:flex;flex-direction:column;gap:calc(var(--ak-space-unit) * 2)}
|
|
82
|
+
.ak-timeline li{position:relative;padding-left:calc(var(--ak-space-unit) * 2)}
|
|
83
|
+
.ak-timeline li::before{content:"";position:absolute;left:calc(var(--ak-space-unit) * -1 - 3px);top:.45em;width:7px;height:7px;border-radius:50%;background:var(--ak-color-accent)}
|
|
84
|
+
.ak-timeline time{display:block;font-family:var(--ak-font-mono);font-size:.78rem;color:var(--ak-color-text-muted)}
|
|
85
|
+
.ak-table-wrap{overflow-x:auto}
|
|
86
|
+
table{border-collapse:collapse;width:100%;background:var(--ak-color-surface)}
|
|
87
|
+
caption{text-align:left;padding-bottom:.5em;color:var(--ak-color-text-muted)}
|
|
88
|
+
th,td{text-align:left;padding:.55em .75em;border-bottom:var(--ak-border-width) solid var(--ak-color-border);vertical-align:top}
|
|
89
|
+
thead th{background:var(--ak-color-surface-raised);font-family:var(--ak-font-mono);font-size:.8rem;text-transform:uppercase;letter-spacing:.04em}
|
|
90
|
+
.ak-compare{display:grid;gap:calc(var(--ak-space-unit) * 2);grid-template-columns:1fr 1fr}
|
|
91
|
+
.ak-compare h3{font-size:calc(var(--ak-font-size-base) * 1.05);margin-bottom:.5em}
|
|
92
|
+
.ak-compare ul{margin:0}
|
|
93
|
+
.ak-callout,.ak-alert{border-left:4px solid var(--ak-color-info);background:var(--ak-color-surface);border-radius:var(--ak-radius-medium);padding:calc(var(--ak-space-unit) * 1.5);display:flex;flex-direction:column;gap:.4em}
|
|
94
|
+
.ak-callout[data-tone="success"],.ak-alert[data-tone="success"]{border-left-color:var(--ak-color-success)}
|
|
95
|
+
.ak-callout[data-tone="warning"],.ak-alert[data-tone="warning"]{border-left-color:var(--ak-color-warning)}
|
|
96
|
+
.ak-callout[data-tone="danger"],.ak-alert[data-tone="danger"]{border-left-color:var(--ak-color-danger)}
|
|
97
|
+
.ak-code{margin:0;background:var(--ak-color-surface-raised);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-medium);padding:calc(var(--ak-space-unit) * 1.5);overflow-x:auto}
|
|
98
|
+
.ak-code pre{margin:0;font-family:var(--ak-font-mono);font-size:.88rem;line-height:1.55}
|
|
99
|
+
.ak-code-head{display:flex;justify-content:space-between;gap:var(--ak-space-unit);align-items:center;margin-bottom:.5em}
|
|
100
|
+
.ak-btn{font:inherit;color:var(--ak-color-text);background:var(--ak-color-surface-raised);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-small);padding:.4em .8em;cursor:pointer;min-height:36px}
|
|
101
|
+
.ak-btn:hover{border-color:var(--ak-color-accent)}
|
|
102
|
+
.ak-btn[data-variant="primary"]{background:var(--ak-color-accent);color:var(--ak-color-accent-contrast);border-color:var(--ak-color-accent)}
|
|
103
|
+
.ak-btn[data-variant="ghost"]{background:transparent;border-color:transparent}
|
|
104
|
+
.ak-toolbar{display:flex;flex-wrap:wrap;gap:var(--ak-space-unit);align-items:center;padding:var(--ak-space-unit);background:var(--ak-color-surface);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-medium)}
|
|
105
|
+
.ak-list{list-style:none;padding:0;display:flex;flex-direction:column;gap:.5em}
|
|
106
|
+
.ak-list li{display:flex;gap:.5em;align-items:baseline;justify-content:space-between;border-bottom:var(--ak-border-width) solid var(--ak-color-border);padding-bottom:.4em}
|
|
107
|
+
.ak-list li[hidden]{display:none}
|
|
108
|
+
li.ak-hidden{display:none}
|
|
109
|
+
.ak-progress{display:flex;flex-direction:column;gap:.35em}
|
|
110
|
+
.ak-progress progress{width:100%;height:10px}
|
|
111
|
+
.ak-progress progress::-webkit-progress-bar{background:var(--ak-color-surface-raised)}
|
|
112
|
+
.ak-media{margin:0;display:flex;flex-direction:column;gap:.5em}
|
|
113
|
+
.ak-media img,.ak-gallery img{max-width:100%;height:auto;border-radius:var(--ak-radius-medium);border:var(--ak-border-width) solid var(--ak-color-border);background:var(--ak-color-surface-raised)}
|
|
114
|
+
.ak-media video{max-width:100%;border-radius:var(--ak-radius-medium)}
|
|
115
|
+
.ak-gallery{display:grid;gap:calc(var(--ak-space-unit) * 2);grid-template-columns:repeat(3,minmax(0,1fr));list-style:none;padding:0;margin:0}
|
|
116
|
+
.ak-sr{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0 0 0 0);white-space:nowrap;border:0}
|
|
117
|
+
@media (max-width:768px){body{--ak-font-size-base:16px}.ak-grid,.ak-compare,.ak-split,.ak-gallery{grid-template-columns:1fr!important}.ak-shell{padding:calc(var(--ak-space-unit) * 2) var(--ak-space-unit) calc(var(--ak-space-unit) * 6)}h1{font-size:calc(var(--ak-font-size-base) * 1.7)}}
|
|
118
|
+
@media (max-width:480px){.ak-toolbar{flex-direction:column;align-items:stretch}.ak-stats{grid-template-columns:1fr 1fr}}
|
|
119
|
+
@media print{.ak-skip,.ak-theme-toggle{display:none}}`;
|
|
120
|
+
export const FEATURE_CSS = {
|
|
121
|
+
tabs: `.ak-tabs [role="tablist"]{display:flex;flex-wrap:wrap;gap:.25em;border-bottom:var(--ak-border-width) solid var(--ak-color-border);margin-bottom:calc(var(--ak-space-unit) * 1.5)}
|
|
122
|
+
.ak-tabs [role="tab"]{font:inherit;background:transparent;border:0;border-bottom:2px solid transparent;padding:.5em .8em;cursor:pointer;color:var(--ak-color-text-muted)}
|
|
123
|
+
.ak-tabs [role="tab"][aria-selected="true"]{color:var(--ak-color-text);border-bottom-color:var(--ak-color-accent)}
|
|
124
|
+
.ak-tabs [role="tabpanel"]{padding:0}
|
|
125
|
+
.ak-tabs [role="tabpanel"][hidden]{display:none}`,
|
|
126
|
+
accordion: `.ak-accordion{display:flex;flex-direction:column;gap:.4em}
|
|
127
|
+
.ak-accordion details{background:var(--ak-color-surface);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-medium);padding:calc(var(--ak-space-unit) * .75) var(--ak-space-unit)}
|
|
128
|
+
.ak-accordion summary{cursor:pointer;font-family:var(--ak-font-heading);font-size:calc(var(--ak-font-size-base) * 1.02)}
|
|
129
|
+
.ak-accordion details[open] summary{margin-bottom:.5em}`,
|
|
130
|
+
carousel: `.ak-carousel{display:flex;flex-direction:column;gap:var(--ak-space-unit)}
|
|
131
|
+
.ak-carousel-slides{position:relative;min-height:120px}
|
|
132
|
+
.ak-carousel-slide{background:var(--ak-color-surface);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-medium);padding:calc(var(--ak-space-unit) * 2)}
|
|
133
|
+
.ak-carousel-slide[hidden]{display:none}
|
|
134
|
+
.ak-carousel-controls{display:flex;gap:var(--ak-space-unit);align-items:center}
|
|
135
|
+
.ak-carousel-status{font-family:var(--ak-font-mono);font-size:.8rem;color:var(--ak-color-text-muted)}`,
|
|
136
|
+
slider: `.ak-slider{display:flex;flex-direction:column;gap:.35em;max-width:420px}
|
|
137
|
+
.ak-slider input[type="range"]{width:100%}
|
|
138
|
+
.ak-slider output{font-family:var(--ak-font-mono);font-size:.85rem;color:var(--ak-color-text-muted)}`,
|
|
139
|
+
dialog: `dialog.ak-dialog{max-width:min(560px,92vw);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-large);background:var(--ak-color-surface);color:var(--ak-color-text);padding:calc(var(--ak-space-unit) * 2);box-shadow:var(--ak-elevation-popover)}
|
|
140
|
+
dialog.ak-dialog::backdrop{background:rgba(0,0,0,.5)}
|
|
141
|
+
.ak-dialog-actions{display:flex;gap:var(--ak-space-unit);justify-content:flex-end;margin-top:calc(var(--ak-space-unit) * 1.5)}`,
|
|
142
|
+
chart: `.ak-chart{display:flex;flex-direction:column;gap:var(--ak-space-unit)}
|
|
143
|
+
.ak-chart svg{width:100%;height:auto;overflow:visible}
|
|
144
|
+
.ak-chart figcaption{font-size:.85rem;color:var(--ak-color-text-muted)}
|
|
145
|
+
.ak-chart .ak-chart-bar{fill:var(--ak-color-accent)}
|
|
146
|
+
.ak-chart .ak-chart-bar--alt{fill:var(--ak-color-info)}
|
|
147
|
+
.ak-chart .ak-chart-line{fill:none;stroke:var(--ak-color-accent);stroke-width:2}
|
|
148
|
+
.ak-chart .ak-chart-area{fill:var(--ak-color-accent);opacity:.18}
|
|
149
|
+
.ak-chart .ak-chart-axis{stroke:var(--ak-color-border);stroke-width:1}
|
|
150
|
+
.ak-chart .ak-chart-label{fill:var(--ak-color-text-muted);font-family:var(--ak-font-mono);font-size:10px}
|
|
151
|
+
.ak-chart :focus-visible{outline:2px solid var(--ak-color-accent)}
|
|
152
|
+
.ak-details{margin-top:var(--ak-space-unit)}
|
|
153
|
+
.ak-details summary{cursor:pointer;color:var(--ak-color-text-muted);font-size:.85rem}`,
|
|
154
|
+
filter: `.ak-search{display:flex;flex-direction:column;gap:.35em;max-width:380px}
|
|
155
|
+
.ak-search input{font:inherit;padding:.45em .6em;border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-small);background:var(--ak-color-surface);color:var(--ak-color-text)}`,
|
|
156
|
+
theme: `.ak-theme-toggle{margin-left:auto}`,
|
|
157
|
+
media: `.ak-media-fallback{display:flex;flex-direction:column;gap:.35em;background:var(--ak-color-surface);border:var(--ak-border-width) dashed var(--ak-color-border);border-radius:var(--ak-radius-medium);padding:calc(var(--ak-space-unit) * 1.5)}
|
|
158
|
+
.ak-media-fallback img{max-width:100%;border-radius:var(--ak-radius-small)}`,
|
|
159
|
+
diagram: `.ak-diagram{overflow-x:auto}
|
|
160
|
+
.ak-diagram svg{max-width:100%;height:auto}
|
|
161
|
+
.ak-diagram-fallback{background:var(--ak-color-surface-raised);border:var(--ak-border-width) solid var(--ak-color-border);border-radius:var(--ak-radius-medium);padding:calc(var(--ak-space-unit) * 1.5)}`,
|
|
162
|
+
};
|
|
163
|
+
//# sourceMappingURL=styles.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"styles.js","sourceRoot":"","sources":["../../src/render/styles.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAIH,MAAM,CAAC,MAAM,QAAQ,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;sDA2G8B,CAAC;AAEvD,MAAM,CAAC,MAAM,WAAW,GAAsD;IAC5E,IAAI,EAAE;;;;iDAIyC;IAE/C,SAAS,EAAE;;;wDAG2C;IAEtD,QAAQ,EAAE;;;;;sGAK0F;IAEpG,MAAM,EAAE;;qGAE2F;IAEnG,MAAM,EAAE;;+HAEqH;IAE7H,KAAK,EAAE;;;;;;;;;;;sFAW6E;IAEpF,MAAM,EAAE;gNACsM;IAE9M,KAAK,EAAE,oCAAoC;IAE3C,KAAK,EAAE;4EACmE;IAE1E,OAAO,EAAE;;0MAE+L;CACzM,CAAC"}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Post-render verification.
|
|
3
|
+
*
|
|
4
|
+
* The compiler checks its own output before releasing it. These are invariants
|
|
5
|
+
* that must hold for every emitted artifact regardless of the spec, so a
|
|
6
|
+
* regression in a renderer fails the compile instead of shipping a page with a
|
|
7
|
+
* missing main landmark or an inline handler.
|
|
8
|
+
*/
|
|
9
|
+
import { type Diagnostic } from '../diagnostics.js';
|
|
10
|
+
import type { IrDocument } from '../ir.js';
|
|
11
|
+
import type { RuntimeFeature } from '../registry/roster.js';
|
|
12
|
+
export interface VerifyInput {
|
|
13
|
+
html: string;
|
|
14
|
+
ir: IrDocument;
|
|
15
|
+
csp: string;
|
|
16
|
+
styleNonce: string;
|
|
17
|
+
scriptNonce: string;
|
|
18
|
+
features: ReadonlySet<RuntimeFeature>;
|
|
19
|
+
css: string;
|
|
20
|
+
js: string;
|
|
21
|
+
}
|
|
22
|
+
export declare function verifyDocument(input: VerifyInput): Diagnostic[];
|
|
23
|
+
/** Verify the IR itself before rendering, catching compiler-side inconsistencies. */
|
|
24
|
+
export declare function verifyIr(ir: IrDocument, features: ReadonlySet<RuntimeFeature>): Diagnostic[];
|
|
25
|
+
//# sourceMappingURL=verify.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"verify.d.ts","sourceRoot":"","sources":["../../src/render/verify.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,KAAK,UAAU,EAAiB,MAAM,mBAAmB,CAAC;AACnE,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AAC3C,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AAE5D,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,UAAU,CAAC;IACf,GAAG,EAAE,MAAM,CAAC;IACZ,UAAU,EAAE,MAAM,CAAC;IACnB,WAAW,EAAE,MAAM,CAAC;IACpB,QAAQ,EAAE,WAAW,CAAC,cAAc,CAAC,CAAC;IACtC,GAAG,EAAE,MAAM,CAAC;IACZ,EAAE,EAAE,MAAM,CAAC;CACZ;AAsDD,wBAAgB,cAAc,CAAC,KAAK,EAAE,WAAW,GAAG,UAAU,EAAE,CAuF/D;AAED,qFAAqF;AACrF,wBAAgB,QAAQ,CAAC,EAAE,EAAE,UAAU,EAAE,QAAQ,EAAE,WAAW,CAAC,cAAc,CAAC,GAAG,UAAU,EAAE,CAyB5F"}
|
|
@@ -0,0 +1,168 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Post-render verification.
|
|
3
|
+
*
|
|
4
|
+
* The compiler checks its own output before releasing it. These are invariants
|
|
5
|
+
* that must hold for every emitted artifact regardless of the spec, so a
|
|
6
|
+
* regression in a renderer fails the compile instead of shipping a page with a
|
|
7
|
+
* missing main landmark or an inline handler.
|
|
8
|
+
*/
|
|
9
|
+
import { DiagnosticBag } from '../diagnostics.js';
|
|
10
|
+
/**
|
|
11
|
+
* A stable substring that must appear in the emitted CSS exactly when the
|
|
12
|
+
* feature is used. The bidirectional check below is what proves feature CSS is
|
|
13
|
+
* tree-shaken rather than merely present.
|
|
14
|
+
*/
|
|
15
|
+
const FEATURE_MARKERS = {
|
|
16
|
+
tabs: '.ak-tabs',
|
|
17
|
+
accordion: '.ak-accordion',
|
|
18
|
+
carousel: '.ak-carousel',
|
|
19
|
+
slider: '.ak-slider',
|
|
20
|
+
dialog: 'dialog.ak-dialog',
|
|
21
|
+
filter: '.ak-search',
|
|
22
|
+
theme: '.ak-theme-toggle',
|
|
23
|
+
chart: '.ak-chart',
|
|
24
|
+
diagram: '.ak-diagram',
|
|
25
|
+
media: '.ak-media-fallback',
|
|
26
|
+
};
|
|
27
|
+
/** Features whose behavior requires emitted JavaScript. */
|
|
28
|
+
const SCRIPTED_FEATURES = [
|
|
29
|
+
'tabs',
|
|
30
|
+
'carousel',
|
|
31
|
+
'slider',
|
|
32
|
+
'filter',
|
|
33
|
+
'theme',
|
|
34
|
+
'dialog',
|
|
35
|
+
];
|
|
36
|
+
function countMatches(text, pattern) {
|
|
37
|
+
return text.match(pattern)?.length ?? 0;
|
|
38
|
+
}
|
|
39
|
+
const INLINE_HANDLER = /<[^>]+\son[a-z]+\s*=/iu;
|
|
40
|
+
const REMOTE_SOURCE = /\ssrc\s*=\s*["']?https?:/iu;
|
|
41
|
+
const STYLESHEET_LINK = /<link[^>]+rel=["']?stylesheet/iu;
|
|
42
|
+
const CSS_IMPORT = /@import/iu;
|
|
43
|
+
const TH_WITHOUT_SCOPE = /<th(?=[\s>])(?![^>]*scope=)[^>]*>/iu;
|
|
44
|
+
/**
|
|
45
|
+
* Remove element bodies whose contents are not markup.
|
|
46
|
+
*
|
|
47
|
+
* The runtime is emitted into a `script` element, and its JavaScript legitimately
|
|
48
|
+
* contains text such as `if (open = ...)`; scanning it as markup produced a
|
|
49
|
+
* false "inline handler" report. Attribute-level checks must only ever look at
|
|
50
|
+
* the markup.
|
|
51
|
+
*/
|
|
52
|
+
function markupOnly(html) {
|
|
53
|
+
return html
|
|
54
|
+
.replace(/<script\b[^>]*>[\s\S]*?<\/script>/giu, '<script></script>')
|
|
55
|
+
.replace(/<style\b[^>]*>[\s\S]*?<\/style>/giu, '<style></style>');
|
|
56
|
+
}
|
|
57
|
+
export function verifyDocument(input) {
|
|
58
|
+
const bag = new DiagnosticBag();
|
|
59
|
+
const { html } = input;
|
|
60
|
+
const markup = markupOnly(html);
|
|
61
|
+
const report = (message, code = 'INTERNAL_ERROR') => {
|
|
62
|
+
bag.add({ code, message, path: '$' });
|
|
63
|
+
};
|
|
64
|
+
if (countMatches(html, /<h1[\s>]/giu) !== 1) {
|
|
65
|
+
report(`expected exactly one <h1>, found ${countMatches(html, /<h1[\s>]/giu)}`);
|
|
66
|
+
}
|
|
67
|
+
if (!/<main[\s>]/iu.test(html))
|
|
68
|
+
report('missing a <main> landmark');
|
|
69
|
+
if (!/<html[^>]+lang="/iu.test(html))
|
|
70
|
+
report('missing a language attribute on <html>');
|
|
71
|
+
if (!/<a class="ak-skip"/iu.test(html))
|
|
72
|
+
report('missing a skip link');
|
|
73
|
+
if (!/default-src 'none'/u.test(input.csp))
|
|
74
|
+
report("CSP must start from default-src 'none'");
|
|
75
|
+
if (/unsafe-inline|unsafe-eval/iu.test(input.csp)) {
|
|
76
|
+
report('CSP must not permit unsafe-inline or unsafe-eval', 'POLICY_VIOLATION');
|
|
77
|
+
}
|
|
78
|
+
if (!input.csp.includes(`'nonce-${input.styleNonce}'`))
|
|
79
|
+
report('CSP style nonce does not match the emitted style element');
|
|
80
|
+
if (input.js === '') {
|
|
81
|
+
if (!input.csp.includes("script-src 'none'")) {
|
|
82
|
+
report("expected script-src 'none' when no script is emitted");
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
else if (!input.csp.includes(`script-src 'nonce-${input.scriptNonce}'`)) {
|
|
86
|
+
report('CSP script nonce does not match the emitted script element');
|
|
87
|
+
}
|
|
88
|
+
if (INLINE_HANDLER.test(markup)) {
|
|
89
|
+
report('emitted inline event handler attribute', 'POLICY_VIOLATION');
|
|
90
|
+
}
|
|
91
|
+
if (STYLESHEET_LINK.test(markup))
|
|
92
|
+
report('emitted a remote stylesheet link', 'POLICY_VIOLATION');
|
|
93
|
+
if (CSS_IMPORT.test(markup))
|
|
94
|
+
report('emitted an @import rule', 'POLICY_VIOLATION');
|
|
95
|
+
if (/<script[^>]+src=/iu.test(markup))
|
|
96
|
+
report('emitted an external script', 'POLICY_VIOLATION');
|
|
97
|
+
if (/<iframe/iu.test(markup))
|
|
98
|
+
report('emitted an iframe', 'POLICY_VIOLATION');
|
|
99
|
+
if (input.ir.policy.network === 'deny' && REMOTE_SOURCE.test(markup)) {
|
|
100
|
+
report('emitted a remote resource reference while the network policy denies access', 'POLICY_VIOLATION');
|
|
101
|
+
}
|
|
102
|
+
const images = markup.match(/<img\b[^>]*>/giu) ?? [];
|
|
103
|
+
for (const image of images) {
|
|
104
|
+
if (!/\salt="/iu.test(image))
|
|
105
|
+
report('an <img> element is missing alt text');
|
|
106
|
+
}
|
|
107
|
+
const ids = [...markup.matchAll(/data-ak-id="([^"]+)"/gu)].map((match) => match[1] ?? '');
|
|
108
|
+
if (new Set(ids).size !== ids.length) {
|
|
109
|
+
report('duplicate data-ak-id values: a target would resolve ambiguously');
|
|
110
|
+
}
|
|
111
|
+
const tables = markup.match(/<table\b[^>]*>/giu) ?? [];
|
|
112
|
+
if (tables.length !== countMatches(markup, /<thead>/giu)) {
|
|
113
|
+
report('every table must have a header row');
|
|
114
|
+
}
|
|
115
|
+
if (TH_WITHOUT_SCOPE.test(markup))
|
|
116
|
+
report('a <th> element is missing a scope attribute');
|
|
117
|
+
const buttons = markup.match(/<button\b[^>]*>/giu) ?? [];
|
|
118
|
+
for (const button of buttons) {
|
|
119
|
+
if (!/\stype="/iu.test(button))
|
|
120
|
+
report('a <button> element is missing an explicit type');
|
|
121
|
+
}
|
|
122
|
+
if (!/:focus-visible/u.test(html))
|
|
123
|
+
report('missing a :focus-visible rule');
|
|
124
|
+
if (!/prefers-reduced-motion/u.test(html))
|
|
125
|
+
report('missing a prefers-reduced-motion rule');
|
|
126
|
+
for (const [feature, marker] of Object.entries(FEATURE_MARKERS)) {
|
|
127
|
+
const used = input.features.has(feature);
|
|
128
|
+
const emitted = input.css.includes(marker);
|
|
129
|
+
if (used && !emitted)
|
|
130
|
+
report(`feature "${feature}" is used but its stylesheet was not emitted`);
|
|
131
|
+
if (!used && emitted) {
|
|
132
|
+
report(`feature "${feature}" is not used but its stylesheet was emitted (tree-shaking regression)`);
|
|
133
|
+
}
|
|
134
|
+
const scripted = SCRIPTED_FEATURES.includes(feature);
|
|
135
|
+
if (used && scripted && input.js === '') {
|
|
136
|
+
report(`feature "${feature}" requires runtime behavior but no script was emitted`);
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
return bag.list();
|
|
140
|
+
}
|
|
141
|
+
/** Verify the IR itself before rendering, catching compiler-side inconsistencies. */
|
|
142
|
+
export function verifyIr(ir, features) {
|
|
143
|
+
const bag = new DiagnosticBag();
|
|
144
|
+
const ids = new Set();
|
|
145
|
+
for (const node of ir.nodes) {
|
|
146
|
+
if (ids.has(node.id)) {
|
|
147
|
+
bag.add({
|
|
148
|
+
code: 'INTERNAL_ERROR',
|
|
149
|
+
path: node.path,
|
|
150
|
+
nodeId: node.id,
|
|
151
|
+
message: `duplicate node id "${node.id}"`,
|
|
152
|
+
});
|
|
153
|
+
}
|
|
154
|
+
ids.add(node.id);
|
|
155
|
+
for (const feature of node.runtimeFeatures) {
|
|
156
|
+
if (!features.has(feature)) {
|
|
157
|
+
bag.add({
|
|
158
|
+
code: 'INTERNAL_ERROR',
|
|
159
|
+
path: node.path,
|
|
160
|
+
nodeId: node.id,
|
|
161
|
+
message: `runtime feature "${feature}" was not collected`,
|
|
162
|
+
});
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
return bag.list();
|
|
167
|
+
}
|
|
168
|
+
//# sourceMappingURL=verify.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"verify.js","sourceRoot":"","sources":["../../src/render/verify.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Strict validation of declarative action bindings.
|
|
3
|
+
*
|
|
4
|
+
* `on` may appear at block level and inside nested prop objects (a toolbar
|
|
5
|
+
* button, a dialog action). Both are validated here by the same closed
|
|
6
|
+
* vocabulary, so there is no position where an action escapes validation.
|
|
7
|
+
*/
|
|
8
|
+
import { type DiagnosticBag } from '../diagnostics.js';
|
|
9
|
+
import { type JsonValue } from '../json.js';
|
|
10
|
+
import type { PropValues } from '../registry/prop-schema.js';
|
|
11
|
+
export type BindingMap = Record<string, PropValues[]>;
|
|
12
|
+
/**
|
|
13
|
+
* Walk a validated props subtree and replace every `on` value with its
|
|
14
|
+
* normalized binding map. Returns the rewritten props.
|
|
15
|
+
*/
|
|
16
|
+
export declare function validateBindingsDeep(value: unknown, path: string, bag: DiagnosticBag): JsonValue | undefined;
|
|
17
|
+
/** Read the normalized bindings of a validated props object. */
|
|
18
|
+
export declare function bindingsOf(props: Record<string, JsonValue>): BindingMap;
|
|
19
|
+
//# sourceMappingURL=bindings.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"bindings.d.ts","sourceRoot":"","sources":["../../src/spec/bindings.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,KAAK,aAAa,EAAsB,MAAM,mBAAmB,CAAC;AAC3E,OAAO,EAAiB,KAAK,SAAS,EAAE,MAAM,YAAY,CAAC;AAE3D,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,4BAA4B,CAAC;AAE7D,MAAM,MAAM,UAAU,GAAG,MAAM,CAAC,MAAM,EAAE,UAAU,EAAE,CAAC,CAAC;AAEtD;;;GAGG;AACH,wBAAgB,oBAAoB,CAClC,KAAK,EAAE,OAAO,EACd,IAAI,EAAE,MAAM,EACZ,GAAG,EAAE,aAAa,GACjB,SAAS,GAAG,SAAS,CA2BvB;AAED,gEAAgE;AAChE,wBAAgB,UAAU,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,UAAU,CAIvE"}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Strict validation of declarative action bindings.
|
|
3
|
+
*
|
|
4
|
+
* `on` may appear at block level and inside nested prop objects (a toolbar
|
|
5
|
+
* button, a dialog action). Both are validated here by the same closed
|
|
6
|
+
* vocabulary, so there is no position where an action escapes validation.
|
|
7
|
+
*/
|
|
8
|
+
import { pathIndex, pathKey } from '../diagnostics.js';
|
|
9
|
+
import { isPlainObject } from '../json.js';
|
|
10
|
+
import { validateActionMap } from '../registry/actions.js';
|
|
11
|
+
/**
|
|
12
|
+
* Walk a validated props subtree and replace every `on` value with its
|
|
13
|
+
* normalized binding map. Returns the rewritten props.
|
|
14
|
+
*/
|
|
15
|
+
export function validateBindingsDeep(value, path, bag) {
|
|
16
|
+
if (Array.isArray(value)) {
|
|
17
|
+
const result = [];
|
|
18
|
+
for (let index = 0; index < value.length; index += 1) {
|
|
19
|
+
const item = validateBindingsDeep(value[index], pathIndex(path, index), bag);
|
|
20
|
+
if (item !== undefined)
|
|
21
|
+
result.push(item);
|
|
22
|
+
}
|
|
23
|
+
return result;
|
|
24
|
+
}
|
|
25
|
+
if (!isPlainObject(value)) {
|
|
26
|
+
return value === undefined ? undefined : value;
|
|
27
|
+
}
|
|
28
|
+
const result = {};
|
|
29
|
+
for (const [key, child] of Object.entries(value)) {
|
|
30
|
+
const childPath = pathKey(path, key);
|
|
31
|
+
if (key === 'on') {
|
|
32
|
+
const { bindings } = validateActionMap(child, childPath, bag);
|
|
33
|
+
if (Object.keys(bindings).length > 0) {
|
|
34
|
+
result[key] = bindings;
|
|
35
|
+
}
|
|
36
|
+
continue;
|
|
37
|
+
}
|
|
38
|
+
const normalized = validateBindingsDeep(child, childPath, bag);
|
|
39
|
+
if (normalized !== undefined)
|
|
40
|
+
result[key] = normalized;
|
|
41
|
+
}
|
|
42
|
+
return result;
|
|
43
|
+
}
|
|
44
|
+
/** Read the normalized bindings of a validated props object. */
|
|
45
|
+
export function bindingsOf(props) {
|
|
46
|
+
const candidate = props.on;
|
|
47
|
+
if (candidate === undefined || !isPlainObject(candidate))
|
|
48
|
+
return {};
|
|
49
|
+
return candidate;
|
|
50
|
+
}
|
|
51
|
+
//# sourceMappingURL=bindings.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"bindings.js","sourceRoot":"","sources":["../../src/spec/bindings.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAsB,SAAS,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAC;AAC3E,OAAO,EAAE,aAAa,EAAkB,MAAM,YAAY,CAAC;AAC3D,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAK3D;;;GAGG;AACH,MAAM,UAAU,oBAAoB,CAClC,KAAc,EACd,IAAY,EACZ,GAAkB;IAElB,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QACzB,MAAM,MAAM,GAAgB,EAAE,CAAC;QAC/B,KAAK,IAAI,KAAK,GAAG,CAAC,EAAE,KAAK,GAAG,KAAK,CAAC,MAAM,EAAE,KAAK,IAAI,CAAC,EAAE,CAAC;YACrD,MAAM,IAAI,GAAG,oBAAoB,CAAC,KAAK,CAAC,KAAK,CAAC,EAAE,SAAS,CAAC,IAAI,EAAE,KAAK,CAAC,EAAE,GAAG,CAAC,CAAC;YAC7E,IAAI,IAAI,KAAK,SAAS;gBAAE,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC5C,CAAC;QACD,OAAO,MAAM,CAAC;IAChB,CAAC;IACD,IAAI,CAAC,aAAa,CAAC,KAAK,CAAC,EAAE,CAAC;QAC1B,OAAO,KAAK,KAAK,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAE,KAAmB,CAAC;IAChE,CAAC;IAED,MAAM,MAAM,GAA8B,EAAE,CAAC;IAC7C,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QACjD,MAAM,SAAS,GAAG,OAAO,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;QACrC,IAAI,GAAG,KAAK,IAAI,EAAE,CAAC;YACjB,MAAM,EAAE,QAAQ,EAAE,GAAG,iBAAiB,CAAC,KAAK,EAAE,SAAS,EAAE,GAAG,CAAC,CAAC;YAC9D,IAAI,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;gBACrC,MAAM,CAAC,GAAG,CAAC,GAAG,QAAgC,CAAC;YACjD,CAAC;YACD,SAAS;QACX,CAAC;QACD,MAAM,UAAU,GAAG,oBAAoB,CAAC,KAAK,EAAE,SAAS,EAAE,GAAG,CAAC,CAAC;QAC/D,IAAI,UAAU,KAAK,SAAS;YAAE,MAAM,CAAC,GAAG,CAAC,GAAG,UAAU,CAAC;IACzD,CAAC;IACD,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,gEAAgE;AAChE,MAAM,UAAU,UAAU,CAAC,KAAgC;IACzD,MAAM,SAAS,GAAG,KAAK,CAAC,EAAE,CAAC;IAC3B,IAAI,SAAS,KAAK,SAAS,IAAI,CAAC,aAAa,CAAC,SAAS,CAAC;QAAE,OAAO,EAAE,CAAC;IACpE,OAAO,SAAkC,CAAC;AAC5C,CAAC"}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Input bounds.
|
|
3
|
+
*
|
|
4
|
+
* Bounds are checked before schema validation so an absurd document fails fast
|
|
5
|
+
* and cheaply. Every limit is application-level and deliberately far below any
|
|
6
|
+
* platform limit, because the same code runs in a CLI, in a library caller, and
|
|
7
|
+
* inside a worker with a bounded memory budget and a request-size ceiling.
|
|
8
|
+
*/
|
|
9
|
+
import { type DiagnosticBag } from '../diagnostics.js';
|
|
10
|
+
export declare const LIMITS: {
|
|
11
|
+
/** Nesting depth of the raw document, root included. */
|
|
12
|
+
readonly maxDepth: 24;
|
|
13
|
+
/** Entries in any `blocks` array, and total authored blocks. */
|
|
14
|
+
readonly maxBlocks: 200;
|
|
15
|
+
/** Objects in the document, anywhere (props objects and list items included). */
|
|
16
|
+
readonly maxNodes: 20000;
|
|
17
|
+
/** Serialized size of the whole document. */
|
|
18
|
+
readonly maxSerializedBytes: 1000000;
|
|
19
|
+
/** Items in any single list. */
|
|
20
|
+
readonly maxListItems: 200;
|
|
21
|
+
/** Keys in an open-keyed map such as `state`. */
|
|
22
|
+
readonly maxMapKeys: 200;
|
|
23
|
+
/** Length of a single-line string. */
|
|
24
|
+
readonly maxStringLength: 2000;
|
|
25
|
+
/** Length of multiline text. */
|
|
26
|
+
readonly maxTextLength: 50000;
|
|
27
|
+
};
|
|
28
|
+
export interface BoundsReport {
|
|
29
|
+
blocks: number;
|
|
30
|
+
nodes: number;
|
|
31
|
+
depth: number;
|
|
32
|
+
bytes: number;
|
|
33
|
+
longestString: number;
|
|
34
|
+
largestList: number;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Measure a raw document and report every exceeded bound.
|
|
38
|
+
*
|
|
39
|
+
* The walk is bounded even when the input is not: exceeding a limit stops
|
|
40
|
+
* descending at that branch instead of continuing to allocate diagnostics.
|
|
41
|
+
*/
|
|
42
|
+
export declare function checkBounds(value: unknown, bag: DiagnosticBag): BoundsReport;
|
|
43
|
+
//# sourceMappingURL=bounds.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"bounds.d.ts","sourceRoot":"","sources":["../../src/spec/bounds.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,KAAK,aAAa,EAAsB,MAAM,mBAAmB,CAAC;AAG3E,eAAO,MAAM,MAAM;IACjB,wDAAwD;;IAExD,gEAAgE;;IAEhE,iFAAiF;;IAEjF,6CAA6C;;IAE7C,gCAAgC;;IAEhC,iDAAiD;;IAEjD,sCAAsC;;IAEtC,gCAAgC;;CAExB,CAAC;AAEX,MAAM,WAAW,YAAY;IAC3B,MAAM,EAAE,MAAM,CAAC;IACf,KAAK,EAAE,MAAM,CAAC;IACd,KAAK,EAAE,MAAM,CAAC;IACd,KAAK,EAAE,MAAM,CAAC;IACd,aAAa,EAAE,MAAM,CAAC;IACtB,WAAW,EAAE,MAAM,CAAC;CACrB;AA4ED;;;;;GAKG;AACH,wBAAgB,WAAW,CAAC,KAAK,EAAE,OAAO,EAAE,GAAG,EAAE,aAAa,GAAG,YAAY,CAyC5E"}
|