@pixel-point/toolcraft 0.0.16 → 0.0.18

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 (313) hide show
  1. package/package.json +1 -1
  2. package/src/generate-performance-iteration-execution.test.mjs +2 -2
  3. package/src/generate-test-demand-only-lifecycle.mjs +14 -3
  4. package/src/generate-test-dependency-sandbox.mjs +42 -5
  5. package/src/generate-test-doc-assertions.mjs +109 -69
  6. package/src/generate-test-doc-assertions.test.mjs +65 -0
  7. package/src/generate-test-doc-policy-assertions.mjs +92 -0
  8. package/src/generate-test-file-assertions.mjs +36 -118
  9. package/src/generate-test-output-assertions.mjs +95 -0
  10. package/src/generate-test-package-assertions.mjs +6 -0
  11. package/src/generate-test-performance-boundary-assertions.mjs +45 -0
  12. package/src/generate-test-product-fixture.mjs +1 -0
  13. package/src/generate-test-product-fixture.test.mjs +18 -0
  14. package/src/generate-test-product-iteration.mjs +1 -0
  15. package/src/generate-test-product-iteration.test.mjs +18 -0
  16. package/src/generate-test-runtime-boundary-assertions.mjs +158 -0
  17. package/src/generate-test-standalone-assertions.mjs +10 -0
  18. package/src/generate-test-standalone-delivery-stages.mjs +14 -6
  19. package/src/generate.test.mjs +14 -0
  20. package/templates/runtime/contracts/component-contracts.choices.test.ts +59 -12
  21. package/templates/runtime/contracts/component-contracts.choices.ts +58 -12
  22. package/templates/runtime/contracts/component-contracts.inputs.test.ts +6 -6
  23. package/templates/runtime/contracts/component-contracts.inputs.ts +6 -6
  24. package/templates/runtime/contracts/component-contracts.media-custom.test.ts +8 -2
  25. package/templates/runtime/contracts/component-contracts.media-custom.ts +8 -2
  26. package/templates/runtime/contracts/component-contracts.runtime-acceptance.test.ts +21 -6
  27. package/templates/runtime/contracts/component-contracts.runtime-labels.test.ts +7 -1
  28. package/templates/runtime/contracts/component-contracts.runtime-panels.test.ts +4 -1
  29. package/templates/runtime/contracts/component-contracts.runtime-shell.test.ts +4 -1
  30. package/templates/runtime/contracts/component-contracts.runtime.ts +15 -10
  31. package/templates/runtime/contracts/component-contracts.test.ts +2 -0
  32. package/templates/runtime/contracts/decision-contracts.test.ts +43 -4
  33. package/templates/runtime/contracts/decision-contracts.ts +10 -10
  34. package/templates/runtime/contracts/performance-verification-policy.test.ts +59 -6
  35. package/templates/runtime/contracts/performance-verification-policy.ts +5 -2
  36. package/templates/runtime/export/artifact-download.test.ts +71 -0
  37. package/templates/runtime/export/artifact-download.ts +80 -0
  38. package/templates/runtime/export/artifact-export-request.ts +23 -0
  39. package/templates/runtime/export/artifact-export-settings.test.ts +75 -0
  40. package/templates/runtime/export/artifact-export-settings.ts +96 -0
  41. package/templates/runtime/export/artifact-frame-renderer.test.ts +107 -0
  42. package/templates/runtime/export/artifact-frame-renderer.ts +96 -0
  43. package/templates/runtime/export/artifact-frame-state.test.ts +54 -0
  44. package/templates/runtime/export/artifact-frame-state.ts +44 -0
  45. package/templates/runtime/export/artifact-scene-frame.test.ts +84 -0
  46. package/templates/runtime/export/artifact-scene-frame.ts +118 -0
  47. package/templates/runtime/export/export-background.ts +46 -0
  48. package/templates/runtime/export/export-error.ts +43 -0
  49. package/templates/runtime/export/export.test.ts +49 -226
  50. package/templates/runtime/export/image-artifact-export.test.ts +111 -0
  51. package/templates/runtime/export/image-artifact-export.ts +145 -0
  52. package/templates/runtime/export/index.ts +44 -3
  53. package/templates/runtime/export/product-export-renderer.test.ts +77 -0
  54. package/templates/runtime/export/product-export-renderer.ts +63 -0
  55. package/templates/runtime/export/video-artifact-export.test.ts +166 -0
  56. package/templates/runtime/export/video-artifact-export.ts +164 -0
  57. package/templates/runtime/export/video-encoding-backend.ts +124 -0
  58. package/templates/runtime/export/video-encoding-policy.test.ts +68 -0
  59. package/templates/runtime/export/video-encoding-policy.ts +86 -0
  60. package/templates/runtime/export/video-frame-schedule.test.ts +58 -0
  61. package/templates/runtime/export/video-frame-schedule.ts +42 -0
  62. package/templates/runtime/index.ts +3 -0
  63. package/templates/runtime/model-import/model-import-limits.ts +15 -4
  64. package/templates/runtime/react/app-shell/runtime-public-api-runtime.test.tsx +291 -0
  65. package/templates/runtime/react/app-shell/runtime-public-api-test-support.ts +21 -0
  66. package/templates/runtime/react/app-shell/runtime-public-api.test.tsx +15 -304
  67. package/templates/runtime/react/app-shell/toolcraft-app.scene-export.test.tsx +41 -27
  68. package/templates/runtime/react/app-shell/toolcraft-app.tsx +39 -11
  69. package/templates/runtime/react/app-shell/toolcraft-source-asset-context.test.tsx +16 -57
  70. package/templates/runtime/react/app-shell/toolcraft-source-asset-context.tsx +75 -434
  71. package/templates/runtime/react/app-shell/toolcraft-source-asset-owner.test.ts +194 -0
  72. package/templates/runtime/react/app-shell/toolcraft-source-asset-owner.ts +227 -0
  73. package/templates/runtime/react/app-shell/toolcraft-source-asset-provider-ownership.test.tsx +243 -0
  74. package/templates/runtime/react/app-shell/toolcraft-source-asset-test-support.ts +51 -0
  75. package/templates/runtime/react/app-shell/toolcraft-unavailable-resource-proof.test.ts +138 -0
  76. package/templates/runtime/react/app-shell/toolcraft-unavailable-resource-proof.ts +378 -0
  77. package/templates/runtime/react/canvas/canvas-shell-rendering.test.tsx +76 -0
  78. package/templates/runtime/react/canvas/canvas-shell-test-utils.tsx +13 -1
  79. package/templates/runtime/react/canvas/canvas-shell.tsx +16 -1
  80. package/templates/runtime/react/canvas/product-scene-surface.test.tsx +195 -0
  81. package/templates/runtime/react/canvas/product-scene-surface.tsx +155 -0
  82. package/templates/runtime/react/canvas/runtime-scene-export.ts +1 -1
  83. package/templates/runtime/react/controls-panel/__tests__/control-conditions.test.ts +61 -0
  84. package/templates/runtime/react/controls-panel/__tests__/controls-panel.collection-actions.test.tsx +89 -0
  85. package/templates/runtime/react/controls-panel/__tests__/controls-panel.control-visibility.test.tsx +40 -19
  86. package/templates/runtime/react/controls-panel/__tests__/controls-panel.footer-actions.test.tsx +7 -12
  87. package/templates/runtime/react/controls-panel/__tests__/controls-panel.scene-export-actions.test.tsx +18 -84
  88. package/templates/runtime/react/controls-panel/__tests__/controls-panel.source-collection.test.tsx +62 -0
  89. package/templates/runtime/react/controls-panel/__tests__/controls-panel.source-color-bank.test.tsx +67 -0
  90. package/templates/runtime/react/controls-panel/actions/controls-panel-actions.ts +43 -87
  91. package/templates/runtime/react/controls-panel/actions/export-action-runner.ts +68 -0
  92. package/templates/runtime/react/controls-panel/conditions/control-conditions.ts +32 -119
  93. package/templates/runtime/react/controls-panel/layout/controls-panel-control-group.tsx +5 -2
  94. package/templates/runtime/react/controls-panel/layout/controls-panel-layout.tsx +10 -8
  95. package/templates/runtime/react/controls-panel/layout/controls-panel-section.tsx +3 -3
  96. package/templates/runtime/react/controls-panel/renderers/controls-panel-collection-item-fields.test.tsx +63 -0
  97. package/templates/runtime/react/controls-panel/renderers/controls-panel-collection-item-fields.tsx +138 -0
  98. package/templates/runtime/react/controls-panel/renderers/controls-panel-collection-items.tsx +104 -0
  99. package/templates/runtime/react/controls-panel/renderers/controls-panel-collection-renderer.tsx +115 -236
  100. package/templates/runtime/react/controls-panel/renderers/controls-panel-file-drop-item-controls.test.tsx +95 -0
  101. package/templates/runtime/react/controls-panel/renderers/controls-panel-file-drop-item-controls.tsx +82 -0
  102. package/templates/runtime/react/controls-panel/renderers/controls-panel-media-renderer.test.tsx +73 -1
  103. package/templates/runtime/react/controls-panel/renderers/controls-panel-media-renderer.tsx +50 -1
  104. package/templates/runtime/react/controls-panel/renderers/controls-panel-renderer-registry.test.ts +1 -1
  105. package/templates/runtime/react/controls-panel/renderers/controls-panel-renderer-registry.ts +2 -1
  106. package/templates/runtime/react/controls-panel/values/controls-panel-collection-values.ts +38 -6
  107. package/templates/runtime/react/controls-panel/values/controls-panel-value-labels.ts +1 -0
  108. package/templates/runtime/react/index.ts +4 -0
  109. package/templates/runtime/react/model-rendering/model-export.ts +1 -1
  110. package/templates/runtime/react/orientation-gizmo/orientation-gizmo-selection.ts +5 -5
  111. package/templates/runtime/react/orientation-gizmo/use-toolcraft-orientation-control-selection.ts +2 -2
  112. package/templates/runtime/react/panel-host/panel-host-runtime-placement.test.tsx +30 -0
  113. package/templates/runtime/react/panel-host/panel-host.tsx +4 -0
  114. package/templates/runtime/scene/scene-bounds.test.ts +23 -0
  115. package/templates/runtime/scene/scene-bounds.ts +32 -19
  116. package/templates/runtime/schema/app-capabilities.test.ts +4 -0
  117. package/templates/runtime/schema/canvas-render-scale.ts +62 -0
  118. package/templates/runtime/schema/collection-item-controls.ts +29 -0
  119. package/templates/runtime/schema/control-applicability.test.ts +127 -0
  120. package/templates/runtime/schema/control-applicability.ts +433 -0
  121. package/templates/runtime/schema/control-schema-normalization.ts +177 -11
  122. package/templates/runtime/schema/controls-panel-actions.ts +2 -2
  123. package/templates/runtime/schema/controls-panel-section-id.test.ts +1 -1
  124. package/templates/runtime/schema/controls-panel-section-layout.ts +14 -9
  125. package/templates/runtime/schema/controls-panel-section-roundtrip.test.ts +62 -3
  126. package/templates/runtime/schema/define-toolcraft.collection-actions-item-controls.test.ts +127 -0
  127. package/templates/runtime/schema/define-toolcraft.control-sections.test.ts +10 -4
  128. package/templates/runtime/schema/define-toolcraft.file-drop-item-controls.test.ts +98 -0
  129. package/templates/runtime/schema/define-toolcraft.file-drop-normalization.test.ts +27 -0
  130. package/templates/runtime/schema/define-toolcraft.segmented-control-fit.test.ts +20 -2
  131. package/templates/runtime/schema/define-toolcraft.setup-background.test.ts +1 -1
  132. package/templates/runtime/schema/define-toolcraft.setup-canvas.test.ts +16 -3
  133. package/templates/runtime/schema/define-toolcraft.setup-render-scale-timeline.test.ts +71 -3
  134. package/templates/runtime/schema/define-toolcraft.source-collection.test.ts +79 -0
  135. package/templates/runtime/schema/define-toolcraft.ts +1 -1
  136. package/templates/runtime/schema/runtime-setup-section.ts +24 -5
  137. package/templates/runtime/schema/schema-resolvers.ts +0 -56
  138. package/templates/runtime/schema/types.ts +72 -17
  139. package/templates/runtime/state/canvas-background-state.ts +6 -0
  140. package/templates/runtime/testing/performance-render-plan-integration.test.ts +64 -0
  141. package/templates/runtime/testing/performance-renderer-pipeline-validation.ts +18 -1
  142. package/templates/starter/AGENTS.md +18 -15
  143. package/templates/starter/NOTICE.md +6 -0
  144. package/templates/starter/docs/toolcraft/README.md +2 -1
  145. package/templates/starter/docs/toolcraft/acceptance-testing.md +23 -35
  146. package/templates/starter/docs/toolcraft/agent-worklog.md +18 -3
  147. package/templates/starter/docs/toolcraft/assembly-workflow.md +13 -5
  148. package/templates/starter/docs/toolcraft/component-rules.md +8 -6
  149. package/templates/starter/docs/toolcraft/core/control-selection.md +9 -3
  150. package/templates/starter/docs/toolcraft/core/layout.md +7 -7
  151. package/templates/starter/docs/toolcraft/core/media-upload.md +4 -2
  152. package/templates/starter/docs/toolcraft/core/performance.md +14 -3
  153. package/templates/starter/docs/toolcraft/core/runtime-boundary.md +16 -3
  154. package/templates/starter/docs/toolcraft/core/setup-export.md +49 -19
  155. package/templates/starter/docs/toolcraft/core/timeline-animation.md +4 -4
  156. package/templates/starter/docs/toolcraft/custom-controls.md +6 -4
  157. package/templates/starter/docs/toolcraft/decision-contract.md +3 -1
  158. package/templates/starter/docs/toolcraft/performance.md +20 -6
  159. package/templates/starter/docs/toolcraft/renderer-technique.md +5 -1
  160. package/templates/starter/docs/toolcraft/schema-reference.md +23 -25
  161. package/templates/starter/docs/toolcraft/workflow.md +7 -2
  162. package/templates/starter/e2e/app-browser-control-applicability-requirements.spec.ts +163 -0
  163. package/templates/starter/e2e/app-browser-control-coverage.spec.ts +33 -0
  164. package/templates/starter/e2e/app-browser-infinity-canvas-evidence.spec.ts +50 -3
  165. package/templates/starter/e2e/app-browser-orientation-evidence.spec.ts +174 -21
  166. package/templates/starter/e2e/app-browser-render-scale-evidence.spec.ts +60 -6
  167. package/templates/starter/e2e/app-browser-render-scale-requirements.spec.ts +77 -1
  168. package/templates/starter/e2e/app-browser-runtime-provenance.spec.ts +8 -0
  169. package/templates/starter/e2e/app-browser-runtime-reporter.spec.ts +35 -0
  170. package/templates/starter/e2e/app-browser-runtime-requirements.spec.ts +5 -34
  171. package/templates/starter/e2e/app-browser-semantic-evidence.spec.ts +61 -16
  172. package/templates/starter/e2e/app-browser-shell.spec.ts +13 -5
  173. package/templates/starter/e2e/app-performance-path-adapters.ts +8 -1
  174. package/templates/starter/e2e/app-performance.spec.ts +16 -9
  175. package/templates/starter/e2e/{browser-conditional-output-evidence-helpers.ts → browser-background-output-evidence.ts} +0 -68
  176. package/templates/starter/e2e/browser-control-applicability-evidence.ts +114 -0
  177. package/templates/starter/e2e/browser-infinity-canvas-evidence.ts +29 -341
  178. package/templates/starter/e2e/browser-infinity-canvas-unavailable-image-evidence.ts +370 -0
  179. package/templates/starter/e2e/browser-media-export-evidence.spec.ts +77 -0
  180. package/templates/starter/e2e/browser-media-export-evidence.ts +208 -0
  181. package/templates/starter/e2e/browser-orientation-gizmo-evidence-helpers.ts +4 -0
  182. package/templates/starter/e2e/browser-orientation-gizmo-live-preconditions.ts +86 -0
  183. package/templates/starter/e2e/browser-render-scale-evidence.ts +37 -29
  184. package/templates/starter/e2e/browser-runtime-applicability-requirements.ts +84 -0
  185. package/templates/starter/e2e/browser-runtime-evidence-reporter.ts +13 -3
  186. package/templates/starter/e2e/browser-runtime-evidence-requirements.ts +72 -35
  187. package/templates/starter/e2e/browser-semantic-evidence-test-helpers.ts +25 -0
  188. package/templates/starter/e2e/browser-standard-timeline-evidence.ts +106 -0
  189. package/templates/starter/e2e/decoded-pixel-observation.spec.ts +74 -0
  190. package/templates/starter/e2e/decoded-pixel-observation.ts +227 -0
  191. package/templates/starter/e2e/export-artifact-helpers.ts +206 -25
  192. package/templates/starter/e2e/image-artifact-inspection.spec.ts +41 -0
  193. package/templates/starter/e2e/image-artifact-inspection.ts +99 -0
  194. package/templates/starter/e2e/performance-canvas-helpers.ts +22 -21
  195. package/templates/starter/e2e/performance-canvas-quality-guard.spec.ts +312 -0
  196. package/templates/starter/e2e/performance-canvas-quality-guard.ts +196 -0
  197. package/templates/starter/e2e/performance-canvas-quality-observer.ts +351 -0
  198. package/templates/starter/e2e/performance-control-layout-helpers.ts +2 -2
  199. package/templates/starter/e2e/performance-path-adapter-contract.ts +4 -4
  200. package/templates/starter/e2e/performance-path-helpers.spec.ts +203 -70
  201. package/templates/starter/e2e/performance-path-helpers.ts +210 -91
  202. package/templates/starter/e2e/performance-pipeline-evidence-continuity.spec.ts +76 -0
  203. package/templates/starter/e2e/performance-pipeline-evidence-test-fixtures.ts +11 -2
  204. package/templates/starter/e2e/performance-pipeline-invariants.ts +47 -4
  205. package/templates/starter/e2e/performance-render-scale-runner.spec.ts +140 -38
  206. package/templates/starter/e2e/video-artifact-inspection.spec.ts +64 -0
  207. package/templates/starter/e2e/video-artifact-inspection.ts +281 -0
  208. package/templates/starter/gitignore +1 -0
  209. package/templates/starter/package.json +1 -0
  210. package/templates/starter/scripts/check-toolcraft-docs.mjs +17 -0
  211. package/templates/starter/scripts/toolcraft-contract-manifest.json +1 -0
  212. package/templates/starter/scripts/toolcraft-delivery-plan-authority.test.mjs +60 -0
  213. package/templates/starter/scripts/toolcraft-delivery-plan-errors.test.mjs +7 -2
  214. package/templates/starter/scripts/toolcraft-delivery-plan.mjs +7 -3
  215. package/templates/starter/scripts/toolcraft-product-boundary-ast.mjs +95 -103
  216. package/templates/starter/scripts/toolcraft-product-boundary-module-policy.mjs +101 -0
  217. package/templates/starter/scripts/toolcraft-product-boundary.mjs +12 -0
  218. package/templates/starter/scripts/toolcraft-product-boundary.test.mjs +0 -26
  219. package/templates/starter/scripts/toolcraft-product-control-bindings.mjs +182 -0
  220. package/templates/starter/scripts/toolcraft-product-control-boundary.mjs +146 -0
  221. package/templates/starter/scripts/toolcraft-product-control-boundary.test.mjs +186 -0
  222. package/templates/starter/scripts/toolcraft-product-evidence-boundary.test.mjs +85 -20
  223. package/templates/starter/scripts/toolcraft-product-evidence-import-policy.mjs +43 -0
  224. package/templates/starter/scripts/toolcraft-product-export-boundary.mjs +157 -0
  225. package/templates/starter/scripts/toolcraft-product-export-boundary.test.mjs +196 -0
  226. package/templates/starter/scripts/toolcraft-typescript-analysis.d.mts +73 -0
  227. package/templates/starter/scripts/toolcraft-typescript-source-evidence-structure.test.mjs +20 -0
  228. package/templates/starter/scripts/toolcraft-typescript-source-evidence.mjs +1 -0
  229. package/templates/starter/scripts/toolcraft-unavailable-resource-evidence-facade-test-helpers.mjs +318 -0
  230. package/templates/starter/scripts/toolcraft-unavailable-resource-evidence-facade.test.mjs +157 -206
  231. package/templates/starter/scripts/toolcraft-verification-inventory.mjs +1 -0
  232. package/templates/starter/scripts/toolcraft-verification-receipt.test.mjs +51 -0
  233. package/templates/starter/scripts/toolcraft-vite-env-activation.test.mjs +128 -59
  234. package/templates/starter/src/app/acceptance/artifact-export-intent.ts +130 -0
  235. package/templates/starter/src/app/acceptance/conditions.ts +1 -1
  236. package/templates/starter/src/app/acceptance/control-acceptance-context.ts +2 -2
  237. package/templates/starter/src/app/acceptance/control-acceptance-coverage.ts +6 -20
  238. package/templates/starter/src/app/acceptance/control-acceptance-kind-rules.ts +24 -5
  239. package/templates/starter/src/app/acceptance/control-acceptance-policy.ts +2 -13
  240. package/templates/starter/src/app/acceptance/control-applicability-cases.test.ts +321 -0
  241. package/templates/starter/src/app/acceptance/control-applicability-cases.ts +290 -0
  242. package/templates/starter/src/app/acceptance/control-applicability.ts +332 -0
  243. package/templates/starter/src/app/acceptance/control-layout-dependency-rules.ts +20 -9
  244. package/templates/starter/src/app/acceptance/control-layout-entity-rules.ts +4 -6
  245. package/templates/starter/src/app/acceptance/control-layout-model.ts +4 -4
  246. package/templates/starter/src/app/acceptance/control-layout-section-rules.ts +3 -10
  247. package/templates/starter/src/app/acceptance/control-parts.ts +8 -0
  248. package/templates/starter/src/app/acceptance/control-section-entity-cohesion.test.ts +215 -0
  249. package/templates/starter/src/app/acceptance/control-section-entity-cohesion.ts +132 -0
  250. package/templates/starter/src/app/acceptance/control-section-inventory.test.ts +87 -0
  251. package/templates/starter/src/app/acceptance/control-section-inventory.ts +74 -44
  252. package/templates/starter/src/app/acceptance/custom-controls.ts +11 -3
  253. package/templates/starter/src/app/acceptance/export-artifact-coverage.ts +113 -0
  254. package/templates/starter/src/app/acceptance/inline-layout.ts +64 -9
  255. package/templates/starter/src/app/acceptance/media-upload.ts +5 -1
  256. package/templates/starter/src/app/acceptance/orientation-gizmo.ts +18 -11
  257. package/templates/starter/src/app/acceptance/output-background-rules.ts +2 -2
  258. package/templates/starter/src/app/acceptance/output-export-layout-rules.ts +18 -10
  259. package/templates/starter/src/app/acceptance/output-export-model.ts +54 -11
  260. package/templates/starter/src/app/acceptance/output-export.ts +35 -12
  261. package/templates/starter/src/app/acceptance/output-video-export-rules.ts +99 -0
  262. package/templates/starter/src/app/acceptance/types.ts +30 -8
  263. package/templates/starter/src/app/acceptance/validate-coverage.ts +20 -2
  264. package/templates/starter/src/app/starter-acceptance.artifact-export-intent.test.ts +239 -0
  265. package/templates/starter/src/app/starter-acceptance.background-export.test.ts +33 -0
  266. package/templates/starter/src/app/starter-acceptance.canvas-sizing.test.ts +16 -1
  267. package/templates/starter/src/app/starter-acceptance.compound-part-coverage.test.ts +65 -0
  268. package/templates/starter/src/app/starter-acceptance.contract-fixtures.test.ts +41 -0
  269. package/templates/starter/src/app/starter-acceptance.contract-fixtures.ts +112 -16
  270. package/templates/starter/src/app/starter-acceptance.control-applicability.test.ts +224 -0
  271. package/templates/starter/src/app/starter-acceptance.control-order.test.ts +58 -3
  272. package/templates/starter/src/app/starter-acceptance.control-state.test.ts +0 -111
  273. package/templates/starter/src/app/starter-acceptance.custom-control-collections.test.ts +3 -1
  274. package/templates/starter/src/app/starter-acceptance.custom-control-valid.test.ts +1 -1
  275. package/templates/starter/src/app/starter-acceptance.export-artifact.test.ts +131 -0
  276. package/templates/starter/src/app/starter-acceptance.export-test-utils.ts +22 -0
  277. package/templates/starter/src/app/{starter-acceptance.image-video-export-settings.test.ts → starter-acceptance.image-export-settings.test.ts} +37 -9
  278. package/templates/starter/src/app/starter-acceptance.interaction-ownership.test.ts +12 -0
  279. package/templates/starter/src/app/starter-acceptance.keyframes.test.ts +14 -4
  280. package/templates/starter/src/app/starter-acceptance.media-upload.fixtures.ts +11 -1
  281. package/templates/starter/src/app/starter-acceptance.media-upload.test.ts +28 -0
  282. package/templates/starter/src/app/starter-acceptance.output-export-intent.test.ts +384 -0
  283. package/templates/starter/src/app/starter-acceptance.output-export-rules.test.ts +46 -1
  284. package/templates/starter/src/app/starter-acceptance.product-output-export.test.ts +112 -105
  285. package/templates/starter/src/app/starter-acceptance.product-readiness.test.ts +12 -0
  286. package/templates/starter/src/app/starter-acceptance.section-cohesion.test.ts +1 -1
  287. package/templates/starter/src/app/starter-acceptance.section-dependencies.test.ts +35 -24
  288. package/templates/starter/src/app/starter-acceptance.section-size.test.ts +72 -0
  289. package/templates/starter/src/app/starter-acceptance.ts +13 -2
  290. package/templates/starter/src/app/starter-acceptance.video-export-settings.test.ts +336 -0
  291. package/templates/starter/src/app/starter-acceptance.view-interaction.test.ts +8 -0
  292. package/templates/starter/src/app/starter-performance-test-utils.ts +103 -0
  293. package/templates/starter/src/app/starter-performance.gates.test.ts +231 -278
  294. package/templates/starter/src/app/starter-performance.lifecycle.test.ts +261 -0
  295. package/templates/starter/src/app/test-evidence/browser-runtime-contract.ts +4 -2
  296. package/templates/starter/src/routes/index.tsx +2 -0
  297. package/templates/ui/components/composites/tabs.tsx +2 -2
  298. package/templates/ui/components/controls/collection-actions/collection-item-groups.test.tsx +38 -0
  299. package/templates/ui/components/controls/collection-actions/collection-item-groups.tsx +36 -0
  300. package/templates/ui/components/controls/collection-actions/index.ts +2 -0
  301. package/templates/ui/components/controls/file-drop/file-drop-collection-control.tsx +137 -0
  302. package/templates/ui/components/controls/file-drop/file-drop-control.test.tsx +189 -0
  303. package/templates/ui/components/controls/file-drop/file-drop-control.tsx +81 -88
  304. package/templates/ui/components/controls/file-drop/file-drop-presentation.tsx +131 -9
  305. package/templates/ui/components/controls/file-drop/file-drop-types.ts +36 -22
  306. package/templates/ui/components/controls/file-drop/index.ts +1 -0
  307. package/templates/ui/components/controls/index.ts +3 -0
  308. package/templates/ui/components/controls/range-slider/range-slider-control.tsx +1 -1
  309. package/templates/ui/components/controls/range-slider/range-slider-value.test.ts +14 -0
  310. package/templates/ui/components/controls/range-slider/range-slider-value.ts +3 -2
  311. package/templates/runtime/export/export.ts +0 -166
  312. package/templates/starter/src/app/acceptance/condition-exclusivity.test.ts +0 -60
  313. package/templates/starter/src/app/acceptance/condition-exclusivity.ts +0 -221
@@ -0,0 +1,157 @@
1
+ import ts from "typescript";
2
+ const forbiddenGlobalExportConstructors = new Set([
3
+ "MediaRecorder",
4
+ "VideoEncoder",
5
+ ]);
6
+ const forbiddenCanvasExportMethods = new Set([
7
+ "captureStream",
8
+ "toBlob",
9
+ "toDataURL",
10
+ ]);
11
+
12
+ export function getToolcraftProductExportModuleKind(
13
+ normalizedSpecifier,
14
+ resolvedSpecifier,
15
+ ) {
16
+ if (/^mediabunny(?:\/|$)/u.test(normalizedSpecifier)) {
17
+ return "runtime-export-mechanics";
18
+ }
19
+ if (
20
+ /^@repo\/toolcraft-runtime\/export(?:\/|$)/u.test(normalizedSpecifier) ||
21
+ /^[#@]\/toolcraft\/runtime\/export(?:\/|$)/u.test(normalizedSpecifier) ||
22
+ /\/src\/toolcraft\/runtime\/export(?:\/|$)/u.test(resolvedSpecifier ?? "")
23
+ ) {
24
+ return "runtime-export-mechanics";
25
+ }
26
+ return null;
27
+ }
28
+
29
+ export function isForbiddenToolcraftRuntimeExport(moduleKind) {
30
+ return moduleKind === "runtime-export-mechanics";
31
+ }
32
+
33
+ function getDeclarationScope(node, sourceFile) {
34
+ let current = node.parent;
35
+ while (current) {
36
+ if (
37
+ ts.isSourceFile(current) ||
38
+ ts.isFunctionLike(current) ||
39
+ ts.isBlock(current) ||
40
+ ts.isCatchClause(current)
41
+ ) {
42
+ return current;
43
+ }
44
+ current = current.parent;
45
+ }
46
+ return sourceFile;
47
+ }
48
+
49
+ function collectLexicalDeclarations(sourceFile) {
50
+ const declarations = [];
51
+
52
+ function collectBindingNames(name, scope) {
53
+ if (ts.isIdentifier(name)) {
54
+ declarations.push({ name: name.text, scope });
55
+ } else if (
56
+ ts.isObjectBindingPattern(name) ||
57
+ ts.isArrayBindingPattern(name)
58
+ ) {
59
+ for (const element of name.elements) {
60
+ if (ts.isBindingElement(element)) collectBindingNames(element.name, scope);
61
+ }
62
+ }
63
+ }
64
+
65
+ function visit(node) {
66
+ if (ts.isImportClause(node) && node.name) {
67
+ collectBindingNames(node.name, sourceFile);
68
+ } else if (ts.isImportSpecifier(node) || ts.isNamespaceImport(node)) {
69
+ collectBindingNames(node.name, sourceFile);
70
+ } else if (ts.isVariableDeclaration(node)) {
71
+ collectBindingNames(node.name, getDeclarationScope(node, sourceFile));
72
+ } else if (ts.isParameter(node)) {
73
+ collectBindingNames(node.name, node.parent);
74
+ } else if (
75
+ (ts.isFunctionDeclaration(node) || ts.isClassDeclaration(node)) &&
76
+ node.name
77
+ ) {
78
+ collectBindingNames(node.name, getDeclarationScope(node, sourceFile));
79
+ }
80
+ ts.forEachChild(node, visit);
81
+ }
82
+
83
+ visit(sourceFile);
84
+ return declarations;
85
+ }
86
+
87
+ export function createToolcraftProductExportInspector({
88
+ getNodeLocation,
89
+ repoPath,
90
+ sourceFile,
91
+ }) {
92
+ const lexicalDeclarations = collectLexicalDeclarations(sourceFile);
93
+
94
+ function isLexicallyDeclared(identifier) {
95
+ const ancestorScopes = new Set();
96
+ let current = identifier.parent;
97
+ while (current) {
98
+ if (
99
+ ts.isSourceFile(current) ||
100
+ ts.isFunctionLike(current) ||
101
+ ts.isBlock(current) ||
102
+ ts.isCatchClause(current)
103
+ ) {
104
+ ancestorScopes.add(current);
105
+ }
106
+ current = current.parent;
107
+ }
108
+ return lexicalDeclarations.some(
109
+ (declaration) =>
110
+ declaration.name === identifier.text &&
111
+ ancestorScopes.has(declaration.scope),
112
+ );
113
+ }
114
+
115
+ function violation(node, subject) {
116
+ return {
117
+ ...getNodeLocation(sourceFile, node),
118
+ kind: "runtime-export-ownership",
119
+ message: `Product source must not own ${subject}. Declare exportRenderer and let runtime export actions encode and download the artifact.`,
120
+ repoPath,
121
+ };
122
+ }
123
+
124
+ return (node) => {
125
+ if (
126
+ ts.isNewExpression(node) &&
127
+ ts.isIdentifier(node.expression) &&
128
+ forbiddenGlobalExportConstructors.has(node.expression.text) &&
129
+ !isLexicallyDeclared(node.expression)
130
+ ) {
131
+ return [
132
+ violation(
133
+ node,
134
+ `${node.expression.text} encoder or recorder construction`,
135
+ ),
136
+ ];
137
+ }
138
+ if (
139
+ ts.isCallExpression(node) &&
140
+ ts.isPropertyAccessExpression(node.expression)
141
+ ) {
142
+ const propertyName = node.expression.name.text;
143
+ if (forbiddenCanvasExportMethods.has(propertyName)) {
144
+ return [violation(node, `canvas.${propertyName}() export mechanics`)];
145
+ }
146
+ if (
147
+ propertyName === "createObjectURL" &&
148
+ ts.isIdentifier(node.expression.expression) &&
149
+ node.expression.expression.text === "URL" &&
150
+ !isLexicallyDeclared(node.expression.expression)
151
+ ) {
152
+ return [violation(node, "URL.createObjectURL() artifact delivery")];
153
+ }
154
+ }
155
+ return [];
156
+ };
157
+ }
@@ -0,0 +1,196 @@
1
+ import assert from "node:assert/strict";
2
+ import test from "node:test";
3
+
4
+ import { evaluateToolcraftProductBoundary } from "./toolcraft-product-boundary.mjs";
5
+ import { createToolcraftProductBoundaryFixture as createFixture } from "./toolcraft-product-boundary-test-fixtures.mjs";
6
+
7
+ test("keeps artifact encoding and download mechanics runtime-owned", async (context) => {
8
+ const workspaceRuntimeExportSpecifier = [
9
+ "@repo",
10
+ "toolcraft-runtime",
11
+ "export",
12
+ "image-artifact-export",
13
+ ].join("/");
14
+ const rootDir = await createFixture(context, {
15
+ "src/features/export-mechanics.ts": `
16
+ import { createToolcraftVideoEncoderBackend as createAliasBackend } from "@/toolcraft/runtime/export/video-encoding-backend";
17
+ import { exportToolcraftImageArtifact } from "${workspaceRuntimeExportSpecifier}";
18
+ import { downloadToolcraftArtifact } from "../toolcraft/runtime/export/artifact-download";
19
+ import { Output } from "mediabunny";
20
+ export function exportArtifact(canvas: HTMLCanvasElement) {
21
+ const recorder = new MediaRecorder(canvas.captureStream());
22
+ const encoder = new VideoEncoder({ error() {}, output() {} });
23
+ canvas.toBlob(() => undefined);
24
+ canvas.toDataURL();
25
+ URL.createObjectURL(new Blob());
26
+ void createAliasBackend;
27
+ void exportToolcraftImageArtifact;
28
+ void downloadToolcraftArtifact;
29
+ void Output;
30
+ void recorder;
31
+ void encoder;
32
+ }
33
+ `,
34
+ "src/features/safe-renderer.ts": `
35
+ import * as Runtime from "@/toolcraft/runtime";
36
+ import {
37
+ getToolcraftImageExportSize,
38
+ shouldIncludeToolcraftPreviewBackground,
39
+ validateToolcraftArtifactSize,
40
+ } from "@/toolcraft/runtime";
41
+ import type {
42
+ ToolcraftExportFrame,
43
+ ToolcraftProductExportRenderer,
44
+ } from "@/toolcraft/runtime";
45
+ export const renderFrame = ({ context }) => context.fillRect(0, 0, 1, 1);
46
+ void Runtime;
47
+ void getToolcraftImageExportSize;
48
+ void shouldIncludeToolcraftPreviewBackground;
49
+ void validateToolcraftArtifactSize;
50
+ void (null as unknown as ToolcraftExportFrame);
51
+ void (null as unknown as ToolcraftProductExportRenderer);
52
+ `,
53
+ "src/features/shadowed-globals.ts": `
54
+ export function localNames(MediaRecorder, VideoEncoder, URL) {
55
+ void new MediaRecorder();
56
+ void new VideoEncoder();
57
+ URL.createObjectURL();
58
+ }
59
+ `,
60
+ });
61
+
62
+ const result = await evaluateToolcraftProductBoundary({ rootDir });
63
+
64
+ assert.equal(result.violations.length, 10);
65
+ assert.equal(
66
+ result.violations.every(
67
+ (violation) => violation.kind === "runtime-export-ownership",
68
+ ),
69
+ true,
70
+ );
71
+ assert.equal(
72
+ result.violations.some((violation) =>
73
+ violation.repoPath.endsWith("shadowed-globals.ts"),
74
+ ),
75
+ false,
76
+ );
77
+ assert.equal(
78
+ result.violations.some((violation) =>
79
+ violation.repoPath.endsWith("safe-renderer.ts"),
80
+ ),
81
+ false,
82
+ );
83
+ });
84
+
85
+ test("classifies every runtime export mechanics module reference once", async (context) => {
86
+ const workspaceRuntimeExportRoot = [
87
+ "@repo",
88
+ "toolcraft-runtime",
89
+ "export",
90
+ ].join("/");
91
+ const rootDir = await createFixture(context, {
92
+ "src/features/dynamic-import.ts": `
93
+ export async function loadMedia() {
94
+ return import("mediabunny");
95
+ }
96
+ `,
97
+ "src/features/import-equals.ts": `
98
+ import Backend = require("@/toolcraft/runtime/export/video-encoding-backend");
99
+ void Backend;
100
+ `,
101
+ "src/features/import-type.ts": `
102
+ type Backend = import("@/toolcraft/runtime/export/video-encoding-backend").ToolcraftVideoEncoderBackend;
103
+ void (null as unknown as Backend);
104
+ `,
105
+ "src/features/regular-export.ts": `
106
+ export {
107
+ createToolcraftVideoEncoderBackend as createFirstBackend,
108
+ createToolcraftVideoEncoderBackend as createSecondBackend,
109
+ } from "@/toolcraft/runtime/export/video-encoding-backend";
110
+ `,
111
+ "src/features/regular-import.ts": `
112
+ import {
113
+ createToolcraftVideoEncoderBackend as createFirstBackend,
114
+ createToolcraftVideoEncoderBackend as createSecondBackend,
115
+ } from "@/toolcraft/runtime/export/video-encoding-backend";
116
+ void createFirstBackend;
117
+ void createSecondBackend;
118
+ `,
119
+ "src/features/require.ts": `
120
+ export const backend = require("${workspaceRuntimeExportRoot}/video-encoding-backend");
121
+ `,
122
+ "src/features/safe-root-type-import.ts": `
123
+ import type { ToolcraftExportFrame } from "@/toolcraft/runtime";
124
+ void (null as unknown as ToolcraftExportFrame);
125
+ `,
126
+ "src/features/side-effect-import.ts": `import "mediabunny";`,
127
+ "src/features/type-only-export.ts": `
128
+ export type {
129
+ ToolcraftImageArtifactExportRequest,
130
+ ToolcraftImageArtifactExportResult,
131
+ } from "${workspaceRuntimeExportRoot}/image-artifact-export";
132
+ `,
133
+ "src/features/type-only-import-equals.ts": `
134
+ import type Backend = require("@/toolcraft/runtime/export/video-encoding-backend");
135
+ void (null as unknown as Backend);
136
+ `,
137
+ "src/features/type-only-import.ts": `
138
+ import type {
139
+ ToolcraftVideoArtifactExportRequest,
140
+ ToolcraftVideoArtifactExportResult,
141
+ } from "${workspaceRuntimeExportRoot}/video-artifact-export";
142
+ void (null as unknown as ToolcraftVideoArtifactExportRequest);
143
+ void (null as unknown as ToolcraftVideoArtifactExportResult);
144
+ `,
145
+ "src/features/typeof-import-type.ts": `
146
+ type MediaBunny = typeof import("mediabunny");
147
+ void (null as unknown as MediaBunny);
148
+ `,
149
+ "src/features/export-boundary.test.ts": `
150
+ import type { ToolcraftVideoEncoderBackend } from "@/toolcraft/runtime/export/video-encoding-backend";
151
+ void (null as unknown as ToolcraftVideoEncoderBackend);
152
+ `,
153
+ "e2e/test-support/export-fixture.ts": `
154
+ export type { ToolcraftVideoEncoderBackend } from "@/toolcraft/runtime/export/video-encoding-backend";
155
+ `,
156
+ });
157
+
158
+ const result = await evaluateToolcraftProductBoundary({ rootDir });
159
+
160
+ assert.deepEqual(
161
+ result.violations.map(({ repoPath }) => repoPath).sort(),
162
+ [
163
+ "src/features/dynamic-import.ts",
164
+ "src/features/import-equals.ts",
165
+ "src/features/import-type.ts",
166
+ "src/features/regular-export.ts",
167
+ "src/features/regular-import.ts",
168
+ "src/features/require.ts",
169
+ "src/features/side-effect-import.ts",
170
+ "src/features/type-only-export.ts",
171
+ "src/features/type-only-import-equals.ts",
172
+ "src/features/type-only-import.ts",
173
+ "src/features/typeof-import-type.ts",
174
+ ],
175
+ );
176
+ assert.equal(
177
+ new Set(result.violations.map(({ repoPath }) => repoPath)).size,
178
+ result.violations.length,
179
+ );
180
+ assert.equal(
181
+ result.violations.every(
182
+ (violation) => violation.kind === "runtime-export-ownership",
183
+ ),
184
+ true,
185
+ );
186
+ assert.equal(
187
+ result.violations.some(({ repoPath }) =>
188
+ [
189
+ "src/features/export-boundary.test.ts",
190
+ "src/features/safe-root-type-import.ts",
191
+ "e2e/test-support/export-fixture.ts",
192
+ ].includes(repoPath),
193
+ ),
194
+ false,
195
+ );
196
+ });
@@ -0,0 +1,73 @@
1
+ import type ts from "typescript";
2
+
3
+ export type ToolcraftTypeScriptImportedBinding = Readonly<{
4
+ importedName: string;
5
+ localName: string;
6
+ specifier: string;
7
+ }>;
8
+
9
+ export type ToolcraftTypeScriptImportedCallTarget = Readonly<{
10
+ callerCallableId: string | null;
11
+ callerExportNames: readonly string[];
12
+ importedName: string;
13
+ localName: string;
14
+ memberPath: string;
15
+ operation: string;
16
+ specifier: string;
17
+ }>;
18
+
19
+ export type ToolcraftTypeScriptModuleBindings = Readonly<{
20
+ callables: unknown;
21
+ exportedCallableBindings: readonly Readonly<{
22
+ callableId: string;
23
+ exportedName: string;
24
+ }>[];
25
+ exportedRuntimeBindings: readonly string[];
26
+ importedBindingSymbols: readonly Readonly<{
27
+ binding: ToolcraftTypeScriptImportedBinding;
28
+ symbol: ts.Symbol;
29
+ }>[];
30
+ importedRuntimeBindings: readonly ToolcraftTypeScriptImportedBinding[];
31
+ }>;
32
+
33
+ export function createToolcraftTypeScriptChecker(
34
+ sourceFile: ts.SourceFile,
35
+ typescript: typeof ts,
36
+ ): ts.TypeChecker;
37
+
38
+ export function collectToolcraftTypeScriptModuleBindings(
39
+ sourceFile: ts.SourceFile,
40
+ typescript: typeof ts,
41
+ checker?: ts.TypeChecker,
42
+ callables?: unknown,
43
+ ): ToolcraftTypeScriptModuleBindings;
44
+
45
+ export function collectToolcraftTypeScriptCallTargets(input: Readonly<{
46
+ bindings: ToolcraftTypeScriptModuleBindings;
47
+ checker: ts.TypeChecker;
48
+ sourceFile: ts.SourceFile;
49
+ ts: typeof ts;
50
+ }>): Readonly<{
51
+ importedCallTargets: readonly ToolcraftTypeScriptImportedCallTarget[];
52
+ localCallTargets: readonly Readonly<{
53
+ calleeCallableId: string;
54
+ callerCallableId: string;
55
+ }>[];
56
+ }>;
57
+
58
+ export function getToolcraftTypeScriptImportedCallTarget(input: Readonly<{
59
+ bindings: ToolcraftTypeScriptModuleBindings;
60
+ checker: ts.TypeChecker;
61
+ expression: ts.Expression;
62
+ ts: typeof ts;
63
+ }>):
64
+ | Omit<
65
+ ToolcraftTypeScriptImportedCallTarget,
66
+ "callerCallableId" | "callerExportNames"
67
+ >
68
+ | undefined;
69
+
70
+ export function unwrapToolcraftTypeScriptExpression(
71
+ node: ts.Expression,
72
+ typescript: typeof ts,
73
+ ): ts.Expression;
@@ -41,4 +41,24 @@ test("keeps TypeScript parsing and boundary facts on one canonical path", async
41
41
  assert.deepEqual(checkerOwners, [
42
42
  "toolcraft-typescript-analysis.mjs",
43
43
  ]);
44
+
45
+ const productBoundarySource = await fs.readFile(
46
+ path.join(scriptsDir, "toolcraft-product-boundary-ast.mjs"),
47
+ "utf8",
48
+ );
49
+ const controlBoundarySource = await fs.readFile(
50
+ path.join(scriptsDir, "toolcraft-product-control-boundary.mjs"),
51
+ "utf8",
52
+ );
53
+ const modulePolicySource = await fs.readFile(
54
+ path.join(scriptsDir, "toolcraft-product-boundary-module-policy.mjs"),
55
+ "utf8",
56
+ );
57
+
58
+ assert.match(productBoundarySource, /createToolcraftProductControlInspector/u);
59
+ assert.match(
60
+ modulePolicySource,
61
+ /isToolcraftPrivateControlImplementationModule/u,
62
+ );
63
+ assert.doesNotMatch(controlBoundarySource, /(?:ts\.)?createSourceFile\(/u);
44
64
  });
@@ -300,6 +300,7 @@ export async function createToolcraftTypeScriptSourceRecord({
300
300
  inspectors.createToolcraftStaticStringResolver(sourceFile, checker);
301
301
  const inspectorInput = {
302
302
  absolutePath,
303
+ checker,
303
304
  getNodeLocation,
304
305
  repoPath,
305
306
  resolveStaticString,