nodality 1.2.8 → 1.2.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (202) hide show
  1. package/README.md +82 -0
  2. package/bin/nodality.js +12 -0
  3. package/bin/schema-cli.mjs +28 -0
  4. package/dist/animator.cjs.js.LICENSE.txt +1 -1
  5. package/dist/animator.esm.js.LICENSE.txt +1 -1
  6. package/dist/audionew.cjs.js.LICENSE.txt +1 -1
  7. package/dist/audionew.esm.js.LICENSE.txt +1 -1
  8. package/dist/base.cjs.js.LICENSE.txt +1 -1
  9. package/dist/base.esm.js.LICENSE.txt +1 -1
  10. package/dist/beta-desktop-bar.cjs.js.LICENSE.txt +1 -1
  11. package/dist/beta-desktop-bar.esm.js.LICENSE.txt +1 -1
  12. package/dist/beta-mobile-bar.cjs.js.LICENSE.txt +1 -1
  13. package/dist/beta-mobile-bar.esm.js.LICENSE.txt +1 -1
  14. package/dist/bundle.umd.js +1 -1
  15. package/dist/bundle.umd.js.LICENSE.txt +1 -1
  16. package/dist/button.cjs.js.LICENSE.txt +1 -1
  17. package/dist/button.esm.js.LICENSE.txt +1 -1
  18. package/dist/card-getter.cjs.js.LICENSE.txt +1 -1
  19. package/dist/card-getter.esm.js.LICENSE.txt +1 -1
  20. package/dist/center.cjs.js.LICENSE.txt +1 -1
  21. package/dist/center.esm.js.LICENSE.txt +1 -1
  22. package/dist/checkbox.cjs.js.LICENSE.txt +1 -1
  23. package/dist/checkbox.esm.js.LICENSE.txt +1 -1
  24. package/dist/code.cjs.js.LICENSE.txt +1 -1
  25. package/dist/code.esm.js.LICENSE.txt +1 -1
  26. package/dist/container.cjs.js.LICENSE.txt +1 -1
  27. package/dist/container.esm.js.LICENSE.txt +1 -1
  28. package/dist/data-list.cjs.js.LICENSE.txt +1 -1
  29. package/dist/data-list.esm.js.LICENSE.txt +1 -1
  30. package/dist/designer.cjs.js +1 -1
  31. package/dist/designer.cjs.js.LICENSE.txt +1 -1
  32. package/dist/designer.esm.js +1 -1
  33. package/dist/designer.esm.js.LICENSE.txt +1 -1
  34. package/dist/element-mapper.cjs.js +1 -1
  35. package/dist/element-mapper.cjs.js.LICENSE.txt +1 -1
  36. package/dist/element-mapper.esm.js +1 -1
  37. package/dist/element-mapper.esm.js.LICENSE.txt +1 -1
  38. package/dist/finalresult.esm.js +1 -1
  39. package/dist/finalresult.esm.js.LICENSE.txt +1 -1
  40. package/dist/flex-card.cjs.js.LICENSE.txt +1 -1
  41. package/dist/flex-card.esm.js.LICENSE.txt +1 -1
  42. package/dist/flex-grid.cjs.js.LICENSE.txt +1 -1
  43. package/dist/flex-grid.esm.js.LICENSE.txt +1 -1
  44. package/dist/flex-row.cjs.js.LICENSE.txt +1 -1
  45. package/dist/flex-row.esm.js.LICENSE.txt +1 -1
  46. package/dist/floating-input.cjs.js.LICENSE.txt +1 -1
  47. package/dist/floating-input.esm.js.LICENSE.txt +1 -1
  48. package/dist/free.cjs.js.LICENSE.txt +1 -1
  49. package/dist/free.esm.js.LICENSE.txt +1 -1
  50. package/dist/horizontal-scroller.cjs.js.LICENSE.txt +1 -1
  51. package/dist/horizontal-scroller.esm.js.LICENSE.txt +1 -1
  52. package/dist/image-picker.cjs.js.LICENSE.txt +1 -1
  53. package/dist/image-picker.esm.js.LICENSE.txt +1 -1
  54. package/dist/image.cjs.js.LICENSE.txt +1 -1
  55. package/dist/image.esm.js.LICENSE.txt +1 -1
  56. package/dist/index.cjs.js +1 -1
  57. package/dist/index.cjs.js.LICENSE.txt +1 -1
  58. package/dist/index.d.ts +1 -1
  59. package/dist/index.esm.js +1 -1
  60. package/dist/index.esm.js.LICENSE.txt +1 -1
  61. package/dist/keyframe-animation.cjs.js.LICENSE.txt +1 -1
  62. package/dist/keyframe-animation.esm.js.LICENSE.txt +1 -1
  63. package/dist/link-getter.cjs.js.LICENSE.txt +1 -1
  64. package/dist/link-getter.esm.js.LICENSE.txt +1 -1
  65. package/dist/link.cjs.js.LICENSE.txt +1 -1
  66. package/dist/link.esm.js.LICENSE.txt +1 -1
  67. package/dist/meta-adder.cjs.js.LICENSE.txt +1 -1
  68. package/dist/meta-adder.esm.js.LICENSE.txt +1 -1
  69. package/dist/modal-2025.cjs.js.LICENSE.txt +1 -1
  70. package/dist/modal-2025.esm.js.LICENSE.txt +1 -1
  71. package/dist/multiswitcher.cjs.js.LICENSE.txt +1 -1
  72. package/dist/multiswitcher.esm.js.LICENSE.txt +1 -1
  73. package/dist/new-nav-bar.cjs.js.LICENSE.txt +1 -1
  74. package/dist/new-nav-bar.esm.js.LICENSE.txt +1 -1
  75. package/dist/picker.cjs.js.LICENSE.txt +1 -1
  76. package/dist/picker.esm.js.LICENSE.txt +1 -1
  77. package/dist/progress.cjs.js.LICENSE.txt +1 -1
  78. package/dist/progress.esm.js.LICENSE.txt +1 -1
  79. package/dist/radio.cjs.js.LICENSE.txt +1 -1
  80. package/dist/radio.esm.js.LICENSE.txt +1 -1
  81. package/dist/range.cjs.js.LICENSE.txt +1 -1
  82. package/dist/range.esm.js.LICENSE.txt +1 -1
  83. package/dist/scroll-video.cjs.js.LICENSE.txt +1 -1
  84. package/dist/scroll-video.esm.js.LICENSE.txt +1 -1
  85. package/dist/side-bar.cjs.js.LICENSE.txt +1 -1
  86. package/dist/side-bar.esm.js.LICENSE.txt +1 -1
  87. package/dist/side-nav-bar.cjs.js.LICENSE.txt +1 -1
  88. package/dist/side-nav-bar.esm.js.LICENSE.txt +1 -1
  89. package/dist/simple-bar.cjs.js.LICENSE.txt +1 -1
  90. package/dist/simple-bar.esm.js.LICENSE.txt +1 -1
  91. package/dist/slider-2025.cjs.js.LICENSE.txt +1 -1
  92. package/dist/slider-2025.esm.js.LICENSE.txt +1 -1
  93. package/dist/spacer.cjs.js.LICENSE.txt +1 -1
  94. package/dist/spacer.esm.js.LICENSE.txt +1 -1
  95. package/dist/stack.cjs.js.LICENSE.txt +1 -1
  96. package/dist/stack.esm.js.LICENSE.txt +1 -1
  97. package/dist/stacker.cjs.js.LICENSE.txt +1 -1
  98. package/dist/stacker.esm.js.LICENSE.txt +1 -1
  99. package/dist/table.cjs.js.LICENSE.txt +1 -1
  100. package/dist/table.esm.js.LICENSE.txt +1 -1
  101. package/dist/text-field.cjs.js.LICENSE.txt +1 -1
  102. package/dist/text-field.esm.js.LICENSE.txt +1 -1
  103. package/dist/text.cjs.js.LICENSE.txt +1 -1
  104. package/dist/text.esm.js.LICENSE.txt +1 -1
  105. package/dist/theme.cjs.js.LICENSE.txt +1 -1
  106. package/dist/theme.esm.js.LICENSE.txt +1 -1
  107. package/dist/transform-anim.cjs.js.LICENSE.txt +1 -1
  108. package/dist/transform-anim.esm.js.LICENSE.txt +1 -1
  109. package/dist/ulist.cjs.js.LICENSE.txt +1 -1
  110. package/dist/ulist.esm.js.LICENSE.txt +1 -1
  111. package/dist/video.cjs.js.LICENSE.txt +1 -1
  112. package/dist/video.esm.js.LICENSE.txt +1 -1
  113. package/dist/wrap.cjs.js.LICENSE.txt +1 -1
  114. package/dist/wrap.esm.js.LICENSE.txt +1 -1
  115. package/dist/zoom-card.cjs.js.LICENSE.txt +1 -1
  116. package/dist/zoom-card.esm.js.LICENSE.txt +1 -1
  117. package/layout/animator.js +1 -1
  118. package/layout/audio.js +1 -1
  119. package/layout/audionew.js +1 -1
  120. package/layout/base.js +1 -1
  121. package/layout/beta-desktop-bar.js +1 -1
  122. package/layout/beta-mobile-bar.js +1 -1
  123. package/layout/button.js +1 -1
  124. package/layout/center.js +1 -1
  125. package/layout/checkbox.js +1 -1
  126. package/layout/circle.js +1 -1
  127. package/layout/code.js +1 -1
  128. package/layout/container.js +1 -1
  129. package/layout/dropdown-2025.js +1 -1
  130. package/layout/flex-card.js +1 -1
  131. package/layout/flex-grid.js +1 -1
  132. package/layout/flex-row.js +1 -1
  133. package/layout/form-components/custom.js +1 -1
  134. package/layout/form-components/data-list.js +1 -1
  135. package/layout/form-components/floating-input.js +1 -1
  136. package/layout/form-components/form-all.js +1 -1
  137. package/layout/form-components/form.js +1 -1
  138. package/layout/form-components/image-picker.js +1 -1
  139. package/layout/form-components/picker.js +1 -1
  140. package/layout/form-components/radio.js +1 -1
  141. package/layout/form-components/radiogroup.js +1 -1
  142. package/layout/form-components/range.js +1 -1
  143. package/layout/free.js +1 -1
  144. package/layout/grid-switcher.js +1 -1
  145. package/layout/grid.js +1 -1
  146. package/layout/horizontal-scroller.js +1 -1
  147. package/layout/image.js +1 -1
  148. package/layout/index.js +1 -1
  149. package/layout/link.js +1 -1
  150. package/layout/list.js +1 -1
  151. package/layout/meta-adder.js +1 -1
  152. package/layout/modal-2025.js +1 -1
  153. package/layout/morph.js +1 -1
  154. package/layout/multiswitcher.js +1 -1
  155. package/layout/nav-bar.js +1 -1
  156. package/layout/nav-factor/custom-div.js +1 -1
  157. package/layout/new-nav-bar.js +1 -1
  158. package/layout/polygon.js +1 -1
  159. package/layout/prerender-site.js +1 -1
  160. package/layout/prerender.js +1 -1
  161. package/layout/progress.js +1 -1
  162. package/layout/row.js +1 -1
  163. package/layout/scroll-video.js +1 -1
  164. package/layout/side-bar.js +1 -1
  165. package/layout/side-nav-bar.js +1 -1
  166. package/layout/simple-bar.js +1 -1
  167. package/layout/slider-2025.js +1 -1
  168. package/layout/spacer.js +1 -1
  169. package/layout/stack.js +1 -1
  170. package/layout/svg.js +1 -1
  171. package/layout/switcher.js +1 -1
  172. package/layout/table.js +1 -1
  173. package/layout/text-field.js +1 -1
  174. package/layout/text.js +1 -1
  175. package/layout/ulist.js +1 -1
  176. package/layout/video.js +1 -1
  177. package/layout/wrap.js +1 -1
  178. package/layout/zoom-card.js +1 -1
  179. package/lib/agent-surface.js +1 -1
  180. package/lib/card-getter.js +1 -1
  181. package/lib/codegen.js +1 -1
  182. package/lib/data.js +1 -1
  183. package/lib/designer.js +21 -1
  184. package/lib/element-mapper.js +173 -16
  185. package/lib/element-params.generated.js +11 -0
  186. package/lib/keyframe-animation.js +1 -1
  187. package/lib/link-getter.js +1 -1
  188. package/lib/morph-node.js +1 -1
  189. package/lib/parse-html.js +139 -0
  190. package/lib/raster-inspect.js +1 -1
  191. package/lib/raster-ops.js +1 -1
  192. package/lib/raster-presets.js +1 -1
  193. package/lib/scroll-video.js +1 -1
  194. package/lib/seo.js +1 -1
  195. package/lib/stacker.js +1 -1
  196. package/lib/suggest.js +1 -1
  197. package/lib/theme.js +1 -1
  198. package/lib/transform-anim.js +1 -1
  199. package/lib/transition.js +1 -1
  200. package/lib/validate-nodes.js +73 -2
  201. package/lib/webmcp-adapter.js +1 -1
  202. package/package.json +2 -1
package/README.md CHANGED
@@ -168,6 +168,88 @@ stills rather than breaking. And determinism is a property of the
168
168
  compiled artefact – the same pair always produces the same output – not
169
169
  of the pixels a particular GPU eventually paints.
170
170
 
171
+ ## Requirements
172
+
173
+ Nodality has **zero runtime dependencies**. What you need depends on how you use it.
174
+
175
+ **The preferred way to start is the scaffolder**, which creates a working project
176
+ with the pipeline, the prerender step and the example pair already wired up:
177
+
178
+ ```bash
179
+ npm create nodality@latest my-app
180
+ ```
181
+
182
+ It needs only Node.js 20 or newer. Everything below is for adding Nodality to
183
+ something that already exists.
184
+
185
+ | Use | Requires |
186
+ |---|---|
187
+ | In a browser | Any browser with ES modules. No build step, no bundler. |
188
+ | `npm install nodality` | Node.js 20 or newer. TypeScript declarations ship in `dist/index.d.ts`. |
189
+ | `npx nodality prerender` (static generation) | Node.js 20 or newer. The prerender path runs the same pipeline inside `jsdom`. |
190
+ | Running the test suite | `npm install` (pulls Playwright, jsdom, webpack, Babel as dev dependencies), then `npx playwright install`. |
191
+
192
+ The published measurements were produced on Node.js v25.6.0.
193
+
194
+ ## Code information
195
+
196
+ | Path | Contains |
197
+ |---|---|
198
+ | `layout/` | Element definitions — the *what exists* half of the pair. |
199
+ | `lib/` | Transformation nodes and the pipeline — the *what is done to it* half. |
200
+ | `dist/` | Built bundles: `index.cjs.js` (CommonJS), `index.esm.js` (ES module), `index.d.ts`. |
201
+ | `bin/` | The command-line entry points, including `prerender`. |
202
+ | `__tests__/` | Playwright regression tests that assert deterministic output. |
203
+ | `examples/` | Runnable pairs, smallest first. |
204
+ | `API.md` | Full API reference. |
205
+ | `CHANGELOG.md` | Version history. |
206
+
207
+ ## Reproducing the published measurements
208
+
209
+ The quantitative results are **not** in this repository. Harnesses, raw data and
210
+ per-measurement READMEs are deposited separately under CC0:
211
+
212
+ - **Repository:** [github.com/nodalityjs/benchmarks](https://github.com/nodalityjs/benchmarks)
213
+ - **Archived deposit:** [10.5281/zenodo.21610251](https://doi.org/10.5281/zenodo.21610251)
214
+
215
+ That deposit covers authoring cost in language-model tokens, compiler scaling
216
+ from 10 to 1 000 elements, crawlability and first-paint timing, model
217
+ properties, determinism, accessibility, and WHATWG validity. Each has its own
218
+ README and run command. The benchmark harnesses pin `nodality` to an exact
219
+ version rather than a range, so a fresh install reproduces the published figures
220
+ against the artefact that produced them.
221
+
222
+ ## Methodology
223
+
224
+ Nodality compiles two plain arrays — `elements` (what exists) and `nodes` (what
225
+ is done to it) — into rendered output. The two meet only through `target`, so
226
+ neither names the other and either can be authored, stored or generated
227
+ independently. The same pair is interpreted twice: at build time inside a
228
+ simulated DOM to emit crawlable static HTML, and in the browser to attach
229
+ behaviour. Determinism is a property of the compiled artefact: the same pair
230
+ always compiles to a byte-identical result, which is asserted by the regression
231
+ suite rather than proved formally.
232
+
233
+ ## Citing
234
+
235
+ If you use Nodality in research, please cite the paper rather than this
236
+ repository:
237
+
238
+ > Vabroušek, F. Nodality: a node-based declarative transformation pipeline for
239
+ > static UI generation. *PeerJ Computer Science*. (Under review.)
240
+
241
+ For the measurements specifically, cite the data deposit:
242
+
243
+ > Vabroušek, F. 2026. *Nodality benchmarks*. Zenodo. DOI 10.5281/zenodo.21610251.
244
+
245
+ ## License and contributing
246
+
247
+ Nodality is released under the [MIT License](LICENSE). The benchmark deposit is
248
+ released separately under CC0 1.0.
249
+
250
+ Contributions are welcome; see [CONTRIBUTING.md](CONTRIBUTING.md) for the
251
+ development setup and the expectations for a pull request.
252
+
171
253
  ## Links
172
254
 
173
255
  - **Docs** – [nodalityjs.github.io](https://nodalityjs.github.io/)
package/bin/nodality.js CHANGED
@@ -64,6 +64,13 @@ function showUsage() {
64
64
  # --dir=<path> copy SKILL.md anywhere
65
65
  # --no-mcp skip MCP registration
66
66
  # Re-run after upgrading to refresh in place.
67
+ nodality schema [type] [--check] # Print the machine-readable element
68
+ # schema, derived from the source
69
+ # at run time. With a type, print
70
+ # just that type — the form an
71
+ # agent puts in its context.
72
+ # --check exit 1 if schema.json
73
+ # is stale (used in CI)
67
74
  nodality help
68
75
 
69
76
  Compile flags:
@@ -872,6 +879,11 @@ async function main() {
872
879
  await runFanoutStandalone(rest);
873
880
  } else if (command === "stage") {
874
881
  await runStage(rest);
882
+ } else if (command === "schema") {
883
+ // Lazily imported like `mcp` and `skill`: a subcommand nobody invoked
884
+ // should cost nothing, and a broken generator must not take the CLI down.
885
+ const { runSchema } = await import("./schema-cli.mjs");
886
+ await runSchema(rest);
875
887
  } else if (command === "skill") {
876
888
  const { runSkillInstall } = await import("./install-skill.mjs");
877
889
  await runSkillInstall(rest);
@@ -0,0 +1,28 @@
1
+ // bin/schema-cli.mjs — `npx nodality schema [type] [--check]`
2
+ //
3
+ // Stage 2 of AGENTIC-FIRST-PLAN.md. The point of the subcommand is property 2
4
+ // of "agentic-first": schema ON DEMAND rather than schema in context. A model
5
+ // that can fetch one type's parameters pays for that type once, instead of
6
+ // carrying every type's vocabulary in every request.
7
+ //
8
+ // The schema is regenerated from source on each call rather than read from
9
+ // the committed schema.json, so what an agent is told can never be staler
10
+ // than the library it is talking to. `--check` compares the two and is what
11
+ // CI runs.
12
+ import { spawn } from "node:child_process";
13
+ import { fileURLToPath } from "node:url";
14
+ import path from "node:path";
15
+
16
+ export async function runSchema(args) {
17
+ const here = path.dirname(fileURLToPath(import.meta.url));
18
+ const gen = path.join(here, "..", "scripts", "generate-schema.mjs");
19
+ const type = args.find((a) => !a.startsWith("--"));
20
+ const passthrough = args.includes("--check")
21
+ ? ["--check"]
22
+ : type ? ["--type", type] : ["--stdout"];
23
+
24
+ await new Promise((resolve) => {
25
+ const p = spawn(process.execPath, [gen, ...passthrough], { stdio: "inherit" });
26
+ p.on("exit", (code) => { process.exitCode = code ?? 0; resolve(); });
27
+ });
28
+ }
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * nodality v1.2.7
2
+ * nodality v1.2.9
3
3
  * (c) 2026 Filip Vabrousek
4
4
  * License: MIT
5
5
  */