@salsita-ai/sdk 0.50.0-develop.b335a15889 → 0.50.0-develop.b9eb39baf0

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 (366) hide show
  1. package/dist/application-spec/generate-application/code/common/index.d.ts +1 -0
  2. package/dist/application-spec/generate-application/code/common/index.js +1 -1
  3. package/dist/application-spec/generate-application/code/common/project-module-list.d.ts +8 -0
  4. package/dist/application-spec/generate-application/code/common/project-module-list.js +3 -0
  5. package/dist/application-spec/generate-application/code/domain-runtime-files.js +1 -1
  6. package/dist/application-spec/generate-application/code/templates/admin-domain-code.d.ts +1 -2
  7. package/dist/application-spec/generate-application/code/templates/admin-domain-code.js +6 -14
  8. package/dist/application-spec/generate-application/code/templates/admin-frontend-code.d.ts +1 -2
  9. package/dist/application-spec/generate-application/code/templates/admin-frontend-code.js +4 -4
  10. package/dist/application-spec/generate-application/code/templates/configurator-domain-code.d.ts +1 -2
  11. package/dist/application-spec/generate-application/code/templates/configurator-domain-code.js +7 -16
  12. package/dist/application-spec/generate-application/code/templates/configurator-frontend-code.d.ts +1 -2
  13. package/dist/application-spec/generate-application/code/templates/configurator-frontend-code.js +7 -9
  14. package/dist/application-spec/generate-application/code/templates/domain.js +3 -3
  15. package/dist/application-spec/generate-application/code/templates/skills/phoenix-review-skill.js +1 -1
  16. package/dist/application-spec/generate-application/code/templates/skills/sdk-content.d.ts +2 -1
  17. package/dist/application-spec/generate-application/code/templates/skills/sdk-content.js +1 -2
  18. package/dist/application-spec/generate-application/code/templates/webhook-builders.js +3 -3
  19. package/dist/docs/complex-use-cases/filtered-controls-with-fix-dialog.mdx +84 -98
  20. package/dist/docs/complex-use-cases/navigation-reset-selection.mdx +18 -12
  21. package/dist/docs/index.json +1 -1
  22. package/dist/docs/layouts/custom-price.mdx +14 -16
  23. package/dist/docs/layouts/sidebar/tabs.mdx +24 -21
  24. package/dist/docs/other-features/domain-actions.mdx +1 -1
  25. package/dist/docs/other-features/side-effects.mdx +42 -34
  26. package/dist/docs/other-features/transformers.mdx +1 -1
  27. package/dist/docs/phoenix/admin.mdx +9 -24
  28. package/dist/docs/phoenix/localization.mdx +3 -22
  29. package/dist/docs/phoenix/project-structure.mdx +6 -0
  30. package/dist/docs/recipes-and-delete/recipe-hierarchy-selection.mdx +15 -13
  31. package/dist/docs/relations/hierarchy.mdx +13 -2
  32. package/dist/domain/actions/action-factory.d.ts +4 -4
  33. package/dist/domain/admin-domain/__generated/enhanced-model.d.ts +1 -1
  34. package/dist/domain/admin-domain/__generated/model/versions/v1.d.ts +1 -1
  35. package/dist/domain/admin-domain/__generated/model/versions/v2.d.ts +1 -1
  36. package/dist/domain/admin-domain/__generated/model/versions/v3.d.ts +1 -1
  37. package/dist/domain/admin-domain/__generated/model/versions/v4.d.ts +1 -1
  38. package/dist/domain/admin-domain/__generated/model/versions/v5.d.ts +1 -1
  39. package/dist/domain/admin-domain/__generated/model/versions/v6.d.ts +2 -2
  40. package/dist/domain/admin-domain/__generated/model/versions/v6.js +1 -1
  41. package/dist/domain/admin-domain/implementation/common-admin-expressions.d.ts +1 -3
  42. package/dist/domain/admin-domain/implementation/common-admin-migrations.d.ts +1 -1
  43. package/dist/domain/admin-domain/index.d.ts +1 -1
  44. package/dist/domain/application/admin-page-factories.d.ts +1 -1
  45. package/dist/domain/application/application-config.d.ts +23 -13
  46. package/dist/domain/application/assistant-field-options.d.ts +1 -2
  47. package/dist/domain/application/assistant-mutations.d.ts +1 -3
  48. package/dist/domain/application/assistant-mutations.js +1 -1
  49. package/dist/domain/application/assistant-recipe-groups.d.ts +1 -3
  50. package/dist/domain/application/configurator-builder.d.ts +30 -16
  51. package/dist/domain/application/configurator-builder.js +1 -1
  52. package/dist/domain/application/element-registration.d.ts +5 -0
  53. package/dist/domain/application/element-registration.js +1 -1
  54. package/dist/domain/application/handler-registration.d.ts +5 -0
  55. package/dist/domain/application/handler-registration.js +1 -1
  56. package/dist/domain/application/index.d.ts +4 -4
  57. package/dist/domain/application/index.js +1 -1
  58. package/dist/domain/application/published-data/create-finalize-admin-domain.d.ts +1 -2
  59. package/dist/domain/application/published-data/map-published-chunked-data.d.ts +1 -1
  60. package/dist/domain/application/published-data/map-published-data.d.ts +1 -2
  61. package/dist/domain/application/resolve-imported-transformers.d.ts +12 -2
  62. package/dist/domain/application/resolve-imported-transformers.js +1 -1
  63. package/dist/domain/components/component-reader-types.d.ts +1 -2
  64. package/dist/domain/components/debug-state-component.d.ts +1 -1
  65. package/dist/domain/components/debug-state-component.js +1 -1
  66. package/dist/domain/components/domain-component-optic.d.ts +4 -5
  67. package/dist/domain/components/domain-component-optic.js +2 -2
  68. package/dist/domain/components/drag-state-component.d.ts +1 -1
  69. package/dist/domain/components/drag-state-component.js +1 -1
  70. package/dist/domain/components/export-state-component.d.ts +1 -1
  71. package/dist/domain/components/export-state-component.js +1 -1
  72. package/dist/domain/components/fullscreen-state-component.d.ts +1 -1
  73. package/dist/domain/components/fullscreen-state-component.js +1 -1
  74. package/dist/domain/components/group-components-by-entity-id-and-name.d.ts +1 -2
  75. package/dist/domain/components/group-components-by-entity-id-and-name.js +1 -1
  76. package/dist/domain/components/hover-state-component.d.ts +1 -1
  77. package/dist/domain/components/hover-state-component.js +1 -1
  78. package/dist/domain/components/legacy-filter.d.ts +1 -2
  79. package/dist/domain/components/navigation-state-component.d.ts +1 -1
  80. package/dist/domain/components/navigation-state-component.js +1 -1
  81. package/dist/domain/components/selection-state-component.d.ts +1 -1
  82. package/dist/domain/components/selection-state-component.js +1 -1
  83. package/dist/domain/components/system-component-builder.d.ts +1 -2
  84. package/dist/domain/components/system-component-builder.js +1 -1
  85. package/dist/domain/components/system-component-filter.d.ts +1 -3
  86. package/dist/domain/components/system-virtual-entity.js +1 -1
  87. package/dist/domain/components/tool-state-component.d.ts +1 -1
  88. package/dist/domain/components/tool-state-component.js +1 -1
  89. package/dist/domain/components/updates.d.ts +1 -2
  90. package/dist/domain/components/view-state-component.d.ts +1 -1
  91. package/dist/domain/components/view-state-component.js +1 -1
  92. package/dist/domain/components/viewport-state-component.d.ts +1 -1
  93. package/dist/domain/components/viewport-state-component.js +1 -1
  94. package/dist/domain/core/action.d.ts +2 -2
  95. package/dist/domain/core/decoder/create-decoder.d.ts +6 -0
  96. package/dist/domain/core/decoder/create-decoder.js +1 -0
  97. package/dist/domain/core/decoder/decoder.d.ts +6 -0
  98. package/dist/domain/core/decoder/index.d.ts +2 -0
  99. package/dist/domain/core/decoder/index.js +1 -0
  100. package/dist/domain/core/domain-factory.d.ts +1 -2
  101. package/dist/domain/core/domain-factory.js +1 -1
  102. package/dist/domain/core/domain.d.ts +1 -2
  103. package/dist/domain/core/domain.js +1 -1
  104. package/dist/domain/core/expression.d.ts +1 -2
  105. package/dist/domain/core/index.d.ts +8 -17
  106. package/dist/domain/core/index.js +1 -1
  107. package/dist/domain/core/migrations.d.ts +1 -2
  108. package/dist/domain/core/{component.d.ts → model/component.d.ts} +1 -1
  109. package/dist/domain/core/model/index.d.ts +6 -0
  110. package/dist/domain/core/model/index.js +1 -0
  111. package/dist/domain/core/{reflection.d.ts → model/reflection.d.ts} +1 -1
  112. package/dist/domain/core/model/reflection.js +1 -0
  113. package/dist/domain/core/schema/extended-schema-validator.js +1 -0
  114. package/dist/domain/core/schema/index.d.ts +3 -0
  115. package/dist/domain/core/schema/index.js +1 -0
  116. package/dist/domain/core/schema/schema-validator.js +1 -0
  117. package/dist/domain/core/state.d.ts +1 -2
  118. package/dist/domain/domain-builder.d.ts +11 -8
  119. package/dist/domain/domain-builder.js +1 -1
  120. package/dist/domain/domain-context/action-system/action-system.d.ts +1 -3
  121. package/dist/domain/domain-context/action-system/action-system.js +1 -1
  122. package/dist/domain/domain-context/create-transformer.d.ts +1 -1
  123. package/dist/domain/domain-context/domain-context-systems.d.ts +1 -3
  124. package/dist/domain/domain-context/navigation-system/navigation-system.d.ts +1 -2
  125. package/dist/domain/domain-context/navigation-system/navigation-updates.d.ts +1 -1
  126. package/dist/domain/domain-context/navigation-system/selection-transformers.d.ts +1 -1
  127. package/dist/domain/domain-context/navigation-system/selection-transformers.js +1 -1
  128. package/dist/domain/domain-context/recipe-system/recipes.d.ts +1 -3
  129. package/dist/domain/domain-context/recipe-system/recipes.js +1 -1
  130. package/dist/domain/domain-context/relation-transformers/cascade-deletes.d.ts +1 -1
  131. package/dist/domain/domain-context/relation-transformers/cascade-deletes.js +1 -1
  132. package/dist/domain/domain-context/relation-transformers/cascade-ref-pruning.d.ts +1 -1
  133. package/dist/domain/domain-context/relation-transformers/create-entity-refs.d.ts +1 -1
  134. package/dist/domain/domain-context/relation-transformers/replace-refs.d.ts +1 -1
  135. package/dist/domain/domain-context/store-system/apply-updates.d.ts +1 -2
  136. package/dist/domain/domain-context/store-system/apply-updates.js +1 -1
  137. package/dist/domain/domain-context/store-system/next-domain-entity-id.d.ts +1 -2
  138. package/dist/domain/domain-context/store-system/next-domain-entity-id.js +1 -1
  139. package/dist/domain/domain-context/store-system/reconcile-projected-entities.d.ts +1 -1
  140. package/dist/domain/domain-context/store-system/store-system.d.ts +1 -3
  141. package/dist/domain/domain-context/store-system/store-system.js +1 -1
  142. package/dist/domain/domain-context/store-system/system-state.d.ts +1 -3
  143. package/dist/domain/domain-context/transformers/actions-builder.d.ts +1 -1
  144. package/dist/domain/domain-context/transformers/actions-builder.js +1 -1
  145. package/dist/domain/domain-context/transformers/auto-snap-transformer.d.ts +1 -2
  146. package/dist/domain/domain-context/transformers/chain-builder.d.ts +2 -2
  147. package/dist/domain/domain-context/transformers/context.d.ts +1 -2
  148. package/dist/domain/domain-context/transformers/entity-builder.d.ts +1 -1
  149. package/dist/domain/domain-context/transformers/entity-builder.js +1 -1
  150. package/dist/domain/domain-context/transformers/then-builder.d.ts +1 -1
  151. package/dist/domain/domain-context/transformers/then-builder.js +1 -1
  152. package/dist/domain/domain-context/transformers/when-builder.d.ts +1 -2
  153. package/dist/domain/domain-context/transformers/when-builder.js +1 -1
  154. package/dist/domain/domain-context/undo-system.d.ts +1 -1
  155. package/dist/domain/domain-runtime/domain-context/component-reader.d.ts +1 -3
  156. package/dist/domain/domain-runtime/domain-context/component-reader.js +1 -1
  157. package/dist/domain/domain-runtime/domain-context/selectors.d.ts +1 -2
  158. package/dist/domain/domain-runtime/domain-context/selectors.js +1 -1
  159. package/dist/domain/domain-runtime/spec/initialize.js +1 -1
  160. package/dist/domain/expressions/constant-expressions.d.ts +1 -3
  161. package/dist/domain/expressions/custom-expression.d.ts +1 -4
  162. package/dist/domain/expressions/memoize-expression.d.ts +1 -2
  163. package/dist/domain/expressions/prepare-domain-expressions.d.ts +1 -1
  164. package/dist/domain/index.d.ts +3 -2
  165. package/dist/domain/index.js +1 -1
  166. package/dist/domain/invariants/builtin-invariant.d.ts +1 -2
  167. package/dist/domain/invariants/custom-invariants.d.ts +1 -2
  168. package/dist/domain/invariants/invariants.d.ts +10 -4
  169. package/dist/domain/invariants/invariants.js +1 -1
  170. package/dist/domain/invariants/violation.d.ts +1 -1
  171. package/dist/domain/mocks/create-mock-domain-runtime.d.ts +1 -1
  172. package/dist/domain/mocks/create-mock-domain-runtime.js +1 -1
  173. package/dist/domain/project-modules/index.d.ts +1 -0
  174. package/dist/domain/project-modules/index.js +1 -0
  175. package/dist/domain/project-modules/project-modules.d.ts +41 -0
  176. package/dist/domain/project-modules/project-modules.js +1 -0
  177. package/dist/domain/projections/projected-entities-projections.d.ts +1 -2
  178. package/dist/domain/projections/snap-matching.d.ts +1 -2
  179. package/dist/domain/projections/snap-utils.d.ts +1 -2
  180. package/dist/domain/relations/all-of-type-relation.d.ts +1 -4
  181. package/dist/domain/relations/all-of-type-relation.js +1 -1
  182. package/dist/domain/relations/component-factories.d.ts +1 -2
  183. package/dist/domain/relations/composed-of.d.ts +1 -1
  184. package/dist/domain/relations/composed-of.js +1 -1
  185. package/dist/domain/relations/direct-relation.d.ts +1 -3
  186. package/dist/domain/relations/indirect-relation.d.ts +1 -4
  187. package/dist/domain/relations/indirect-relation.js +1 -1
  188. package/dist/domain/relations/reference-component.d.ts +1 -2
  189. package/dist/domain/relations/reference-component.js +1 -1
  190. package/dist/domain/relations/reference-field.d.ts +1 -1
  191. package/dist/domain/relations/relation-factory.d.ts +1 -3
  192. package/dist/domain/relations/relation-implementation.d.ts +1 -4
  193. package/dist/domain/system-components/admin-sidebar.d.ts +1 -1
  194. package/dist/domain/system-components/admin-sidebar.js +1 -1
  195. package/dist/domain/system-components/angle-indicator.d.ts +1 -1
  196. package/dist/domain/system-components/angle-indicator.js +1 -1
  197. package/dist/domain/system-components/application-config.d.ts +1 -1
  198. package/dist/domain/system-components/application-config.js +1 -1
  199. package/dist/domain/system-components/attribute-selection.js +1 -1
  200. package/dist/domain/system-components/autorotate-camera-component.d.ts +1 -1
  201. package/dist/domain/system-components/basic-sidebar-footer.d.ts +1 -1
  202. package/dist/domain/system-components/basic-sidebar-footer.js +1 -1
  203. package/dist/domain/system-components/bounding-box-component.d.ts +1 -1
  204. package/dist/domain/system-components/bounding-sphere-component.d.ts +1 -1
  205. package/dist/domain/system-components/camera-based-hidden-entity-object.js +1 -1
  206. package/dist/domain/system-components/camera-based-hidden-entity.js +1 -1
  207. package/dist/domain/system-components/canvas-config.d.ts +1 -1
  208. package/dist/domain/system-components/canvas-config.js +1 -1
  209. package/dist/domain/system-components/canvas-padding.d.ts +1 -1
  210. package/dist/domain/system-components/canvas-padding.js +1 -1
  211. package/dist/domain/system-components/canvas-preset-environment.d.ts +1 -1
  212. package/dist/domain/system-components/canvas-preset-environment.js +1 -1
  213. package/dist/domain/system-components/child-entity-selection.d.ts +1 -1
  214. package/dist/domain/system-components/client-side-image.js +1 -1
  215. package/dist/domain/system-components/collision-box-geometry.d.ts +1 -1
  216. package/dist/domain/system-components/collision-geometries.d.ts +1 -1
  217. package/dist/domain/system-components/collision-geometry.d.ts +1 -1
  218. package/dist/domain/system-components/collision-point-geometry.d.ts +1 -1
  219. package/dist/domain/system-components/common/dimension-indicator-schema.d.ts +1 -1
  220. package/dist/domain/system-components/common/dimension-indicator-schema.js +1 -1
  221. package/dist/domain/system-components/constraint.d.ts +1 -1
  222. package/dist/domain/system-components/create-blueprint.d.ts +1 -1
  223. package/dist/domain/system-components/custom-header.d.ts +1 -1
  224. package/dist/domain/system-components/custom-header.js +1 -1
  225. package/dist/domain/system-components/custom-scene-entity.d.ts +1 -1
  226. package/dist/domain/system-components/custom-scene-entity.js +1 -1
  227. package/dist/domain/system-components/custom-sidebar-footer.d.ts +1 -1
  228. package/dist/domain/system-components/custom-sidebar-footer.js +1 -1
  229. package/dist/domain/system-components/dimension-indicator.d.ts +1 -1
  230. package/dist/domain/system-components/dimension-indicator.js +1 -1
  231. package/dist/domain/system-components/distance-dimension-select.d.ts +1 -1
  232. package/dist/domain/system-components/distance-dimension-select.js +1 -1
  233. package/dist/domain/system-components/distance-dimension.d.ts +1 -1
  234. package/dist/domain/system-components/distance-dimension.js +1 -1
  235. package/dist/domain/system-components/drag-handle.d.ts +1 -1
  236. package/dist/domain/system-components/drag-handle.js +1 -1
  237. package/dist/domain/system-components/editable-angle-indicator.d.ts +1 -1
  238. package/dist/domain/system-components/editable-angle-indicator.js +1 -1
  239. package/dist/domain/system-components/editable-distance-dimension-indicator.d.ts +1 -1
  240. package/dist/domain/system-components/editable-distance-dimension-indicator.js +1 -1
  241. package/dist/domain/system-components/editable-offset-indicator.d.ts +1 -1
  242. package/dist/domain/system-components/editable-offset-indicator.js +1 -1
  243. package/dist/domain/system-components/editable-size-indicator.d.ts +1 -1
  244. package/dist/domain/system-components/editable-size-indicator.js +1 -1
  245. package/dist/domain/system-components/exit-tool-mode-fab.d.ts +1 -1
  246. package/dist/domain/system-components/exit-tool-mode-fab.js +1 -1
  247. package/dist/domain/system-components/finalize-action.d.ts +1 -1
  248. package/dist/domain/system-components/finalize-action.js +1 -1
  249. package/dist/domain/system-components/fixed-header.d.ts +1 -1
  250. package/dist/domain/system-components/fixed-header.js +1 -1
  251. package/dist/domain/system-components/floating-header.d.ts +1 -1
  252. package/dist/domain/system-components/floating-header.js +1 -1
  253. package/dist/domain/system-components/generic-dimension.d.ts +1 -1
  254. package/dist/domain/system-components/generic-dimension.js +1 -1
  255. package/dist/domain/system-components/hidden-header.d.ts +1 -1
  256. package/dist/domain/system-components/hidden-header.js +1 -1
  257. package/dist/domain/system-components/hidden-sidebar-footer.d.ts +1 -1
  258. package/dist/domain/system-components/hidden-sidebar-footer.js +1 -1
  259. package/dist/domain/system-components/horizontal-tabs.d.ts +1 -1
  260. package/dist/domain/system-components/horizontal-tabs.js +1 -1
  261. package/dist/domain/system-components/hotspot-drag-handle.d.ts +1 -1
  262. package/dist/domain/system-components/hotspot-drag-handle.js +1 -1
  263. package/dist/domain/system-components/list-selector-dimension-indicator.d.ts +1 -1
  264. package/dist/domain/system-components/list-selector-dimension-indicator.js +1 -1
  265. package/dist/domain/system-components/material-swatch.js +1 -1
  266. package/dist/domain/system-components/offset-anchors.d.ts +1 -1
  267. package/dist/domain/system-components/offset-anchors.js +1 -1
  268. package/dist/domain/system-components/offset-indicator.d.ts +1 -2
  269. package/dist/domain/system-components/offset-indicator.js +1 -1
  270. package/dist/domain/system-components/offset.d.ts +1 -1
  271. package/dist/domain/system-components/offset.js +1 -1
  272. package/dist/domain/system-components/other-action.d.ts +1 -1
  273. package/dist/domain/system-components/other-action.js +1 -1
  274. package/dist/domain/system-components/pivot-point.d.ts +1 -1
  275. package/dist/domain/system-components/pivot-point.js +1 -1
  276. package/dist/domain/system-components/price.js +1 -1
  277. package/dist/domain/system-components/projected-entities.d.ts +1 -1
  278. package/dist/domain/system-components/projected-entities.js +1 -1
  279. package/dist/domain/system-components/property-page.d.ts +1 -1
  280. package/dist/domain/system-components/property-page.js +1 -1
  281. package/dist/domain/system-components/read-sidebar-footer.d.ts +1 -1
  282. package/dist/domain/system-components/read-sidebar-footer.js +1 -1
  283. package/dist/domain/system-components/save-template-thumbnail.js +1 -1
  284. package/dist/domain/system-components/scene-entity-add-fab.js +1 -1
  285. package/dist/domain/system-components/scene-entity-delete-fab.js +1 -1
  286. package/dist/domain/system-components/scene-entity-local-material-override.js +1 -1
  287. package/dist/domain/system-components/scene-entity-material-override.js +1 -1
  288. package/dist/domain/system-components/scene-entity-navigation-hotspot.js +1 -1
  289. package/dist/domain/system-components/scene-entity-object-local-material-override.js +1 -1
  290. package/dist/domain/system-components/scene-entity-object-material-override.js +1 -1
  291. package/dist/domain/system-components/scene-entity-object-remote-material-override.js +1 -1
  292. package/dist/domain/system-components/scene-entity-object-transimissive-material-override.js +1 -1
  293. package/dist/domain/system-components/scene-entity-remote-material-override.js +1 -1
  294. package/dist/domain/system-components/scene-entity-select-hotspot.js +1 -1
  295. package/dist/domain/system-components/scene-entity-transimissive-material-override.js +1 -1
  296. package/dist/domain/system-components/sidebar-tabs.d.ts +1 -1
  297. package/dist/domain/system-components/sidebar-tabs.js +1 -1
  298. package/dist/domain/system-components/simple-summary.js +1 -1
  299. package/dist/domain/system-components/size.d.ts +1 -1
  300. package/dist/domain/system-components/size.js +1 -1
  301. package/dist/domain/system-components/sketching-draw.d.ts +1 -1
  302. package/dist/domain/system-components/sketching-draw.js +1 -1
  303. package/dist/domain/system-components/sketching-edit.d.ts +1 -1
  304. package/dist/domain/system-components/sketching-edit.js +1 -1
  305. package/dist/domain/system-components/sketching-line.d.ts +1 -1
  306. package/dist/domain/system-components/sketching-line.js +1 -1
  307. package/dist/domain/system-components/sketching-rectangle.d.ts +1 -1
  308. package/dist/domain/system-components/sketching-rectangle.js +1 -1
  309. package/dist/domain/system-components/sketching.d.ts +1 -1
  310. package/dist/domain/system-components/sketching.js +1 -1
  311. package/dist/domain/system-components/snap-axis.d.ts +1 -1
  312. package/dist/domain/system-components/snap-axis.js +1 -1
  313. package/dist/domain/system-components/snap-edge.d.ts +1 -1
  314. package/dist/domain/system-components/snap-edge.js +1 -1
  315. package/dist/domain/system-components/snap-plane.d.ts +1 -1
  316. package/dist/domain/system-components/snap-plane.js +1 -1
  317. package/dist/domain/system-components/snap-point.d.ts +1 -1
  318. package/dist/domain/system-components/snap-point.js +1 -1
  319. package/dist/domain/system-components/summary-component.js +1 -1
  320. package/dist/domain/system-components/tool-menu-fab.d.ts +1 -1
  321. package/dist/domain/system-components/tool-menu-fab.js +1 -1
  322. package/dist/domain/system-components/toolbar.d.ts +1 -1
  323. package/dist/domain/system-components/toolbar.js +1 -1
  324. package/dist/domain/system-components/universal-sidebar-footer.d.ts +1 -1
  325. package/dist/domain/system-components/universal-sidebar-footer.js +1 -1
  326. package/dist/domain/utils/eval-cache.d.ts +1 -2
  327. package/dist/domain/utils/memo-eval.d.ts +1 -3
  328. package/dist/editor/domain-editors/use-implementation-files.d.ts +7 -6
  329. package/dist/editor/domain-editors/use-implementation-files.js +1 -1
  330. package/dist/legacy/domain-cli/gen/configurator-builder.js +21 -8
  331. package/dist/legacy/domain-cli/utils/cache.d.ts +1 -1
  332. package/dist/legacy/domain-cli/utils/cache.js +1 -1
  333. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/frontend-admin.js +18 -19
  334. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/frontend-configurator.js +15 -16
  335. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/frontend-embedded-admin.js +22 -23
  336. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/frontend-embedded-configurator.js +15 -16
  337. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/generator-shared.d.ts +7 -2
  338. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/generator-shared.js +8 -12
  339. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/index.d.ts +1 -1
  340. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/index.js +1 -1
  341. package/dist/legacy/phoenix-cli/project-gen/generators/file-templates/webhook-builders.js +7 -7
  342. package/dist/phoenix/scripts/build-admin.js +1 -1
  343. package/dist/react-sdk/application-runtime/hooks/use-domain-application-props.d.ts +5 -2
  344. package/dist/react-sdk/application-runtime/mocks/create-mock-application-runtime.d.ts +1 -1
  345. package/dist/react-sdk/application-runtime/mocks/create-mock-application-runtime.js +1 -1
  346. package/package.json +3 -3
  347. package/dist/domain/core/json-schema.js +0 -1
  348. package/dist/domain/core/reflection.js +0 -1
  349. /package/dist/domain/core/{enhanced-json-schema.js → decoder/decoder.js} +0 -0
  350. /package/dist/domain/core/{alias.d.ts → model/alias.d.ts} +0 -0
  351. /package/dist/domain/core/{alias.js → model/alias.js} +0 -0
  352. /package/dist/domain/core/{common-definitions.d.ts → model/common-definitions.d.ts} +0 -0
  353. /package/dist/domain/core/{common-definitions.js → model/common-definitions.js} +0 -0
  354. /package/dist/domain/core/{component.js → model/component.js} +0 -0
  355. /package/dist/domain/core/{model.d.ts → model/model.d.ts} +0 -0
  356. /package/dist/domain/core/{model.js → model/model.js} +0 -0
  357. /package/dist/domain/core/{preset.d.ts → model/preset.d.ts} +0 -0
  358. /package/dist/domain/core/{preset.js → model/preset.js} +0 -0
  359. /package/dist/domain/core/{schema-validator-ajv.d.ts → schema/create-ajv-schema-validator.d.ts} +0 -0
  360. /package/dist/domain/core/{schema-validator-ajv.js → schema/create-ajv-schema-validator.js} +0 -0
  361. /package/dist/domain/core/{schema-validator-csp.d.ts → schema/create-csp-schema-validator.d.ts} +0 -0
  362. /package/dist/domain/core/{schema-validator-csp.js → schema/create-csp-schema-validator.js} +0 -0
  363. /package/dist/domain/core/{enhanced-json-schema.d.ts → schema/enhanced-json-schema.d.ts} +0 -0
  364. /package/dist/domain/core/{schema-validator.js → schema/enhanced-json-schema.js} +0 -0
  365. /package/dist/domain/core/{json-schema.d.ts → schema/extended-schema-validator.d.ts} +0 -0
  366. /package/dist/domain/core/{schema-validator.d.ts → schema/schema-validator.d.ts} +0 -0
@@ -3,3 +3,4 @@ export * from './code-imports.js';
3
3
  export * from './exported-type-declarations.js';
4
4
  export * from './env-reader.js';
5
5
  export * from './file-headers.js';
6
+ export * from './project-module-list.js';
@@ -1 +1 @@
1
- export*from"./application-type-imports.js";export*from"./code-imports.js";export*from"./exported-type-declarations.js";export*from"./env-reader.js";export*from"./file-headers.js";
1
+ export*from"./application-type-imports.js";export*from"./code-imports.js";export*from"./exported-type-declarations.js";export*from"./env-reader.js";export*from"./file-headers.js";export*from"./project-module-list.js";
@@ -0,0 +1,8 @@
1
+ /** The default imports of one convention folder's files, as a generated barrel lists them. */
2
+ export declare const generateProjectModuleImports: (files: readonly string[], prefix: string) => readonly string[];
3
+ /**
4
+ * The origin-tagged module list a generated barrel exports for one convention folder. The barrel only
5
+ * pairs each default export with its project path; the SDK validates and merges the exports, so that an
6
+ * invalid file is reported by name and the built app and the editor's hot reload share one implementation.
7
+ */
8
+ export declare const generateProjectModuleList: (files: readonly string[], prefix: string) => string;
@@ -0,0 +1,3 @@
1
+ export const generateProjectModuleImports=(e,t)=>e.map((e,r)=>`import ${t}${r} from '../${e.replace(/\.tsx?$/,".js")}'`);export const generateProjectModuleList=(e,t)=>{if(0===e.length)return"[]";let r=e.map((e,r)=>` { origin: '${e}', exports: ${t}${r} },`);return`[
2
+ ${r.join("\n")}
3
+ ]`};
@@ -1 +1 @@
1
- import{GeneratedApplicationFile as n}from"../../core/index.js";import{createApplicationTypeImportRegistrar as e}from"./common/index.js";import{generateAdminGlobalBindingBlock as i,generateApplicationSpecAdminCode as o,generateApplicationSpecAdminFrontendCode as t,generateApplicationSpecAdminGlobals as a,generateApplicationSpecConfiguratorCode as r,generateApplicationSpecConfiguratorConfig as s,generateApplicationSpecConfiguratorFrontendCode as d,generateApplicationSpecConfiguratorGlobals as c,generateApplicationSpecDomainFile as g,generateApplicationSpecDomainSpecFile as m,generateApplicationSpecGlobals as p,generateApplicationSpecTypesModule as l,generateConfiguratorGlobalBindingBlock as f,generateImportedStateConstants as B,generatePhxExportsBlock as u,generatePhxGlobalsBlock as x,generateStateConstants as h}from"./templates/index.js";import{splitWebhookMembership as k}from"./webhook-safe-files.js";let y=()=>"";export const globalPhxBindingStrategy={generateApplicationTypesFile:(e,i)=>n("globals.d.ts",p(e,i)),generateDomainBindingBlock:x,generateStateConstants:h,generateConfiguratorBindingBlock:f,configuratorBindingDescription:"Creates the configurator interface and sets phx.frontend — must run before any user code imports.",generateAdminBindingBlock:i,adminBindingDescription:"Creates the admin interface and sets phx.frontend.admin — must run before admin user code imports."};export const modulePhxBindingStrategy={applicationTypeImportSource:"./application-types.js",generateApplicationTypesFile:(e,i)=>n("application-types.ts",l(e,i)),generateDomainBindingBlock:u,generateStateConstants:B,generateConfiguratorBindingBlock:y,configuratorBindingDescription:"Creates and exports the configurator interface for a module-scoped phx binding.",generateAdminBindingBlock:y,adminBindingDescription:"Creates and exports the admin interface for a module-scoped phx binding."};let C=n=>n.map(n=>n.file.name);export const generateDomainRuntimeFiles=(i,p)=>{let{applicationSpec:l,categorizedFiles:f,phxDefinitions:B,includeDefaultEnvs:u}=i,x=e(p.applicationTypeImportSource),h=C(f.expressions),y=C(f.actions),b=C(f.handlers),D=C(f.elements),S=C(f.transformers),A=C(f.invariants),F=C(f.adminInvariants),j=C(f.adminExpressions),I=C(f.adminElements),T=k(f.components),w=C(T.webhookIncluded),v=C(T.frontendOnly),E=k(f.adminComponents),O=C(E.webhookIncluded),P=C(E.frontendOnly);return[n("domain-spec.ts",m(l,{generateBindingBlock:p.generateDomainBindingBlock,generateStateConstants:p.generateStateConstants,registerApplicationTypeImports:x})),n("configurator-globals.ts",c(p.generateConfiguratorBindingBlock,p.configuratorBindingDescription)),n("configurator-domain-code.ts",r({expressionFiles:h,actionFiles:y,invariantFiles:A,componentFiles:w},x)),n("configurator-frontend-code.ts",d({transformerFiles:S,handlerFiles:b,elementFiles:D,componentFiles:v},x)),n("admin-domain-code.ts",o({adminExpressionFiles:j,adminInvariantFiles:F,adminComponentFiles:O},x)),n("admin-frontend-code.ts",t({adminElementFiles:I,adminComponentFiles:P},x)),n("domain.ts",g(l)),n("configurator-config.ts",s(l,{includeDefaultEnvs:u})),p.generateApplicationTypesFile(l,B),n("admin-globals.ts",a(p.generateAdminBindingBlock,p.adminBindingDescription))]};
1
+ import{GeneratedApplicationFile as n}from"../../core/index.js";import{createApplicationTypeImportRegistrar as e}from"./common/index.js";import{generateAdminGlobalBindingBlock as i,generateApplicationSpecAdminCode as o,generateApplicationSpecAdminFrontendCode as t,generateApplicationSpecAdminGlobals as a,generateApplicationSpecConfiguratorCode as r,generateApplicationSpecConfiguratorConfig as s,generateApplicationSpecConfiguratorFrontendCode as d,generateApplicationSpecConfiguratorGlobals as c,generateApplicationSpecDomainFile as g,generateApplicationSpecDomainSpecFile as m,generateApplicationSpecGlobals as p,generateApplicationSpecTypesModule as l,generateConfiguratorGlobalBindingBlock as f,generateImportedStateConstants as B,generatePhxExportsBlock as u,generatePhxGlobalsBlock as x,generateStateConstants as h}from"./templates/index.js";import{splitWebhookMembership as k}from"./webhook-safe-files.js";let y=()=>"";export const globalPhxBindingStrategy={generateApplicationTypesFile:(e,i)=>n("globals.d.ts",p(e,i)),generateDomainBindingBlock:x,generateStateConstants:h,generateConfiguratorBindingBlock:f,configuratorBindingDescription:"Creates the configurator interface and sets phx.frontend — must run before any user code imports.",generateAdminBindingBlock:i,adminBindingDescription:"Creates the admin interface and sets phx.frontend.admin — must run before admin user code imports."};export const modulePhxBindingStrategy={applicationTypeImportSource:"./application-types.js",generateApplicationTypesFile:(e,i)=>n("application-types.ts",l(e,i)),generateDomainBindingBlock:u,generateStateConstants:B,generateConfiguratorBindingBlock:y,configuratorBindingDescription:"Creates and exports the configurator interface for a module-scoped phx binding.",generateAdminBindingBlock:y,adminBindingDescription:"Creates and exports the admin interface for a module-scoped phx binding."};let C=n=>n.map(n=>n.file.name);export const generateDomainRuntimeFiles=(i,p)=>{let{applicationSpec:l,categorizedFiles:f,phxDefinitions:B,includeDefaultEnvs:u}=i,x=e(p.applicationTypeImportSource),h=C(f.expressions),y=C(f.actions),b=C(f.handlers),D=C(f.elements),S=C(f.transformers),A=C(f.invariants),F=C(f.adminInvariants),j=C(f.adminExpressions),I=C(f.adminElements),T=k(f.components),w=C(T.webhookIncluded),v=C(T.frontendOnly),E=k(f.adminComponents),O=C(E.webhookIncluded),P=C(E.frontendOnly);return[n("domain-spec.ts",m(l,{generateBindingBlock:p.generateDomainBindingBlock,generateStateConstants:p.generateStateConstants,registerApplicationTypeImports:x})),n("configurator-globals.ts",c(p.generateConfiguratorBindingBlock,p.configuratorBindingDescription)),n("configurator-domain-code.ts",r({expressionFiles:h,actionFiles:y,invariantFiles:A,componentFiles:w})),n("configurator-frontend-code.ts",d({transformerFiles:S,handlerFiles:b,elementFiles:D,componentFiles:v})),n("admin-domain-code.ts",o({adminExpressionFiles:j,adminInvariantFiles:F,adminComponentFiles:O})),n("admin-frontend-code.ts",t({adminElementFiles:I,adminComponentFiles:P})),n("domain.ts",g(l)),n("configurator-config.ts",s(l,{includeDefaultEnvs:u})),p.generateApplicationTypesFile(l,B),n("admin-globals.ts",a(p.generateAdminBindingBlock,p.adminBindingDescription))]};
@@ -1,8 +1,7 @@
1
- import { type ApplicationTypeImportRegistrar } from '../common/index.js';
2
1
  interface GenerateAdminCodeOptions {
3
2
  readonly adminExpressionFiles: readonly string[];
4
3
  readonly adminInvariantFiles: readonly string[];
5
4
  readonly adminComponentFiles: readonly string[];
6
5
  }
7
- export declare const generateApplicationSpecAdminCode: (options: GenerateAdminCodeOptions, registerApplicationTypeImports?: ApplicationTypeImportRegistrar) => string;
6
+ export declare const generateApplicationSpecAdminCode: (options: GenerateAdminCodeOptions) => string;
8
7
  export {};
@@ -1,17 +1,9 @@
1
- import{autoHeader as n}from"../common/file-headers.js";import{CodeImports as t,skipApplicationTypeImports as e}from"../common/index.js";let s=(n,t)=>n.map((n,e)=>{let s=`../${n.replace(/\.tsx?$/,".js")}`;return`import ${t}${e} from '${s}'`}),i=(n,t="\n")=>n.length>0?"\n"+n.join(t)+"\n":"";export const generateApplicationSpecAdminCode=(o,a=e)=>{let{adminExpressionFiles:r,adminInvariantFiles:m,adminComponentFiles:d}=o,p=new t;for(let n of["AliasedExpressions","AliasedInvariants","DomainComponentOptic","SystemComponentTypeConstraint"])p.addTypeImport("@salsita-ai/sdk/domain",n);a(p,["Admin","FrontendData","PublishedData","SessionData"]);let c=[...s(r,"adminExpressions"),...s(m,"adminInvariants"),...s(d,"adminComponents")],A=r.map((n,t)=>`for (const [type, exprs] of Object.entries(adminExpressions${t})) {
2
- mergedExpressions[type] = { ...mergedExpressions[type], ...exprs }
3
- }`),y=m.map((n,t)=>`for (const [type, invs] of Object.entries(adminInvariants${t})) {
4
- mergedInvariants[type] = [...(mergedInvariants[type] ?? []), ...invs]
5
- }`),l=d.map((n,t)=>`adminComponents${t}`);return`${n("admin-domain-code.ts","Barrel file for user-authored admin domain code — expressions, invariants and components.")}
6
- ${p.toString()}
7
- ${i(c)}
8
- const mergedExpressions: Record<string, Record<string, unknown>> = {}
9
- ${i(A,"\n\n")}
10
- export const customAdminExpressions = mergedExpressions as AliasedExpressions<Admin.AnyDomainEntity, Admin.RootEntity, PublishedData, SessionData, FrontendData, Admin.Aliases>
1
+ import{autoHeader as n}from"../common/file-headers.js";import{CodeImports as o,generateProjectModuleImports as e,generateProjectModuleList as t}from"../common/index.js";export const generateApplicationSpecAdminCode=i=>{let{adminExpressionFiles:s,adminInvariantFiles:r,adminComponentFiles:a}=i,d=new o;d.addTypeImport("@salsita-ai/sdk/domain","ProjectModule");let m=[...e(s,"adminExpressions"),...e(r,"adminInvariants"),...e(a,"adminComponents")];return`${n("admin-domain-code.ts","Barrel file for user-authored admin domain code — expressions, invariants and components.")}
2
+ ${d.toString()}
3
+ ${m.length>0?"\n"+m.join("\n")+"\n":""}
4
+ export const customAdminExpressions: readonly ProjectModule[] = ${t(s,"adminExpressions")}
11
5
 
12
- const mergedInvariants: Record<string, ReadonlyArray<unknown>> = {}
13
- ${i(y,"\n\n")}
14
- export const customAdminInvariants = mergedInvariants as AliasedInvariants<Admin.AnyDomainEntity, Admin.RootEntity, PublishedData, SessionData, FrontendData, Admin.Aliases, string>
6
+ export const customAdminInvariants: readonly ProjectModule[] = ${t(r,"adminInvariants")}
15
7
 
16
- export const customAdminComponentOptics: ReadonlyArray<DomainComponentOptic<Admin.AnyDomainEntity, Admin.RootEntity, PublishedData, SessionData, FrontendData, Admin.AnyDomainEntity, SystemComponentTypeConstraint>> = [${l.join(", ")}].flat()
8
+ export const customAdminComponentOptics: readonly ProjectModule[] = ${t(a,"adminComponents")}
17
9
  `};
@@ -1,7 +1,6 @@
1
- import { type ApplicationTypeImportRegistrar } from '../common/index.js';
2
1
  interface GenerateAdminFrontendCodeOptions {
3
2
  readonly adminElementFiles: readonly string[];
4
3
  readonly adminComponentFiles: readonly string[];
5
4
  }
6
- export declare const generateApplicationSpecAdminFrontendCode: (options: GenerateAdminFrontendCodeOptions, registerApplicationTypeImports?: ApplicationTypeImportRegistrar) => string;
5
+ export declare const generateApplicationSpecAdminFrontendCode: (options: GenerateAdminFrontendCodeOptions) => string;
7
6
  export {};
@@ -1,9 +1,9 @@
1
- import{autoHeader as n}from"../common/file-headers.js";import{CodeImports as t,skipApplicationTypeImports as e}from"../common/index.js";let o=(n,t)=>n.map((n,e)=>{let o=`../${n.replace(/\.tsx?$/,".js")}`;return`import ${t}${e} from '${o}'`});export const generateApplicationSpecAdminFrontendCode=(m,i=e)=>{let{adminElementFiles:a,adminComponentFiles:r}=m,d=new t;for(let n of["DomainComponentOptic","ElementRegistration","SystemComponentTypeConstraint"])d.addTypeImport("@salsita-ai/sdk/domain",n);i(d,["Admin","FrontendData","PublishedData","SessionData"]);let s=[...o(a,"adminElements"),...o(r,"frontendAdminComponents")],p=a.map((n,t)=>`adminElements${t}`),l=r.map((n,t)=>`frontendAdminComponents${t}`);return`${n("admin-frontend-code.ts","Barrel file for user-authored admin frontend code — elements and frontend-only components. Needs phx.frontend.admin.")}
2
- ${d.toString()}
1
+ import{autoHeader as n}from"../common/file-headers.js";import{CodeImports as e,generateProjectModuleImports as o,generateProjectModuleList as t}from"../common/index.js";export const generateApplicationSpecAdminFrontendCode=d=>{let{adminElementFiles:m,adminComponentFiles:r}=d,i=new e;i.addTypeImport("@salsita-ai/sdk/domain","ProjectModule");let s=[...o(m,"adminElements"),...o(r,"frontendAdminComponents")];return`${n("admin-frontend-code.ts","Barrel file for user-authored admin frontend code — elements and frontend-only components. Needs phx.frontend.admin.")}
2
+ ${i.toString()}
3
3
 
4
4
  import './admin-globals.js'
5
5
  ${s.length>0?"\n"+s.join("\n")+"\n":""}
6
- export const customAdminElements: readonly ElementRegistration[] = [${p.join(", ")}].flat()
6
+ export const customAdminElements: readonly ProjectModule[] = ${t(m,"adminElements")}
7
7
 
8
- export const customFrontendAdminComponentOptics: ReadonlyArray<DomainComponentOptic<Admin.AnyDomainEntity, Admin.RootEntity, PublishedData, SessionData, FrontendData, Admin.AnyDomainEntity, SystemComponentTypeConstraint>> = [${l.join(", ")}].flat()
8
+ export const customFrontendAdminComponentOptics: readonly ProjectModule[] = ${t(r,"frontendAdminComponents")}
9
9
  `};
@@ -1,9 +1,8 @@
1
- import { type ApplicationTypeImportRegistrar } from '../common/index.js';
2
1
  interface GenerateConfiguratorCodeOptions {
3
2
  readonly expressionFiles: readonly string[];
4
3
  readonly actionFiles: readonly string[];
5
4
  readonly invariantFiles: readonly string[];
6
5
  readonly componentFiles: readonly string[];
7
6
  }
8
- export declare const generateApplicationSpecConfiguratorCode: (options: GenerateConfiguratorCodeOptions, registerApplicationTypeImports?: ApplicationTypeImportRegistrar) => string;
7
+ export declare const generateApplicationSpecConfiguratorCode: (options: GenerateConfiguratorCodeOptions) => string;
9
8
  export {};
@@ -1,20 +1,11 @@
1
- import{autoHeader as t}from"../common/file-headers.js";import{CodeImports as n,skipApplicationTypeImports as e}from"../common/index.js";let o=(t,n)=>t.map((t,e)=>{let o=`../${t.replace(/\.tsx?$/,".js")}`;return`import ${n}${e} from '${o}'`}),a=(t,n="\n")=>t.length>0?"\n"+t.join(n)+"\n":"";export const generateApplicationSpecConfiguratorCode=(i,s=e)=>{let{expressionFiles:r,actionFiles:p,invariantFiles:m,componentFiles:d}=i,c=new n;for(let t of["ActionImplementations","AliasedExpressions","AliasedInvariants","DomainComponentOptic","SystemComponentTypeConstraint"])c.addTypeImport("@salsita-ai/sdk/domain",t);s(c,["$Map","ActionTypes","Aliases","AnyDomainEntity","ExportState","FrontendData","NavigationState","PublishedData","RootEntity","SessionData","ToolState","ViewState"]);let l=[...o(r,"expressions"),...o(p,"actions"),...o(m,"invariants"),...o(d,"components")],y=p.map((t,n)=>`...actions${n}`),D=r.map((t,n)=>`for (const [type, exprs] of Object.entries(expressions${n})) {
2
- mergedExpressions[type] = { ...mergedExpressions[type], ...exprs }
3
- }`),x=m.map((t,n)=>`for (const [type, invs] of Object.entries(invariants${n})) {
4
- mergedInvariants[type] = [...(mergedInvariants[type] ?? []), ...invs]
5
- }`),A=d.map((t,n)=>`components${n}`);return`${t("configurator-domain-code.ts","Barrel file for user-authored domain code — expressions, actions, invariants and components. Needs only phx.domain.")}
6
- ${c.toString()}
7
- ${a(l)}
8
- const mergedExpressions: Record<string, Record<string, unknown>> = {}
9
- ${a(D,"\n\n")}
10
- export const customExpressions = mergedExpressions as AliasedExpressions<AnyDomainEntity, RootEntity, PublishedData, SessionData, FrontendData, Aliases>
1
+ import{autoHeader as o}from"../common/file-headers.js";import{CodeImports as n,generateProjectModuleImports as e,generateProjectModuleList as t}from"../common/index.js";export const generateApplicationSpecConfiguratorCode=s=>{let{expressionFiles:r,actionFiles:i,invariantFiles:a,componentFiles:c}=s,d=new n;d.addTypeImport("@salsita-ai/sdk/domain","ProjectModule");let p=[...e(r,"expressions"),...e(i,"actions"),...e(a,"invariants"),...e(c,"components")];return`${o("configurator-domain-code.ts","Barrel file for user-authored domain code — expressions, actions, invariants and components. Needs only phx.domain.")}
2
+ ${d.toString()}
3
+ ${p.length>0?"\n"+p.join("\n")+"\n":""}
4
+ export const customExpressions: readonly ProjectModule[] = ${t(r,"expressions")}
11
5
 
12
- // A declared action without an implementation fails here; an implementation of an undeclared action fails in its own file.
13
- export const customActions: ActionImplementations<AnyDomainEntity, RootEntity, $Map, PublishedData, SessionData, FrontendData, NavigationState, ViewState, ToolState, ExportState, ActionTypes> = { ${y.join(", ")} }
6
+ export const customActions: readonly ProjectModule[] = ${t(i,"actions")}
14
7
 
15
- const mergedInvariants: Record<string, ReadonlyArray<unknown>> = {}
16
- ${a(x,"\n\n")}
17
- export const customInvariants = mergedInvariants as AliasedInvariants<AnyDomainEntity, RootEntity, PublishedData, SessionData, FrontendData, Aliases, string>
8
+ export const customInvariants: readonly ProjectModule[] = ${t(a,"invariants")}
18
9
 
19
- export const customComponentOptics: ReadonlyArray<DomainComponentOptic<AnyDomainEntity, RootEntity, PublishedData, SessionData, FrontendData, AnyDomainEntity, SystemComponentTypeConstraint>> = [${A.join(", ")}].flat()
10
+ export const customComponentOptics: readonly ProjectModule[] = ${t(c,"components")}
20
11
  `};
@@ -1,9 +1,8 @@
1
- import { type ApplicationTypeImportRegistrar } from '../common/index.js';
2
1
  interface GenerateConfiguratorFrontendCodeOptions {
3
2
  readonly transformerFiles: readonly string[];
4
3
  readonly handlerFiles: readonly string[];
5
4
  readonly elementFiles: readonly string[];
6
5
  readonly componentFiles: readonly string[];
7
6
  }
8
- export declare const generateApplicationSpecConfiguratorFrontendCode: (options: GenerateConfiguratorFrontendCodeOptions, registerApplicationTypeImports?: ApplicationTypeImportRegistrar) => string;
7
+ export declare const generateApplicationSpecConfiguratorFrontendCode: (options: GenerateConfiguratorFrontendCodeOptions) => string;
9
8
  export {};
@@ -1,15 +1,13 @@
1
- import{autoHeader as t}from"../common/file-headers.js";import{CodeImports as n,skipApplicationTypeImports as o}from"../common/index.js";let e=(t,n)=>t.map((t,o)=>{let e=`../${t.replace(/\.tsx?$/,".js")}`;return`import ${n}${o} from '${e}'`});export const generateApplicationSpecConfiguratorFrontendCode=(r,a=o)=>{let{transformerFiles:s,handlerFiles:i,elementFiles:m,componentFiles:p}=r,l=new n;for(let t of["DomainComponentOptic","ElementRegistration","HandlerRegistration","ImportedTransformer","SystemComponentTypeConstraint"])l.addTypeImport("@salsita-ai/sdk/domain",t);a(l,["$Map","AnyDomainEntity","ExportState","FrontendData","NavigationState","PublishedData","RootEntity","SessionData","ToolState","ViewState"]);let d=[...e(s,"transformers"),...e(i,"handlers"),...e(m,"elements"),...e(p,"frontendComponents")],f=s.map((t,n)=>{let o=t.replace(/^.*\//,"").replace(/\.tsx?$/,"");return` { name: '${o}', transformer: transformers${n} }`}),y=i.map((t,n)=>`handlers${n}`),c=m.map((t,n)=>`elements${n}`),$=p.map((t,n)=>`frontendComponents${n}`);return`${t("configurator-frontend-code.ts","Barrel file for user-authored frontend code — transformers, handlers, elements and frontend-only components. Needs phx.frontend.")}
2
- ${l.toString()}
1
+ import{autoHeader as o}from"../common/file-headers.js";import{CodeImports as e,generateProjectModuleImports as n,generateProjectModuleList as r}from"../common/index.js";export const generateApplicationSpecConfiguratorFrontendCode=t=>{let{transformerFiles:s,handlerFiles:d,elementFiles:l,componentFiles:a}=t,m=new e;m.addTypeImport("@salsita-ai/sdk/domain","ProjectModule");let c=[...n(s,"transformers"),...n(d,"handlers"),...n(l,"elements"),...n(a,"frontendComponents")];return`${o("configurator-frontend-code.ts","Barrel file for user-authored frontend code — transformers, handlers, elements and frontend-only components. Needs phx.frontend.")}
2
+ ${m.toString()}
3
3
 
4
4
  import './configurator-globals.js'
5
- ${d.length>0?"\n"+d.join("\n")+"\n":""}
6
- export const customTransformers: ReadonlyArray<ImportedTransformer<AnyDomainEntity, RootEntity, $Map, NavigationState, ViewState, ToolState, ExportState>> = [
7
- ${f.join(",\n")}
8
- ]
5
+ ${c.length>0?"\n"+c.join("\n")+"\n":""}
6
+ export const customTransformers: readonly ProjectModule[] = ${r(s,"transformers")}
9
7
 
10
- export const customHandlers: ReadonlyArray<HandlerRegistration<any, any>> = [${y.join(", ")}].flat()
8
+ export const customHandlers: readonly ProjectModule[] = ${r(d,"handlers")}
11
9
 
12
- export const customElements: readonly ElementRegistration[] = [${c.join(", ")}].flat()
10
+ export const customElements: readonly ProjectModule[] = ${r(l,"elements")}
13
11
 
14
- export const customFrontendComponentOptics: ReadonlyArray<DomainComponentOptic<AnyDomainEntity, RootEntity, PublishedData, SessionData, FrontendData, AnyDomainEntity, SystemComponentTypeConstraint>> = [${$.join(", ")}].flat()
12
+ export const customFrontendComponentOptics: readonly ProjectModule[] = ${r(a,"frontendComponents")}
15
13
  `};
@@ -1,4 +1,4 @@
1
- import{CodeImports as i}from"../common/code-imports.js";import{autoHeader as n}from"../common/file-headers.js";let o=/v(\d+)\.ts$/,t=(i,n)=>i.versionedModels.filter(i=>void 0!==i.migrationFile).map(i=>({version:i.version,file:i.migrationFile,importName:n?`${n}MigrateToV${i.version}`:`migrateToV${i.version}`})),s=i=>i.map(i=>{let n=i.file.replace(o,`v${i.version}.js`),t=`migrateToV${i.version}`,s=i.importName!==t?` as ${i.importName}`:"";return`import { ${t}${s} } from '../${n}'`}).join("\n"),e=(i,n,o,t)=>[`const ${t}Migrations = {`,...i.map(i=>` ${i.version}: ${i.importName},`),"}","",`const ${t} = MigrateFunctionBuilder`,` .fromVersions(${n})`,` .to(${o})`,` .using(${t}Migrations)`," .build()"].join("\n");export const generateApplicationSpecDomainFile=o=>{let r=new i,a="./domain-spec.js",m="./configurator-domain-code.js",d="./admin-domain-code.js",p=i=>[...i.expressions.values()].some(i=>[...i.values()].some(i=>"relation"===i.implementation.kind)),l=p(o.configurator.expressions),c=p(o.admin.expressions),u=t(o.configurator.resolvedVersions,""),I=t(o.admin.resolvedVersions,"admin"),g=u.length>0,h=I.length>0;r.addImport(a,"baseConfiguratorBuilder"),r.addImport(a,"domainBuilder"),r.addImport(a,"adminDomainBuilder"),r.addImport(a,"attachComponent"),r.addImport(a,"attachAdminComponent"),r.addImport(a,"implementCustomExpressions"),r.addImport(a,"implementAdminCustomExpressions"),r.addImport(a,"createI18n"),r.addImport(a,"componentOptics"),r.addImport(a,"adminComponentOptics"),r.addImport(a,"invariantBuilder"),r.addImport(a,"adminInvariantBuilder"),r.addImport(m,"customExpressions"),r.addImport(m,"customInvariants"),r.addImport(m,"customActions"),r.addImport(d,"customAdminExpressions"),r.addImport(d,"customAdminInvariants"),l&&r.addImport(a,"relationExpressions"),c&&r.addImport(a,"adminRelationExpressions"),(g||h)&&r.addImport("@salsita-ai/sdk/domain","MigrateFunctionBuilder"),g&&r.addImport(a,"modelVersions"),h&&r.addImport(a,"adminModelVersions");let x=[];g&&x.push(s(u)),h&&x.push(s(I));let v=x.length>0?"\n"+x.join("\n")+"\n":"",$=[];g&&$.push(e(u,"modelVersions",o.configurator.schemaVersion,"migrate")),h&&$.push(e(I,"adminModelVersions",o.admin.schemaVersion,"migrateAdmin"));let E=$.length>0?"\n"+$.join("\n\n")+"\n":"",f=["const domainFactory = domainBuilder",l?" .withExpressions(relationExpressions)":null," .withExpressions(invariantBuilder.withInvariants(customInvariants).buildViolationExpressions())"," .withExpressions(customExpressions)"," .withActionImplementations(customActions)",g?" .withMigrate(migrate)":null," .build()"].filter(Boolean).join("\n"),A=["const adminDomainFactory = adminDomainBuilder",c?" .withExpressions(adminRelationExpressions)":null," .withExpressions(adminInvariantBuilder.withInvariants(customAdminInvariants).buildViolationExpressions())"," .withExpressions(customAdminExpressions)",h?" .withMigrate(migrateAdmin)":null," .build()"].filter(Boolean).join("\n");return`${n("domain.ts","Assembles domain and admin domain factories from builders, migrations, expressions and invariants.")}
1
+ import{CodeImports as i}from"../common/code-imports.js";import{autoHeader as o}from"../common/file-headers.js";let n=/v(\d+)\.ts$/,t=(i,o)=>i.versionedModels.filter(i=>void 0!==i.migrationFile).map(i=>({version:i.version,file:i.migrationFile,importName:o?`${o}MigrateToV${i.version}`:`migrateToV${i.version}`})),s=i=>i.map(i=>{let o=i.file.replace(n,`v${i.version}.js`),t=`migrateToV${i.version}`,s=i.importName!==t?` as ${i.importName}`:"";return`import { ${t}${s} } from '../${o}'`}).join("\n"),e=(i,o,n,t)=>[`const ${t}Migrations = {`,...i.map(i=>` ${i.version}: ${i.importName},`),"}","",`const ${t} = MigrateFunctionBuilder`,` .fromVersions(${o})`,` .to(${n})`,` .using(${t}Migrations)`," .build()"].join("\n");export const generateApplicationSpecDomainFile=n=>{let r=new i,a="./domain-spec.js",m="./configurator-domain-code.js",d="./admin-domain-code.js",p=i=>[...i.expressions.values()].some(i=>[...i.values()].some(i=>"relation"===i.implementation.kind)),l=p(n.configurator.expressions),c=p(n.admin.expressions),u=t(n.configurator.resolvedVersions,""),g=t(n.admin.resolvedVersions,"admin"),h=u.length>0,I=g.length>0;r.addImport(a,"baseConfiguratorBuilder"),r.addImport(a,"domainBuilder"),r.addImport(a,"adminDomainBuilder"),r.addImport(a,"attachComponent"),r.addImport(a,"attachAdminComponent"),r.addImport(a,"implementCustomExpressions"),r.addImport(a,"implementAdminCustomExpressions"),r.addImport(a,"createI18n"),r.addImport(a,"componentOptics"),r.addImport(a,"adminComponentOptics"),r.addImport(a,"invariantBuilder"),r.addImport(a,"adminInvariantBuilder"),r.addImport(m,"customExpressions"),r.addImport(m,"customInvariants"),r.addImport(m,"customActions"),r.addImport(d,"customAdminExpressions"),r.addImport(d,"customAdminInvariants"),l&&r.addImport(a,"relationExpressions"),c&&r.addImport(a,"adminRelationExpressions"),(h||I)&&r.addImport("@salsita-ai/sdk/domain","MigrateFunctionBuilder"),h&&r.addImport(a,"modelVersions"),I&&r.addImport(a,"adminModelVersions");let x=[];h&&x.push(s(u)),I&&x.push(s(g));let v=x.length>0?"\n"+x.join("\n")+"\n":"",$=[];h&&$.push(e(u,"modelVersions",n.configurator.schemaVersion,"migrate")),I&&$.push(e(g,"adminModelVersions",n.admin.schemaVersion,"migrateAdmin"));let E=$.length>0?"\n"+$.join("\n\n")+"\n":"",f=["const domainFactory = domainBuilder",l?" .withExpressions(relationExpressions)":null," .withExpressions(invariantBuilder.withInvariantModules(customInvariants).buildViolationExpressions())"," .withExpressionModules(customExpressions)"," .withActionModules(customActions)",h?" .withMigrate(migrate)":null," .build()"].filter(Boolean).join("\n"),A=["const adminDomainFactory = adminDomainBuilder",c?" .withExpressions(adminRelationExpressions)":null," .withExpressions(adminInvariantBuilder.withInvariantModules(customAdminInvariants).buildViolationExpressions())"," .withExpressionModules(customAdminExpressions)",I?" .withMigrate(migrateAdmin)":null," .build()"].filter(Boolean).join("\n");return`${o("domain.ts","Assembles domain and admin domain factories from builders, migrations, expressions and invariants.")}
2
2
  ${r.toString()}
3
3
  ${v}export { attachComponent, attachAdminComponent, implementCustomExpressions, implementAdminCustomExpressions, createI18n }
4
4
  ${E}
@@ -8,6 +8,6 @@ ${A}
8
8
  export const configuratorBuilder = baseConfiguratorBuilder
9
9
  .withDomainFactory(domainFactory)
10
10
  .withAdminDomainFactory(adminDomainFactory)
11
- .withComponentOptics(componentOptics)
12
- .withAdminComponentOptics(adminComponentOptics)
11
+ .withComponentOptics([{ origin: '.phoenix/domain-spec.ts', exports: componentOptics }])
12
+ .withAdminComponentOptics([{ origin: '.phoenix/domain-spec.ts', exports: adminComponentOptics }])
13
13
  `};
@@ -7,7 +7,7 @@ import{renderAgentSkill as e}from"./agent-skill.js";let i=`Review all current gi
7
7
  - [ ] Relations properly define parent-child ownership (1-N, 0-1)
8
8
  - [ ] Expressions have matching implementations in src/expressions/
9
9
  - [ ] Invariants have matching implementations in src/invariants/
10
- - [ ] Actions declared under actions: have matching implementations in src/actions/ (a missing one fails the type check of the generated barrel)
10
+ - [ ] Actions declared under actions: have matching implementations in src/actions/ (a missing one stops the application at start; it is not a type error)
11
11
  - [ ] Component bindings use correct entity types or aliases
12
12
  - [ ] $read/$write/$bind reference valid properties or expressions
13
13
  - [ ] A model that has been deployed is unchanged under its version: the change is in \`model.latest\`, the deployed model is kept as \`model.v<N>\`, and \`src/migrations/v<N+1>.ts\` migrates saved configurations
@@ -65,7 +65,8 @@ Declarative 3D product configurator built with Phoenix SDK. Domain model defined
65
65
  - Underscore folders (_shared/, _utils/) are NOT auto-imported`;
66
66
  /** The default-export rule of the SDK auto-import system. */
67
67
  readonly exportRules: `## Export Rules
68
- All files in src/expressions/, src/actions/, src/invariants/, src/transformers/, src/components/, src/handlers/, src/webhooks/ MUST use default exports. Can be a single item or an array. Named exports are ignored by the SDK auto-import system.`;
68
+ All files in src/expressions/, src/actions/, src/invariants/, src/transformers/, src/components/, src/handlers/, src/elements/, src/webhooks/ MUST use default exports. Can be a single item or an array. Named exports are ignored by the SDK auto-import system.
69
+ The default export must be what the folder's phx factory returns (for example \`phx.frontend.createCustomPhoenixLayoutElement()\` in src/elements/). Any other value, such as a plain React component, stops the application at start with an "Invalid default export in <file>" error. Put plain components and helpers in an underscore folder.`;
69
70
  /** Which components and handlers are bundled into the webhook. */
70
71
  readonly webhookMembership: `## Webhook Membership
71
72
  - User-authored components, admin components, and handlers are frontend-only by default.
@@ -6,8 +6,7 @@ Declarative 3D product configurator built with Phoenix SDK. Domain model defined
6
6
  - Expressions: entity-name.ts
7
7
  - Migrations: v*.ts (sequential)
8
8
  - Specs: kebab-case.yaml
9
- - Underscore folders (_shared/, _utils/) are NOT auto-imported`,exportRules:`## Export Rules
10
- All files in src/expressions/, src/actions/, src/invariants/, src/transformers/, src/components/, src/handlers/, src/webhooks/ MUST use default exports. Can be a single item or an array. Named exports are ignored by the SDK auto-import system.`,webhookMembership:"## Webhook Membership\n- User-authored components, admin components, and handlers are frontend-only by default.\n- A handler that registers `createMapPublishedRevisionDataHandler`, `createMapPublishedChunkedDataHandler`, `createDataRowValidatorHandler`, or `createSheetValidatorHandler` is included in the webhook automatically.\n- To include another component or handler in the webhook, put `'use webhook'` as its first statement (leading comments are allowed).\n- A webhook-included file and its runtime local-import closure must not import browser SDK entrypoints (`application`, `admin`, `configurator`, `editor`, `react`, `ui`) or style/font/image assets. Spec parsing reports the unsafe import and inclusion reason as a diagnostic.\n- Keep browser rendering in an unpinned file. Move shared server-safe logic into a separate module when both frontend and webhook code need it.",doNotEdit:"## Do Not Edit\n- `.phoenix/` directory — completely regenerated on each build. The one exception is `.phoenix/variants/`, where the `phoenix-variants` skill has you write option files; a rebuild keeps it\n- `tsconfig.json`, `eslint.config.js`, `prettier.config.js`, `.prettierignore`, `.linguirc`, `.nvmrc`\n- `src/locales/` .ts files — compiled from .po files",modelVersioning:"## Version the Domain Model Once It Is Deployed\nA deployed model version cannot change, because saved configurations depend on it. `pnpm phoenix deploy` is refused, before anything is uploaded, when the model differs from the one already deployed under the same version. The version is not written anywhere: `model.latest` is always the highest numbered version plus one, so a spec with only `latest` is v1, and `applicationVersion` plays no part. `pnpm phoenix dev` accepts every model change, so a working preview does not show that the deploy will pass.\n\nTo change a model that has been deployed as v<N>:\n1. Keep the deployed model, unchanged, as `model.v<N>` in the spec. A file of its own, such as `spec/model-v<N>.yaml`, keeps `latest` readable.\n2. Make the change in `model.latest`, which is now v<N+1>.\n3. Add `src/migrations/v<N+1>.ts` exporting `migrateToV<N+1>`. It receives the saved entities of v<N> and returns entities that are valid in v<N+1>; `ModelV<N>` and `ModelV<N+1>` are generated global namespaces.\n\nThe admin model is versioned on its own, under `src/admin/migrations/`, with its types in `AdminV<N>`.\n\n**Replacing the starter.** When the first deployment of the workspace was the starter, its `Box` model is v1 in production. When the real model replaces it, keep the starter's model as `model.v1` and define the real model in `latest`. Configurations saved from the starter are not worth converting, so the migration returns the starting state of the new model, the `initialDomainEntities` of its preset, and drops the boxes:\n```typescript\n// src/migrations/v2.ts\nimport type { Migration } from '@salsita-ai/sdk/domain'\n\nexport const migrateToV2: Migration<ModelV1.AnyDomainEntity, ModelV2.AnyDomainEntity> = () => [\n // the entities of the new model's preset\n]\n```\nAn entity of a type the new version no longer has must not stay in the returned state. An entity id starts with its type (`Box-1`), so an entity that keeps its data under a new type name needs a new id and every relation pointing at it rewritten. Read `docs/phoenix/migrations.mdx` before writing any other migration.",sdkDocumentation:'## SDK Documentation\n\nAlways search SDK docs for relevant examples before implementing Phoenix features.\n\n### Commands\n- `pnpm phoenix docs` — Full documentation index with descriptions\n- `pnpm phoenix docs -s <term>` — Search all doc content and metadata (case-insensitive)\n- `pnpm phoenix docs --dir` — Print the absolute docs directory for grep or ripgrep\n- `pnpm phoenix docs -r <path>` — Read specific doc (raw text to stdout)\n- `pnpm phoenix docs -c <category>` — List docs in a category\n- `pnpm phoenix docs -l` — List all doc paths with titles\n\n### Key Docs\n- `docs/phoenix/getting-started.mdx` — Setup, prerequisites, first project\n- `docs/phoenix/quickstart.mdx` — End-to-end tutorial building a configurator\n- `docs/phoenix/domain-model.mdx` — Entities, attributes, relations, specs\n- `docs/phoenix/components.mdx` — ECS pattern, YAML components, custom components\n- `docs/phoenix/project-structure.mdx` — Files, folders, conventions\n- `docs/phoenix/best-practices.mdx` — YAML-first, code patterns, common pitfalls\n- `docs/phoenix/state-management.mdx` — Reactive state, RxJS pipelines, data flow\n- `docs/phoenix/expression-context.mdx` — Expression API, context object, helpers\n- `docs/phoenix/webhooks.mdx` — Server-side finalization workflows\n- `docs/phoenix/finalization.mdx` — Finalization system, PDF/email/CSV generation\n- `docs/phoenix/migrations.mdx` — Schema versioning, migration files\n\n### Agent Workflow\n1. Find relevant docs by content: `pnpm phoenix docs -s \'camera\'`\n2. Read matching doc: `pnpm phoenix docs -r docs/3d-scene/cameras/transitions.mdx`\n3. Search within a doc: `pnpm phoenix docs -r <path> | grep "example"`\n4. Search titles only as a fallback: `pnpm phoenix docs -l | grep "camera"`\n5. Search generated files directly when needed: `grep -rn "camera" "$(pnpm phoenix docs --dir)"`\n6. Browse a topic area: `pnpm phoenix docs -c "Layouts"`',assetInspection:"## 3D Asset Inspection\n\nRun `pnpm phoenix inspect:assets` to discover all glTF/GLB files in `public/` and get a summary table. Use `--file <path>` for detailed single-file inspection.\n\n**When to use:** before writing YAML/code that references objectName, materialsToOverride, morphTargetInfluences, or object positioning.\n\n**What it shows per node:**\n- Name, type (Mesh/Light/Camera/Empty), children\n- Transform: `pos=`, `rot=`, `scale=` (only non-default values shown)\n- Per-node morph targets: `morphs=Width,Height`\n- Bounding box: `bounds=WxHxD` (width x height x depth in meters)\n- Origin placement: `origin=center`, `bottom-center`, `top-center`, `bottom-corner`, etc. with numerical offset\n\n**Use cases:**\n- Find exact node names for `objectName` in scene entity components\n- Find material names for `materialsToOverride`\n- Find morph target names for `morphTargetInfluences`\n- Check model dimensions (bounds) for positioning, dimension indicators, or invariants\n- Check origin placement to understand how models anchor (center vs bottom-center)\n- Use `--json` for programmatic access to all data\n\n**Flags:** `--objects`, `--materials`, `--morphs`, `--animations`, `--json`",screenshotCli:"## Screenshot CLI\n\nCapture 3D canvas screenshots from a running dev server via `pnpm phoenix screenshot`.\n\n**Prerequisites:**\n1. `phoenix dev` must be running (starts the WebSocket server on port 3020)\n2. Configurator must be open in a browser (the browser does the actual rendering)\n\n**Options:**\n- `--output, -o` — Output file path (default: `./screenshot.png`)\n- `--width, -w` — Width in pixels (default: 1920)\n- `--height` — Height in pixels (default: 1080)\n- `--format, -f` — Image format: PNG or JPEG (default: PNG)\n- `--port` — WebSocket server port (default: 3020)\n\n**Example workflow:**\n1. Start dev server: `pnpm phoenix dev`\n2. Open configurator in browser (or via Playwright MCP)\n3. Take screenshot: `pnpm phoenix screenshot -o ./render.png -w 2560 --height 1440`\n\n**Use cases:** visual regression testing, generating product images, debugging 3D renders",inspectState:"## Inspect: State\n\nGet the current editor runtime state as JSON via `pnpm phoenix inspect:state`.\n\n**Prerequisites:** same as screenshot (dev server running + browser open)\n\n**Options:**\n- `--output, -o` — Output file path (prints to stdout if omitted)\n- `--sections, -s` — Comma-separated: entities, navigation, validation (default: all)\n- `--pretty` — Pretty-print JSON (default: true)\n- `--port` — WebSocket server port (default: 3020)\n\n**Example:** `pnpm phoenix inspect:state -o ./state.json -s entities,navigation`\n\n**Lifecycle status:** Always included in response. Shows which systems are ready:\n- `domainLoaded` — domain data loaded\n- `domainContextReady` — domain context initialized (entities available)\n- `configuratorReady` — 3D configurator initialized\n- `sessionAuthenticated` — session service active\n- `editorMode` — editor mode enabled\n\n**Tips:** Use `--sections` to limit payload size. Pipe through `head`/`tail` for partial output (e.g., `pnpm phoenix inspect:state | head -50`).\n\n**Use cases:** AI agent context, debugging entity state, inspecting navigation/validation",inspectData:`## Inspect: Data
9
+ - Underscore folders (_shared/, _utils/) are NOT auto-imported`,exportRules:'## Export Rules\nAll files in src/expressions/, src/actions/, src/invariants/, src/transformers/, src/components/, src/handlers/, src/elements/, src/webhooks/ MUST use default exports. Can be a single item or an array. Named exports are ignored by the SDK auto-import system.\nThe default export must be what the folder\'s phx factory returns (for example `phx.frontend.createCustomPhoenixLayoutElement()` in src/elements/). Any other value, such as a plain React component, stops the application at start with an "Invalid default export in <file>" error. Put plain components and helpers in an underscore folder.',webhookMembership:"## Webhook Membership\n- User-authored components, admin components, and handlers are frontend-only by default.\n- A handler that registers `createMapPublishedRevisionDataHandler`, `createMapPublishedChunkedDataHandler`, `createDataRowValidatorHandler`, or `createSheetValidatorHandler` is included in the webhook automatically.\n- To include another component or handler in the webhook, put `'use webhook'` as its first statement (leading comments are allowed).\n- A webhook-included file and its runtime local-import closure must not import browser SDK entrypoints (`application`, `admin`, `configurator`, `editor`, `react`, `ui`) or style/font/image assets. Spec parsing reports the unsafe import and inclusion reason as a diagnostic.\n- Keep browser rendering in an unpinned file. Move shared server-safe logic into a separate module when both frontend and webhook code need it.",doNotEdit:"## Do Not Edit\n- `.phoenix/` directory — completely regenerated on each build. The one exception is `.phoenix/variants/`, where the `phoenix-variants` skill has you write option files; a rebuild keeps it\n- `tsconfig.json`, `eslint.config.js`, `prettier.config.js`, `.prettierignore`, `.linguirc`, `.nvmrc`\n- `src/locales/` .ts files — compiled from .po files",modelVersioning:"## Version the Domain Model Once It Is Deployed\nA deployed model version cannot change, because saved configurations depend on it. `pnpm phoenix deploy` is refused, before anything is uploaded, when the model differs from the one already deployed under the same version. The version is not written anywhere: `model.latest` is always the highest numbered version plus one, so a spec with only `latest` is v1, and `applicationVersion` plays no part. `pnpm phoenix dev` accepts every model change, so a working preview does not show that the deploy will pass.\n\nTo change a model that has been deployed as v<N>:\n1. Keep the deployed model, unchanged, as `model.v<N>` in the spec. A file of its own, such as `spec/model-v<N>.yaml`, keeps `latest` readable.\n2. Make the change in `model.latest`, which is now v<N+1>.\n3. Add `src/migrations/v<N+1>.ts` exporting `migrateToV<N+1>`. It receives the saved entities of v<N> and returns entities that are valid in v<N+1>; `ModelV<N>` and `ModelV<N+1>` are generated global namespaces.\n\nThe admin model is versioned on its own, under `src/admin/migrations/`, with its types in `AdminV<N>`.\n\n**Replacing the starter.** When the first deployment of the workspace was the starter, its `Box` model is v1 in production. When the real model replaces it, keep the starter's model as `model.v1` and define the real model in `latest`. Configurations saved from the starter are not worth converting, so the migration returns the starting state of the new model, the `initialDomainEntities` of its preset, and drops the boxes:\n```typescript\n// src/migrations/v2.ts\nimport type { Migration } from '@salsita-ai/sdk/domain'\n\nexport const migrateToV2: Migration<ModelV1.AnyDomainEntity, ModelV2.AnyDomainEntity> = () => [\n // the entities of the new model's preset\n]\n```\nAn entity of a type the new version no longer has must not stay in the returned state. An entity id starts with its type (`Box-1`), so an entity that keeps its data under a new type name needs a new id and every relation pointing at it rewritten. Read `docs/phoenix/migrations.mdx` before writing any other migration.",sdkDocumentation:'## SDK Documentation\n\nAlways search SDK docs for relevant examples before implementing Phoenix features.\n\n### Commands\n- `pnpm phoenix docs` — Full documentation index with descriptions\n- `pnpm phoenix docs -s <term>` — Search all doc content and metadata (case-insensitive)\n- `pnpm phoenix docs --dir` — Print the absolute docs directory for grep or ripgrep\n- `pnpm phoenix docs -r <path>` — Read specific doc (raw text to stdout)\n- `pnpm phoenix docs -c <category>` — List docs in a category\n- `pnpm phoenix docs -l` — List all doc paths with titles\n\n### Key Docs\n- `docs/phoenix/getting-started.mdx` — Setup, prerequisites, first project\n- `docs/phoenix/quickstart.mdx` — End-to-end tutorial building a configurator\n- `docs/phoenix/domain-model.mdx` — Entities, attributes, relations, specs\n- `docs/phoenix/components.mdx` — ECS pattern, YAML components, custom components\n- `docs/phoenix/project-structure.mdx` — Files, folders, conventions\n- `docs/phoenix/best-practices.mdx` — YAML-first, code patterns, common pitfalls\n- `docs/phoenix/state-management.mdx` — Reactive state, RxJS pipelines, data flow\n- `docs/phoenix/expression-context.mdx` — Expression API, context object, helpers\n- `docs/phoenix/webhooks.mdx` — Server-side finalization workflows\n- `docs/phoenix/finalization.mdx` — Finalization system, PDF/email/CSV generation\n- `docs/phoenix/migrations.mdx` — Schema versioning, migration files\n\n### Agent Workflow\n1. Find relevant docs by content: `pnpm phoenix docs -s \'camera\'`\n2. Read matching doc: `pnpm phoenix docs -r docs/3d-scene/cameras/transitions.mdx`\n3. Search within a doc: `pnpm phoenix docs -r <path> | grep "example"`\n4. Search titles only as a fallback: `pnpm phoenix docs -l | grep "camera"`\n5. Search generated files directly when needed: `grep -rn "camera" "$(pnpm phoenix docs --dir)"`\n6. Browse a topic area: `pnpm phoenix docs -c "Layouts"`',assetInspection:"## 3D Asset Inspection\n\nRun `pnpm phoenix inspect:assets` to discover all glTF/GLB files in `public/` and get a summary table. Use `--file <path>` for detailed single-file inspection.\n\n**When to use:** before writing YAML/code that references objectName, materialsToOverride, morphTargetInfluences, or object positioning.\n\n**What it shows per node:**\n- Name, type (Mesh/Light/Camera/Empty), children\n- Transform: `pos=`, `rot=`, `scale=` (only non-default values shown)\n- Per-node morph targets: `morphs=Width,Height`\n- Bounding box: `bounds=WxHxD` (width x height x depth in meters)\n- Origin placement: `origin=center`, `bottom-center`, `top-center`, `bottom-corner`, etc. with numerical offset\n\n**Use cases:**\n- Find exact node names for `objectName` in scene entity components\n- Find material names for `materialsToOverride`\n- Find morph target names for `morphTargetInfluences`\n- Check model dimensions (bounds) for positioning, dimension indicators, or invariants\n- Check origin placement to understand how models anchor (center vs bottom-center)\n- Use `--json` for programmatic access to all data\n\n**Flags:** `--objects`, `--materials`, `--morphs`, `--animations`, `--json`",screenshotCli:"## Screenshot CLI\n\nCapture 3D canvas screenshots from a running dev server via `pnpm phoenix screenshot`.\n\n**Prerequisites:**\n1. `phoenix dev` must be running (starts the WebSocket server on port 3020)\n2. Configurator must be open in a browser (the browser does the actual rendering)\n\n**Options:**\n- `--output, -o` — Output file path (default: `./screenshot.png`)\n- `--width, -w` — Width in pixels (default: 1920)\n- `--height` — Height in pixels (default: 1080)\n- `--format, -f` — Image format: PNG or JPEG (default: PNG)\n- `--port` — WebSocket server port (default: 3020)\n\n**Example workflow:**\n1. Start dev server: `pnpm phoenix dev`\n2. Open configurator in browser (or via Playwright MCP)\n3. Take screenshot: `pnpm phoenix screenshot -o ./render.png -w 2560 --height 1440`\n\n**Use cases:** visual regression testing, generating product images, debugging 3D renders",inspectState:"## Inspect: State\n\nGet the current editor runtime state as JSON via `pnpm phoenix inspect:state`.\n\n**Prerequisites:** same as screenshot (dev server running + browser open)\n\n**Options:**\n- `--output, -o` — Output file path (prints to stdout if omitted)\n- `--sections, -s` — Comma-separated: entities, navigation, validation (default: all)\n- `--pretty` — Pretty-print JSON (default: true)\n- `--port` — WebSocket server port (default: 3020)\n\n**Example:** `pnpm phoenix inspect:state -o ./state.json -s entities,navigation`\n\n**Lifecycle status:** Always included in response. Shows which systems are ready:\n- `domainLoaded` — domain data loaded\n- `domainContextReady` — domain context initialized (entities available)\n- `configuratorReady` — 3D configurator initialized\n- `sessionAuthenticated` — session service active\n- `editorMode` — editor mode enabled\n\n**Tips:** Use `--sections` to limit payload size. Pipe through `head`/`tail` for partial output (e.g., `pnpm phoenix inspect:state | head -50`).\n\n**Use cases:** AI agent context, debugging entity state, inspecting navigation/validation",inspectData:`## Inspect: Data
11
10
 
12
11
  Get the current editor context data as JSON via \`pnpm phoenix inspect:data\`.
13
12
 
@@ -5,7 +5,7 @@ let e=e=>`webhookHandlers${e}`;export const generateApplicationSpecWebhookBuilde
5
5
  oauthClientId: phx.webhooksEnv.OAUTH_PROVIDER_CLIENT_ID,
6
6
  oauthClientSecret: phx.webhooksEnv.OAUTH_PROVIDER_CLIENT_SECRET,
7
7
  oauthProviderBaseUrl: phx.webhooksEnv.OAUTH_PROVIDER_BASE_URL,
8
- },`:"",n=o.map((t,o)=>{let i=e(o),n=t.replace(/\.tsx?$/,".js");return`import ${i} from '../${n}'`}).join("\n"),r=o.length>0,s=o.map((t,o)=>e(o)),a=r?`[${s.join(", ")}].flat()`:"[]",l=r?`
8
+ },`:"",r=o.map((t,o)=>{let i=e(o),r=t.replace(/\.tsx?$/,".js");return`import ${i} from '../${r}'`}).join("\n"),n=o.length>0,s=o.map((t,o)=>`{ origin: '${t}', exports: ${e(o)} }`),a=`[${s.join(", ")}]`,l=n?`
9
9
  .withHandlers(${a})`:"";return`// Auto-generated by application-spec pipeline. Do not edit.
10
10
  import { createDomainWebhook } from '@salsita-ai/sdk/webhook'
11
11
  import type { DeploymentAssistant } from '@salsita-ai/sdk/contracts/assistant'
@@ -13,8 +13,8 @@ import type { DeploymentAssistant } from '@salsita-ai/sdk/contracts/assistant'
13
13
  import { configuratorBuilder, createI18n } from './domain.js'
14
14
  import { customComponentOptics } from './configurator-domain-code.js'
15
15
  import { customAdminComponentOptics } from './admin-domain-code.js'
16
- ${n?`
17
- ${n}
16
+ ${r?`
17
+ ${r}
18
18
  `:""}
19
19
  const $assistantServerSettings: Pick<DeploymentAssistant, 'instructions' | 'ai'> | null = ${JSON.stringify(t.configurator.assistantServerSettings?{instructions:t.configurator.assistantServerSettings.instructions??void 0,ai:t.configurator.assistantServerSettings.ai}:null)}
20
20
 
@@ -104,106 +104,92 @@ All inputs include countersinkNotAvailable, as that is fixable by auto fix dialo
104
104
  And corresponding transformers
105
105
 
106
106
  ```typescript
107
- configuratorBuilder
108
- .withTransformers(() => [
109
- {
110
- priority: 3,
111
- transformer: (updates, currentState) => {
112
- if (updates.length > 1) {
113
- return updates
114
- }
115
-
116
- const materialUpdate = updates.find(
117
- (u): u is ComponentModification<MaterialSwatchComponent> =>
118
- u.kind === 'modifyComponent' && u.updateTag === 'selectSwatch-material'
119
- )
120
-
121
- if (!materialUpdate) {
122
- return updates
123
- }
124
-
125
- const plate = currentState.domainState.entities.find(Plate.is)!
126
- const newMaterial = materialUpdate.writableState.selectedSwatchKey
127
-
128
- const isAvailable = availableMaterials.some(
129
- state =>
130
- state.material === newMaterial && state.finish === plate.finish && state.thickness === plate.thickness
131
- )
132
-
133
- if (isAvailable) {
134
- return updates
135
- }
136
-
137
- const similarMaterial = availableMaterials.find(m => m.material === newMaterial)
138
-
139
- if (!similarMaterial) {
140
- return updates
141
- }
142
-
143
- const fixUpdate = updateFactory.DomainEntityModification({
144
- entityId: plate.id,
145
- stateDelta: {
146
- material: similarMaterial.material,
147
- finish: similarMaterial.finish,
148
- thickness: similarMaterial.thickness,
149
- },
150
- updateTag: 'fix.material',
151
- })
152
-
153
- return [fixUpdate]
107
+ // src/transformers/fix-finish.ts
108
+ import { availableMaterials } from '../_shared/available-materials.js'
109
+
110
+ export default phx.frontend.transformerBuilder.when
111
+ .entity(['Plate'])
112
+ .modified({ atFields: ['finish'] })
113
+ .then.overrideMatchingUpdate(({ update, getOld$Entity }) => {
114
+ const plate = getOld$Entity()
115
+ const newFinish = update.stateDelta.finish
116
+
117
+ const isAvailable = availableMaterials.some(
118
+ state => state.material === plate.material && state.finish === newFinish && state.thickness === plate.thickness
119
+ )
120
+
121
+ if (isAvailable) {
122
+ return [update]
123
+ }
124
+
125
+ const similarMaterial = availableMaterials.find(m => m.finish === newFinish && m.material === plate.material)
126
+
127
+ if (!similarMaterial) {
128
+ return [update]
129
+ }
130
+
131
+ const fixUpdate = phx.frontend.updates.DomainEntityModification({
132
+ entityId: plate.id,
133
+ stateDelta: {
134
+ material: similarMaterial.material,
135
+ finish: similarMaterial.finish,
136
+ thickness: similarMaterial.thickness,
154
137
  },
155
- },
156
- {
157
- priority: 3.1,
158
- transformer: (updates, currentState) => {
159
- if (updates.length > 1) {
160
- return updates
161
- }
162
-
163
- const materialUpdate = updates.find(
164
- (u): u is ComponentModification<AttributeSelectionComponent> =>
165
- u.kind === 'modifyComponent' &&
166
- u.updateTag === 'AttributeSelect.update' &&
167
- (u.componentInstance.instanceName as string) === 'finish'
168
- )
169
-
170
- if (!materialUpdate) {
171
- return updates
172
- }
173
-
174
- const plate = currentState.domainState.entities.find(Plate.is)!
175
- const newFinish = materialUpdate.writableState.value
176
-
177
- const isAvailable = availableMaterials.some(
178
- state =>
179
- state.material === plate.material && state.finish === newFinish && state.thickness === plate.thickness
180
- )
181
-
182
- if (isAvailable) {
183
- return updates
184
- }
185
-
186
- const similarMaterial = availableMaterials.find(m => m.finish === newFinish && m.material === plate.material)
187
-
188
- if (!similarMaterial) {
189
- return updates
190
- }
191
-
192
- const fixUpdate = updateFactory.DomainEntityModification({
193
- entityId: plate.id,
194
- stateDelta: {
195
- material: similarMaterial.material,
196
- finish: similarMaterial.finish,
197
- thickness: similarMaterial.thickness,
198
- },
199
- updateTag: 'fix.brushed',
200
- })
201
-
202
- return [fixUpdate]
138
+ updateTag: 'fix.brushed',
139
+ })
140
+
141
+ return [fixUpdate]
142
+ })
143
+ .build('fix-finish')
144
+ ```
145
+
146
+ ```typescript
147
+ // src/transformers/fix-material.ts
148
+ import { availableMaterials } from '../_shared/available-materials.js'
149
+
150
+ export default phx.frontend.transformerBuilder.when
151
+ .entity(['Plate'])
152
+ .modified({ atFields: ['material'] })
153
+ .then.overrideMatchingUpdate(({ update, getOld$Entity }) => {
154
+ const plate = getOld$Entity()
155
+ const newMaterial = update.stateDelta.material
156
+
157
+ const isAvailable = availableMaterials.some(
158
+ state => state.material === newMaterial && state.finish === plate.finish && state.thickness === plate.thickness
159
+ )
160
+
161
+ if (isAvailable) {
162
+ return [update]
163
+ }
164
+
165
+ const similarMaterial = availableMaterials.find(m => m.material === newMaterial)
166
+
167
+ if (!similarMaterial) {
168
+ return [update]
169
+ }
170
+
171
+ const fixUpdate = phx.frontend.updates.DomainEntityModification({
172
+ entityId: plate.id,
173
+ stateDelta: {
174
+ material: similarMaterial.material,
175
+ finish: similarMaterial.finish,
176
+ thickness: similarMaterial.thickness,
203
177
  },
204
- },
205
- ])
206
- .buildConfig()
178
+ updateTag: 'fix.material',
179
+ })
180
+
181
+ return [fixUpdate]
182
+ })
183
+ .build('fix-material')
184
+ ```
185
+
186
+ Each file in `src/transformers/` default-exports one transformer and is picked up by its location. The `transformers` section of the spec turns it on by name. For a transformer made with `build(name)` that is the name passed to `build(...)`, which must match the file name with case and dashes ignored (`fix-finish.ts` and `fixFinish` match). For a plain-function export it is the file name:
187
+
188
+ ```yaml
189
+ # spec/application.yaml
190
+ transformers:
191
+ - name: fix-finish
192
+ - name: fix-material
207
193
  ```
208
194
 
209
195
  And FilteredControls
@@ -18,7 +18,7 @@ The `createResetSelectionOnNavigationTransformer` automatically deselects entiti
18
18
 
19
19
  ## Guide
20
20
 
21
- The `createResetSelectionOnNavigationTransformer` is added through the `.withTransformers()` method. It automatically injects a deselect update when navigating to specified states.
21
+ The `createResetSelectionOnNavigationTransformer` is added as a file in `src/transformers/`. It automatically injects a deselect update when navigating to specified states.
22
22
 
23
23
  ### Step 1: Import the transformer
24
24
 
@@ -28,19 +28,25 @@ Import the transformer function from the domain package:
28
28
  import { createResetSelectionOnNavigationTransformer } from '@salsita-ai/sdk/domain'
29
29
  ```
30
30
 
31
- ### Step 2: Add the transformer to your config
31
+ ### Step 2: Add the transformer to your project
32
32
 
33
- Use the `.withTransformers()` method on the builder:
33
+ Create the transformer in a file under `src/transformers/`:
34
34
 
35
35
  ```typescript
36
- const config = configuratorBuilder
37
- .withTransformers(ctx => [
38
- {
39
- priority: 32,
40
- transformer: createResetSelectionOnNavigationTransformer([ApplicationTypes.NavigationState.SecondStep], ctx),
41
- },
42
- ])
43
- .buildConfig()
36
+ // src/transformers/reset-selection.ts
37
+ import { createResetSelectionOnNavigationTransformer } from '@salsita-ai/sdk/domain'
38
+
39
+ export default phx.frontend.createTransformer(ctx =>
40
+ createResetSelectionOnNavigationTransformer([phx.applicationTypes.NavigationState.SecondStep], ctx)
41
+ )
42
+ ```
43
+
44
+ Each file in `src/transformers/` default-exports one transformer and is picked up by its location. The `transformers` section of the spec turns it on by name. For a transformer made with `build(name)` that is the name passed to `build(...)`, which must match the file name with case and dashes ignored (`fix-finish.ts` and `fixFinish` match). For a plain-function export it is the file name:
45
+
46
+ ```yaml
47
+ # spec/application.yaml
48
+ transformers:
49
+ - name: reset-selection
44
50
  ```
45
51
 
46
52
  The transformer takes two arguments:
@@ -97,7 +103,7 @@ When the transformer triggers, any selected entity is deselected automatically.
97
103
  *
98
104
  * @param navigationStates - Array of navigation state names that trigger deselection
99
105
  * @param ctx - Domain context providing access to the navigation system
100
- * @returns Update transformer that can be registered in withTransformers
106
+ * @returns Update transformer to return from a transformer file in src/transformers/
101
107
  *
102
108
  * @example
103
109
  * // Deselect when entering the summary step
@@ -1,5 +1,5 @@
1
1
  {
2
- "generatedAt": "2026-10-12T16:01:57.319Z",
2
+ "generatedAt": "2026-10-13T05:23:14.254Z",
3
3
  "categories": [
4
4
  {
5
5
  "name": "Phoenix",