@volter/editor-core 0.5.57

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 (719) hide show
  1. package/BUNDLED_NOTICES +1527 -0
  2. package/LICENSE +686 -0
  3. package/LICENSE-APACHE +202 -0
  4. package/NOTICE +18 -0
  5. package/README.md +24 -0
  6. package/dist/build/chunk-JS4D4XZ3.js +175 -0
  7. package/dist/build/chunk-JS4D4XZ3.js.map +7 -0
  8. package/dist/build/vite-plugin-product-contributions.js +100 -0
  9. package/dist/build/vite-plugin-product-contributions.js.map +7 -0
  10. package/dist/build/vite-plugin-shared-react.js +25 -0
  11. package/dist/build/vite-plugin-shared-react.js.map +7 -0
  12. package/dist/build/vite-plugin-shared-three.js +86 -0
  13. package/dist/build/vite-plugin-shared-three.js.map +7 -0
  14. package/dist/server/chunk-KMJC7AGO.js +98 -0
  15. package/dist/server/chunk-KMJC7AGO.js.map +7 -0
  16. package/dist/server/chunk-PSILUMGS.js +46 -0
  17. package/dist/server/chunk-PSILUMGS.js.map +7 -0
  18. package/dist/server/frame-proxy.js +255 -0
  19. package/dist/server/frame-proxy.js.map +7 -0
  20. package/dist/server/open-browser.js +53 -0
  21. package/dist/server/open-browser.js.map +7 -0
  22. package/dist/server/process-shutdown.js +127 -0
  23. package/dist/server/process-shutdown.js.map +7 -0
  24. package/dist/server/session-registry.js +141 -0
  25. package/dist/server/session-registry.js.map +7 -0
  26. package/dist/server/spawn-opener.js +11 -0
  27. package/dist/server/spawn-opener.js.map +7 -0
  28. package/dist/server/worktree-identity.js +11 -0
  29. package/dist/server/worktree-identity.js.map +7 -0
  30. package/dist-server/packaged.mjs +88816 -0
  31. package/package.json +118 -0
  32. package/scripts/build-plugins.mjs +14 -0
  33. package/scripts/build-server.mjs +26 -0
  34. package/scripts/build-session.mjs +9 -0
  35. package/server/account-credentials.ts +60 -0
  36. package/server/account-service.ts +1434 -0
  37. package/server/adapter-region-includes.ts +47 -0
  38. package/server/asset-catalog-v2.ts +175 -0
  39. package/server/asset-history-snapshots.ts +196 -0
  40. package/server/asset-ledger-store.ts +195 -0
  41. package/server/asset-library-routes.ts +1595 -0
  42. package/server/blender-wasm-artifact.ts +430 -0
  43. package/server/boot-timings.ts +106 -0
  44. package/server/canonical-path.ts +50 -0
  45. package/server/checkout-workspace-preflight.ts +349 -0
  46. package/server/cloud-asset-catalog.ts +158 -0
  47. package/server/coding-inference-launch.ts +237 -0
  48. package/server/collaboration-account-client.ts +202 -0
  49. package/server/collaboration-attribution.ts +122 -0
  50. package/server/collaboration-session.ts +934 -0
  51. package/server/comfyui-bridge.ts +248 -0
  52. package/server/console-ledger.ts +499 -0
  53. package/server/creation-site-transform.ts +304 -0
  54. package/server/creation-site-write.ts +648 -0
  55. package/server/data-file-serialize.ts +158 -0
  56. package/server/editor-brand-html.ts +72 -0
  57. package/server/editor-control-socket.ts +366 -0
  58. package/server/editor-server-options.ts +190 -0
  59. package/server/editor-server.ts +1483 -0
  60. package/server/editor-sse.ts +352 -0
  61. package/server/engine-provenance.ts +169 -0
  62. package/server/engine-source-restart.ts +117 -0
  63. package/server/frame-bridge.ts +115 -0
  64. package/server/frame-proxy.ts +490 -0
  65. package/server/frame-workbench.ts +259 -0
  66. package/server/frontend-handoff.ts +229 -0
  67. package/server/game-globals-shadow.ts +113 -0
  68. package/server/gameplay-session-retention.ts +149 -0
  69. package/server/gameplay-sessions.ts +123 -0
  70. package/server/generation-jobs.ts +201 -0
  71. package/server/generation-reconciler.ts +137 -0
  72. package/server/generative-execution-context.ts +59 -0
  73. package/server/git-workflow.ts +612 -0
  74. package/server/harness-chat-caller.ts +36 -0
  75. package/server/harness-chat-service.ts +1681 -0
  76. package/server/idle-shutdown.ts +170 -0
  77. package/server/js-profiling-policy.ts +52 -0
  78. package/server/launcher-settings.ts +84 -0
  79. package/server/local-asset-catalog.ts +410 -0
  80. package/server/managed-account-defaults.ts +22 -0
  81. package/server/mock-control-plane.ts +540 -0
  82. package/server/model-import-conversion.ts +345 -0
  83. package/server/native-credential-store.ts +162 -0
  84. package/server/open-browser.ts +118 -0
  85. package/server/packaged.ts +1192 -0
  86. package/server/play-stall.ts +126 -0
  87. package/server/process-shutdown.ts +218 -0
  88. package/server/product-presets.ts +55 -0
  89. package/server/project-build-artifact.ts +95 -0
  90. package/server/project-components.ts +100 -0
  91. package/server/project-dependency-invalidation.ts +114 -0
  92. package/server/project-file-scan.ts +235 -0
  93. package/server/project-hmr-files.ts +215 -0
  94. package/server/project-install-roots.ts +210 -0
  95. package/server/project-kinds.ts +71 -0
  96. package/server/project-mcp-servers.ts +82 -0
  97. package/server/project-module-freshness.ts +109 -0
  98. package/server/project-module-instance.ts +375 -0
  99. package/server/project-optimize-deps-entries.ts +827 -0
  100. package/server/project-output-writer.ts +679 -0
  101. package/server/project-package-origin.ts +63 -0
  102. package/server/project-root-surface.ts +831 -0
  103. package/server/project-scratch-path.ts +47 -0
  104. package/server/project-script-hmr.ts +619 -0
  105. package/server/project-serving-plugins.ts +236 -0
  106. package/server/project-tools.ts +653 -0
  107. package/server/project-validation.ts +250 -0
  108. package/server/project-verbs.ts +127 -0
  109. package/server/project-view.ts +52 -0
  110. package/server/project-watch.ts +1134 -0
  111. package/server/project-work-coordinator.ts +288 -0
  112. package/server/provider-credentials.ts +331 -0
  113. package/server/recent-projects-store.ts +98 -0
  114. package/server/redact-secrets.ts +71 -0
  115. package/server/repository-presence.ts +267 -0
  116. package/server/routes/account.ts +357 -0
  117. package/server/routes/agents.ts +60 -0
  118. package/server/routes/assets.ts +154 -0
  119. package/server/routes/build.ts +13 -0
  120. package/server/routes/collaboration.ts +595 -0
  121. package/server/routes/configurations.ts +419 -0
  122. package/server/routes/context.ts +264 -0
  123. package/server/routes/control-plane.ts +1811 -0
  124. package/server/routes/logs.ts +272 -0
  125. package/server/routes/project-identity.ts +302 -0
  126. package/server/routes/project-open.ts +429 -0
  127. package/server/routes/project-source.ts +686 -0
  128. package/server/routes/project-state.ts +383 -0
  129. package/server/routes/relay.ts +1029 -0
  130. package/server/routes/route-helpers.ts +29 -0
  131. package/server/routes/served-modules.ts +138 -0
  132. package/server/routes/session-tabs.ts +196 -0
  133. package/server/routes/settings.ts +121 -0
  134. package/server/routes/share-control.ts +486 -0
  135. package/server/routes/themes.ts +116 -0
  136. package/server/routes/tools.ts +230 -0
  137. package/server/routes/worktrees.ts +595 -0
  138. package/server/scoped-game-css.ts +461 -0
  139. package/server/server-utils.ts +1194 -0
  140. package/server/session-product.ts +112 -0
  141. package/server/session-registry.ts +230 -0
  142. package/server/share-claims.ts +138 -0
  143. package/server/share-host.ts +526 -0
  144. package/server/share-session-gateway.ts +1362 -0
  145. package/server/share-tunnel.ts +123 -0
  146. package/server/spawn-opener.ts +74 -0
  147. package/server/support/play/log-format.ts +76 -0
  148. package/server/support/play/session-record.ts +199 -0
  149. package/server/support/project/build-discipline.ts +718 -0
  150. package/server/support/project/inspection-node.ts +119 -0
  151. package/server/support/project/log-naming.ts +54 -0
  152. package/server/support/project/provenance.ts +290 -0
  153. package/server/support/project/run-name.ts +18 -0
  154. package/server/support/project/session-journal.ts +830 -0
  155. package/server/support/project/shared.ts +327 -0
  156. package/server/tab-bootstrap.ts +62 -0
  157. package/server/tab-heartbeat.ts +477 -0
  158. package/server/tab-lifecycle.ts +550 -0
  159. package/server/tab-presence.ts +1508 -0
  160. package/server/team-agent-mirror.ts +95 -0
  161. package/server/twin-auth.ts +138 -0
  162. package/server/vendored-lock-recorder.ts +968 -0
  163. package/server/worktree-identity.ts +121 -0
  164. package/server/worktree-management.ts +398 -0
  165. package/server/worktree-retention.d.mts +13 -0
  166. package/server/worktree-retention.mjs +205 -0
  167. package/src/EditorContext.tsx +169 -0
  168. package/src/account.ts +333 -0
  169. package/src/action-registry.ts +532 -0
  170. package/src/active-product.ts +74 -0
  171. package/src/active-project.ts +155 -0
  172. package/src/adapter-editor-config.ts +25 -0
  173. package/src/adapter-observation.ts +49 -0
  174. package/src/animation/stage-transport.ts +379 -0
  175. package/src/animation/three-clips-subject.ts +172 -0
  176. package/src/api/asset-library-wire.ts +45 -0
  177. package/src/api/assets.ts +365 -0
  178. package/src/api/base.ts +10 -0
  179. package/src/api/build.ts +99 -0
  180. package/src/api/git-wire.ts +56 -0
  181. package/src/api/logs.ts +92 -0
  182. package/src/api/project-identity.ts +74 -0
  183. package/src/api/project-open.ts +355 -0
  184. package/src/api/project-source.ts +162 -0
  185. package/src/api/project-state.ts +107 -0
  186. package/src/api/relay.ts +268 -0
  187. package/src/api/settings.ts +36 -0
  188. package/src/api/themes.ts +45 -0
  189. package/src/api/worktrees.ts +257 -0
  190. package/src/asset-compare-core.ts +171 -0
  191. package/src/asset-compare.ts +294 -0
  192. package/src/asset-editor-context.tsx +100 -0
  193. package/src/asset-events.ts +97 -0
  194. package/src/asset-inspector-actions.ts +87 -0
  195. package/src/asset-preview-framing.ts +357 -0
  196. package/src/asset-preview.ts +2802 -0
  197. package/src/asset-selection-viewer-registry.ts +113 -0
  198. package/src/asset-selection.ts +133 -0
  199. package/src/asset-workflow/asset-capabilities.ts +344 -0
  200. package/src/asset-workflow/asset-import-jobs.ts +106 -0
  201. package/src/asset-workflow/asset-ledger-backend.ts +126 -0
  202. package/src/asset-workflow/asset-ledger.ts +156 -0
  203. package/src/asset-workflow/asset-materialization-report.ts +140 -0
  204. package/src/asset-workflow/asset-pack-manifest.ts +320 -0
  205. package/src/asset-workflow/asset-types.ts +142 -0
  206. package/src/asset-workflow/asset-workflow-quality.ts +61 -0
  207. package/src/asset-workflow/audio-preview-player.ts +193 -0
  208. package/src/asset-workflow/audio-waveform.ts +22 -0
  209. package/src/asset-workflow/cloud-asset-client.ts +263 -0
  210. package/src/asset-workflow/folder-preview.ts +345 -0
  211. package/src/asset-workflow/hosted-asset-materialization.ts +236 -0
  212. package/src/asset-workflow/image-view-scale.ts +32 -0
  213. package/src/asset-workflow/import-contract.ts +124 -0
  214. package/src/asset-workflow/ledger-write-lock.ts +244 -0
  215. package/src/asset-workflow/model-inspection.ts +818 -0
  216. package/src/asset-workflow/pixi-spritesheet.ts +197 -0
  217. package/src/asset-workflow/preview-resource-lifetime.ts +44 -0
  218. package/src/asset-workflow/project-asset-commands.ts +23 -0
  219. package/src/asset-workflow/project-asset-health.ts +139 -0
  220. package/src/asset-workflow/project-asset-operations.ts +154 -0
  221. package/src/asset-workflow/project-asset-roots.ts +68 -0
  222. package/src/asset-workflow/project-content.ts +288 -0
  223. package/src/asset-workflow/project-source-index.ts +550 -0
  224. package/src/asset-workflow/thumbnail-system.ts +256 -0
  225. package/src/authoring/active-adapter.ts +199 -0
  226. package/src/authoring/active-systems.ts +422 -0
  227. package/src/authoring/adapter-key.ts +18 -0
  228. package/src/authoring/authoring-asset-url.ts +27 -0
  229. package/src/authoring/bootstrap-state.ts +49 -0
  230. package/src/authoring/boundary-authoring-adapter.ts +184 -0
  231. package/src/authoring/breakpoint-state.ts +43 -0
  232. package/src/authoring/canvas-scene-guides.ts +76 -0
  233. package/src/authoring/component-instance-root.ts +171 -0
  234. package/src/authoring/composite-authoring-adapter.ts +2110 -0
  235. package/src/authoring/consumer-actions.ts +520 -0
  236. package/src/authoring/css-numeric-style.ts +97 -0
  237. package/src/authoring/design-time-layers.ts +849 -0
  238. package/src/authoring/design-time-mount-registry.ts +235 -0
  239. package/src/authoring/design-time-settle.ts +343 -0
  240. package/src/authoring/edit-mode-authoring.ts +619 -0
  241. package/src/authoring/eyedropper-session.ts +60 -0
  242. package/src/authoring/instance-source-menu-register.ts +13 -0
  243. package/src/authoring/instance-source-menu.ts +135 -0
  244. package/src/authoring/layered-pick.ts +183 -0
  245. package/src/authoring/live-gesture-lock.ts +50 -0
  246. package/src/authoring/live-object-transform.ts +62 -0
  247. package/src/authoring/mount-failure-report.ts +154 -0
  248. package/src/authoring/mounted-root-subjects.ts +144 -0
  249. package/src/authoring/no-authoring-adapter.ts +55 -0
  250. package/src/authoring/null-inspection-subjects.tsx +75 -0
  251. package/src/authoring/object3d-document-persistence.ts +106 -0
  252. package/src/authoring/object3d-document-session-registry.ts +120 -0
  253. package/src/authoring/object3d-document-session.ts +1326 -0
  254. package/src/authoring/object3d-gesture-controller.ts +113 -0
  255. package/src/authoring/panel-authoring.ts +121 -0
  256. package/src/authoring/prefab-instance-inspector-section.tsx +237 -0
  257. package/src/authoring/prefab-instance-section-model.ts +55 -0
  258. package/src/authoring/project-authoring-session.ts +105 -0
  259. package/src/authoring/provenance.ts +99 -0
  260. package/src/authoring/quarks-particle-systems.ts +19 -0
  261. package/src/authoring/react-canvas-navigation.ts +255 -0
  262. package/src/authoring/react-design-canvas-style.ts +20 -0
  263. package/src/authoring/react-story-board.ts +937 -0
  264. package/src/authoring/selection-scope.ts +195 -0
  265. package/src/authoring/shell-document-ops.ts +169 -0
  266. package/src/authoring/shell-object3d-document-write-policy.ts +108 -0
  267. package/src/authoring/shell-viewport-policy.ts +48 -0
  268. package/src/authoring/source-object3d-authoring-adapter.ts +526 -0
  269. package/src/authoring/stories-scope.ts +35 -0
  270. package/src/authoring/story-board-chrome-fit.ts +107 -0
  271. package/src/authoring/story-board-presentation.ts +111 -0
  272. package/src/authoring/three-projection-core.ts +226 -0
  273. package/src/authoring/viewport-pick-context.ts +40 -0
  274. package/src/authoring/viewport-raycast.ts +240 -0
  275. package/src/authoring/viewport-tool-context.ts +73 -0
  276. package/src/authoring/world-canvas-viewport-state.ts +35 -0
  277. package/src/authoring/world-hidden-viewport.ts +152 -0
  278. package/src/authoring/world-pan-state.ts +198 -0
  279. package/src/authoring/world-session-state.ts +101 -0
  280. package/src/authoring/write-pipe.ts +173 -0
  281. package/src/availability-tick.ts +66 -0
  282. package/src/bitmap-label.ts +120 -0
  283. package/src/blender-tab-metrics.ts +161 -0
  284. package/src/board-open-actions.ts +20 -0
  285. package/src/boot-routing.ts +391 -0
  286. package/src/build-identity.ts +15 -0
  287. package/src/bytes-codec.ts +62 -0
  288. package/src/camera-authoring.ts +175 -0
  289. package/src/cancellation-reason.ts +58 -0
  290. package/src/canvas-preview-frames.ts +482 -0
  291. package/src/capture-camera-pose.ts +77 -0
  292. package/src/chrome-registry.ts +159 -0
  293. package/src/chrome-slot-registry.ts +91 -0
  294. package/src/collaboration-client.ts +264 -0
  295. package/src/collaboration-presence.ts +41 -0
  296. package/src/command-dispatch.ts +19 -0
  297. package/src/command-listener.ts +2743 -0
  298. package/src/command-registry.ts +70 -0
  299. package/src/component-board-registry.ts +205 -0
  300. package/src/component-states-registry.ts +200 -0
  301. package/src/components/AgentPresentationNotice.tsx +75 -0
  302. package/src/components/AlignToolbar.tsx +204 -0
  303. package/src/components/AppRoot.tsx +394 -0
  304. package/src/components/ApplicationMenus.tsx +415 -0
  305. package/src/components/AssetBrowser.tsx +2843 -0
  306. package/src/components/AssetEditorShell.tsx +216 -0
  307. package/src/components/AssetInspectorToolSection.tsx +124 -0
  308. package/src/components/BoardRulers.tsx +354 -0
  309. package/src/components/CameraInfo.tsx +81 -0
  310. package/src/components/CanvasSceneViewport.tsx +556 -0
  311. package/src/components/CapabilityCoverageSection.tsx +185 -0
  312. package/src/components/CenterDocuments.tsx +22 -0
  313. package/src/components/ChromeSlot.tsx +20 -0
  314. package/src/components/CodeView.tsx +470 -0
  315. package/src/components/CollaborationHeaderControl.css +74 -0
  316. package/src/components/CompactInspectorCard.tsx +190 -0
  317. package/src/components/CompactInspectorShell.tsx +39 -0
  318. package/src/components/ConsolePanel.css +55 -0
  319. package/src/components/ConsolePanel.tsx +270 -0
  320. package/src/components/DefaultEditorLayout.tsx +106 -0
  321. package/src/components/DocumentHeaderStrip.tsx +96 -0
  322. package/src/components/DocumentShelfRail.tsx +45 -0
  323. package/src/components/DocumentThumbnail.tsx +345 -0
  324. package/src/components/EditorLeaseGuard.tsx +372 -0
  325. package/src/components/ErrorBanner.tsx +123 -0
  326. package/src/components/FolderPreviewTile.tsx +159 -0
  327. package/src/components/GameHierarchy.tsx +3842 -0
  328. package/src/components/GameplaySessionTimeline.tsx +295 -0
  329. package/src/components/InspectionProjection.tsx +968 -0
  330. package/src/components/Inspector.tsx +233 -0
  331. package/src/components/InspectorCanvasPreview.tsx +35 -0
  332. package/src/components/InspectorFieldsSection.tsx +290 -0
  333. package/src/components/InspectorObjectPreview.tsx +57 -0
  334. package/src/components/InspectorStoriesSection.tsx +92 -0
  335. package/src/components/InspectorToolSection.tsx +96 -0
  336. package/src/components/InspectorTransformSection.tsx +245 -0
  337. package/src/components/LightExplorerPanel.tsx +433 -0
  338. package/src/components/MediaProperties.tsx +145 -0
  339. package/src/components/NonThreeAuthoringBootstrap.tsx +19 -0
  340. package/src/components/Object3DDocumentToolbar.css +100 -0
  341. package/src/components/Object3DDocumentToolbar.tsx +454 -0
  342. package/src/components/Object3DDocumentViewport.tsx +58 -0
  343. package/src/components/ProjectHeader.css +617 -0
  344. package/src/components/ProjectHeader.tsx +328 -0
  345. package/src/components/ProjectLayout.tsx +249 -0
  346. package/src/components/ReactCanvasControls.tsx +284 -0
  347. package/src/components/RootSelectionOverlay.tsx +3162 -0
  348. package/src/components/RootTextEditor.tsx +79 -0
  349. package/src/components/SaveStatus.tsx +70 -0
  350. package/src/components/StageHost.tsx +1954 -0
  351. package/src/components/StageOverlays.tsx +21 -0
  352. package/src/components/StartupErrorScreen.tsx +76 -0
  353. package/src/components/StartupLoadingScreen.tsx +65 -0
  354. package/src/components/StatsOverlay.tsx +78 -0
  355. package/src/components/SurfaceStateOverlay.tsx +24 -0
  356. package/src/components/ToolContributionSurfaces.tsx +65 -0
  357. package/src/components/ToolHost.tsx +370 -0
  358. package/src/components/ToolObject3DPreview.tsx +39 -0
  359. package/src/components/Toolbar.tsx +595 -0
  360. package/src/components/TransientHint.tsx +44 -0
  361. package/src/components/TransportStrip.tsx +174 -0
  362. package/src/components/VersionControlSection.tsx +470 -0
  363. package/src/components/VgaiLogo.css +83 -0
  364. package/src/components/VgaiLogo.tsx +35 -0
  365. package/src/components/ViewportControlsHint.tsx +60 -0
  366. package/src/components/ViewportFurniture.tsx +401 -0
  367. package/src/components/ViewportOverlay.tsx +145 -0
  368. package/src/components/ViewportOverlaysMenu.tsx +153 -0
  369. package/src/components/ViewportShadingMenu.tsx +300 -0
  370. package/src/components/ViewportViewMenu.tsx +101 -0
  371. package/src/components/WorkspaceDocumentSurface.tsx +204 -0
  372. package/src/components/WorkspaceUtilitySurface.tsx +22 -0
  373. package/src/components/WorktreeSwitcher.css +239 -0
  374. package/src/components/WorktreeSwitcher.tsx +890 -0
  375. package/src/components/account-documents.tsx +1162 -0
  376. package/src/components/asset-documents.tsx +812 -0
  377. package/src/components/asset-editor-persistence.ts +216 -0
  378. package/src/components/asset-selection-section.tsx +535 -0
  379. package/src/components/asset-thumbnails.tsx +312 -0
  380. package/src/components/asset-viewers/AudioViewer.tsx +201 -0
  381. package/src/components/asset-viewers/EntityModelDocument.tsx +122 -0
  382. package/src/components/asset-viewers/EnvironmentAssetDocument.tsx +440 -0
  383. package/src/components/asset-viewers/GenericJsonViewer.tsx +102 -0
  384. package/src/components/asset-viewers/ImageViewer.tsx +300 -0
  385. package/src/components/asset-viewers/JsonAssetDocument.tsx +93 -0
  386. package/src/components/asset-viewers/LiveModuleDocument.tsx +417 -0
  387. package/src/components/asset-viewers/LutAssetDocument.tsx +444 -0
  388. package/src/components/asset-viewers/ModelAssetDocument.tsx +105 -0
  389. package/src/components/asset-viewers/Object3DPreview.tsx +359 -0
  390. package/src/components/asset-viewers/OnlineAssetDetail.tsx +421 -0
  391. package/src/components/asset-viewers/PasteboardModuleDocument.tsx +67 -0
  392. package/src/components/asset-viewers/QuarksAssetDocument.tsx +526 -0
  393. package/src/components/asset-viewers/ShaderAssetDocument.tsx +743 -0
  394. package/src/components/asset-viewers/SourceAssetViewer.tsx +281 -0
  395. package/src/components/asset-viewers/SpritesheetSpriteView.tsx +102 -0
  396. package/src/components/asset-viewers/VideoViewer.tsx +101 -0
  397. package/src/components/asset-viewers/shader-source.ts +144 -0
  398. package/src/components/asset-workflow.css +731 -0
  399. package/src/components/board-guides.ts +150 -0
  400. package/src/components/compact-inspector.css +539 -0
  401. package/src/components/core-utilities.tsx +90 -0
  402. package/src/components/editor-notifications.css +40 -0
  403. package/src/components/engine-workspace.css +274 -0
  404. package/src/components/inspector-preview-section.tsx +238 -0
  405. package/src/components/inspector-property-grouping.ts +64 -0
  406. package/src/components/inspector-revert-label.ts +20 -0
  407. package/src/components/inspector-selection.ts +42 -0
  408. package/src/components/inspector-stories-gating.ts +171 -0
  409. package/src/components/inspector-transform-subject.ts +11 -0
  410. package/src/components/inspector-transform.ts +75 -0
  411. package/src/components/kind-documents.tsx +500 -0
  412. package/src/components/palette-action-publisher.tsx +140 -0
  413. package/src/components/primitives/DraftColorInput.tsx +74 -0
  414. package/src/components/product-shell.css +1829 -0
  415. package/src/components/project-tool-documents.tsx +410 -0
  416. package/src/components/scene-documents.tsx +223 -0
  417. package/src/components/stage-keyboard.tsx +37 -0
  418. package/src/components/stage-overlay-set.tsx +107 -0
  419. package/src/components/stage-presence-markers.ts +478 -0
  420. package/src/components/standard-viewport-dressing.ts +417 -0
  421. package/src/components/status-contributions.tsx +403 -0
  422. package/src/components/tool-documents.tsx +309 -0
  423. package/src/components/tool-schema-form.tsx +262 -0
  424. package/src/components/use-after-paint.ts +41 -0
  425. package/src/components/use-project-image-assets.ts +86 -0
  426. package/src/components/viewport-header-controls.css +90 -0
  427. package/src/components/viewport-surface-status.tsx +55 -0
  428. package/src/components/workspace-history.ts +32 -0
  429. package/src/components/workspace-static-panel-registry.tsx +152 -0
  430. package/src/components/workspace-surfaces.css +621 -0
  431. package/src/components/world-documents.tsx +586 -0
  432. package/src/components/world-overlay-gestures.ts +1694 -0
  433. package/src/composite-screenshot.ts +1641 -0
  434. package/src/console-sync.ts +131 -0
  435. package/src/constraint-helper.ts +338 -0
  436. package/src/content-entry-source-registry.ts +184 -0
  437. package/src/coverage/authoring-seam-evidence.ts +300 -0
  438. package/src/coverage/canvas-reveal.ts +192 -0
  439. package/src/coverage/design-time-surfaces.ts +101 -0
  440. package/src/coverage/live-seam-evidence.ts +11 -0
  441. package/src/coverage/ontology-invariants.ts +466 -0
  442. package/src/coverage/session-vitals.ts +501 -0
  443. package/src/coverage/system-seam-evidence.ts +72 -0
  444. package/src/crash-null-boundary.ts +36 -0
  445. package/src/creation-site-edit.ts +1479 -0
  446. package/src/creation-site-registry.ts +160 -0
  447. package/src/delegate-harness-registry.ts +143 -0
  448. package/src/document-context-registry.ts +177 -0
  449. package/src/document-open-registry.ts +200 -0
  450. package/src/document-preview-source.ts +20 -0
  451. package/src/document-renderer-session.ts +138 -0
  452. package/src/editor-api.ts +46 -0
  453. package/src/editor-chrome-capture.ts +139 -0
  454. package/src/editor-commands.ts +164 -0
  455. package/src/editor-console.ts +563 -0
  456. package/src/editor-current-view.ts +82 -0
  457. package/src/editor-document-probe.ts +881 -0
  458. package/src/editor-git-client.ts +115 -0
  459. package/src/editor-host-door.ts +462 -0
  460. package/src/editor-hotkeys.ts +842 -0
  461. package/src/editor-lease-view.ts +39 -0
  462. package/src/editor-lease.ts +415 -0
  463. package/src/editor-mode.ts +19 -0
  464. package/src/editor-notifications.ts +140 -0
  465. package/src/editor-presence.ts +563 -0
  466. package/src/editor-presentation-activity.ts +50 -0
  467. package/src/editor-presentation-notice.ts +42 -0
  468. package/src/editor-runtime.tsx +145 -0
  469. package/src/editor-server-response.ts +86 -0
  470. package/src/editor-session-attribution.ts +75 -0
  471. package/src/editor-session-mode.ts +54 -0
  472. package/src/editor-shell-store.ts +1304 -0
  473. package/src/editor-state-facets.ts +74 -0
  474. package/src/editor-styles.css +33 -0
  475. package/src/editor-view-presentation.ts +810 -0
  476. package/src/editor-viewport.ts +5302 -0
  477. package/src/entity-lod.ts +31 -0
  478. package/src/entity-object.ts +91 -0
  479. package/src/files/file-provider.ts +62 -0
  480. package/src/files/project-files.ts +264 -0
  481. package/src/finders/index.ts +136 -0
  482. package/src/finders/scenes-from-entrypoint-selection.ts +387 -0
  483. package/src/frame/bridge.tsx +1408 -0
  484. package/src/frame/product.ts +77 -0
  485. package/src/gameplay-dom-recording.ts +319 -0
  486. package/src/gameplay-export-state.ts +14 -0
  487. package/src/gameplay-replay.ts +417 -0
  488. package/src/gameplay-session-time.ts +9 -0
  489. package/src/gameplay-sessions.ts +204 -0
  490. package/src/harness-chat-types.ts +253 -0
  491. package/src/hierarchy-component-marks.ts +298 -0
  492. package/src/hierarchy-drop.ts +91 -0
  493. package/src/hierarchy-expansion-state.ts +80 -0
  494. package/src/hierarchy-header-slot.ts +52 -0
  495. package/src/hierarchy-internals.ts +197 -0
  496. package/src/hierarchy-kind-icon.ts +217 -0
  497. package/src/hierarchy-mark-reader.ts +73 -0
  498. package/src/hierarchy-menu-registry.ts +67 -0
  499. package/src/hierarchy-node-rows.ts +307 -0
  500. package/src/hierarchy-panel-view.ts +280 -0
  501. package/src/hierarchy-projection.ts +76 -0
  502. package/src/hierarchy-row-cache.ts +243 -0
  503. package/src/hierarchy-row-model.ts +308 -0
  504. package/src/hierarchy-rows.ts +11 -0
  505. package/src/hierarchy-walk.ts +86 -0
  506. package/src/history/editor-session.ts +25 -0
  507. package/src/history/history-commands.ts +147 -0
  508. package/src/history/history-delegate.ts +163 -0
  509. package/src/history/history-limit-notices.ts +43 -0
  510. package/src/history/history-service.ts +1173 -0
  511. package/src/history/persistence-coordinator.ts +35 -0
  512. package/src/history/project-file-history.ts +386 -0
  513. package/src/history/project-root-history-backends.ts +139 -0
  514. package/src/history/resource-registry.ts +209 -0
  515. package/src/history/snapshot-store.ts +103 -0
  516. package/src/history/source-history-backend.ts +546 -0
  517. package/src/history/types.ts +124 -0
  518. package/src/hmr-registration-group.ts +67 -0
  519. package/src/hmr-stable-react-context.ts +23 -0
  520. package/src/hotkeys.ts +188 -0
  521. package/src/inference-diagnostics.ts +69 -0
  522. package/src/initial-project.ts +80 -0
  523. package/src/inspection/active-subject.ts +578 -0
  524. package/src/inspection/active-surface.ts +142 -0
  525. package/src/inspection/compose.ts +1064 -0
  526. package/src/inspection/display.ts +170 -0
  527. package/src/inspection/document-subject.ts +109 -0
  528. package/src/inspection/game-subject.ts +85 -0
  529. package/src/inspection/model.ts +542 -0
  530. package/src/inspection/null-subject.ts +115 -0
  531. package/src/inspection/serialize.ts +357 -0
  532. package/src/inspection/use-active-inspection.ts +180 -0
  533. package/src/inspector-presentation.ts +201 -0
  534. package/src/inspector-section-registry.ts +221 -0
  535. package/src/instance-source-actions.ts +163 -0
  536. package/src/instanced-presentation.ts +164 -0
  537. package/src/js-heap.ts +71 -0
  538. package/src/key-actions.ts +91 -0
  539. package/src/keymap-presets.ts +401 -0
  540. package/src/layout-policy.ts +31 -0
  541. package/src/learn-links.ts +73 -0
  542. package/src/light-explorer-model.ts +134 -0
  543. package/src/live-canvas-frame.ts +55 -0
  544. package/src/live-document.ts +279 -0
  545. package/src/live-module-source.ts +230 -0
  546. package/src/live-session-registry.ts +220 -0
  547. package/src/live-transition.ts +633 -0
  548. package/src/manifest-project.ts +107 -0
  549. package/src/model-thumbnail.ts +523 -0
  550. package/src/native-selection-style.ts +202 -0
  551. package/src/object3d-document-write-policy.ts +137 -0
  552. package/src/packaged-runtime.ts +108 -0
  553. package/src/palettes/maya.palette.json +57 -0
  554. package/src/palettes/substance.palette.json +57 -0
  555. package/src/pasteboard-module.ts +81 -0
  556. package/src/performance-profiler.ts +367 -0
  557. package/src/performance-sources.ts +69 -0
  558. package/src/play-boot-phase.ts +145 -0
  559. package/src/presentation-surface.ts +248 -0
  560. package/src/project-adapter.ts +1143 -0
  561. package/src/project-asset-refresh.ts +26 -0
  562. package/src/project-declaration-refresh.ts +31 -0
  563. package/src/project-local-state.ts +118 -0
  564. package/src/project-manager.ts +243 -0
  565. package/src/project-module-changes.ts +163 -0
  566. package/src/project-module-split.ts +266 -0
  567. package/src/project-provenance.ts +115 -0
  568. package/src/project-ready.ts +42 -0
  569. package/src/project-session-reset.ts +67 -0
  570. package/src/project-shape.ts +68 -0
  571. package/src/project-tool-discovery.ts +66 -0
  572. package/src/project-tools.ts +107 -0
  573. package/src/project-work-types.ts +149 -0
  574. package/src/projection/three.ts +898 -0
  575. package/src/projection/types.ts +44 -0
  576. package/src/readiness.ts +113 -0
  577. package/src/reflection-probe-helper.ts +142 -0
  578. package/src/reported-play-state.ts +90 -0
  579. package/src/resolve-relative-specifier.ts +33 -0
  580. package/src/scene-document-plan.ts +315 -0
  581. package/src/scene-framing.ts +315 -0
  582. package/src/scene-live-open.ts +210 -0
  583. package/src/scene-view-fog.ts +89 -0
  584. package/src/scoped-game-css.ts +152 -0
  585. package/src/session-orphan-record.ts +193 -0
  586. package/src/session-tombstone.ts +126 -0
  587. package/src/settings/settings-provider.ts +82 -0
  588. package/src/settings-store.ts +345 -0
  589. package/src/shared-view-restore.ts +42 -0
  590. package/src/shell-store-door.ts +45 -0
  591. package/src/source-conflict.ts +122 -0
  592. package/src/spatial-handle-visuals.ts +332 -0
  593. package/src/stage-context.ts +341 -0
  594. package/src/stage-store-registry.ts +63 -0
  595. package/src/stale-chunk-recovery.ts +34 -0
  596. package/src/state-report-deferral.ts +73 -0
  597. package/src/storage/host-files-storage.ts +97 -0
  598. package/src/storage/http-storage.ts +174 -0
  599. package/src/storage/index.ts +75 -0
  600. package/src/storage/mem-storage.ts +149 -0
  601. package/src/storage/path-lock.ts +44 -0
  602. package/src/storage/paths.ts +26 -0
  603. package/src/storage/types.ts +116 -0
  604. package/src/stories/StoryComponentThumbnail.tsx +184 -0
  605. package/src/stories/StoryPreviewMount.tsx +306 -0
  606. package/src/stories/component-content-source.tsx +106 -0
  607. package/src/stories/component-states-source.ts +78 -0
  608. package/src/stories/compose-project-stories.ts +255 -0
  609. package/src/stories/pixi-story-model.ts +30 -0
  610. package/src/stories/prefabs-finder.ts +54 -0
  611. package/src/stories/prefabs-from-stories.ts +182 -0
  612. package/src/stories/project-story-discovery.ts +78 -0
  613. package/src/stories/project-story-regions.ts +24 -0
  614. package/src/stories/story-actions.ts +54 -0
  615. package/src/stories/story-capture-command.ts +124 -0
  616. package/src/stories/story-capture.ts +584 -0
  617. package/src/stories/story-declared-medium.ts +126 -0
  618. package/src/stories/story-discovery.ts +176 -0
  619. package/src/stories/story-document-openers.ts +36 -0
  620. package/src/stories/story-dom-runtime.ts +78 -0
  621. package/src/stories/story-grouping.ts +111 -0
  622. package/src/stories/story-lane.ts +88 -0
  623. package/src/stories/story-mount-turn.ts +27 -0
  624. package/src/stories/story-opener.ts +260 -0
  625. package/src/stories/story-pixi-preview.ts +408 -0
  626. package/src/stories/story-presentation.ts +215 -0
  627. package/src/stories/story-registry.ts +517 -0
  628. package/src/stories/story-three-preview.ts +807 -0
  629. package/src/stories/three-story-model.ts +96 -0
  630. package/src/story-three-preview-runtime.ts +56 -0
  631. package/src/surface-keyboard.ts +112 -0
  632. package/src/surface-state.ts +124 -0
  633. package/src/tab-bootstrap.js +628 -0
  634. package/src/tab-census.ts +198 -0
  635. package/src/tab-lifecycle-client.ts +196 -0
  636. package/src/theme-library.ts +844 -0
  637. package/src/theme-preference.ts +378 -0
  638. package/src/theme.css +3437 -0
  639. package/src/three-viewport/bone-selection-highlight.ts +119 -0
  640. package/src/three-viewport/camera-fit.ts +41 -0
  641. package/src/three-viewport/interactive-renderer.ts +132 -0
  642. package/src/three-viewport/selection-brackets.ts +310 -0
  643. package/src/three-viewport/selection-outline.ts +183 -0
  644. package/src/three-viewport/skeleton-helper.ts +61 -0
  645. package/src/three-viewport/source-color.ts +167 -0
  646. package/src/three-viewport/studio-environment.ts +96 -0
  647. package/src/three-viewport-presentation.ts +23 -0
  648. package/src/tool-contribution-play.ts +74 -0
  649. package/src/tool-loader.ts +1798 -0
  650. package/src/transform-mode-request.ts +57 -0
  651. package/src/transient-hint.ts +78 -0
  652. package/src/trigger-volume-helper.ts +116 -0
  653. package/src/ui-source/adapter-region-includes.ts +241 -0
  654. package/src/ui-source/ensure-import.ts +132 -0
  655. package/src/ui-source/file-region-resolver.ts +302 -0
  656. package/src/ui-source/inspect.ts +775 -0
  657. package/src/ui-source/oid-transform.ts +1845 -0
  658. package/src/ui-source/plan-csf-story.ts +196 -0
  659. package/src/ui-source/plan-extract-component.ts +421 -0
  660. package/src/ui-source/plan-fork-component.ts +621 -0
  661. package/src/ui-source/plan-named-style.ts +95 -0
  662. package/src/ui-source/plan-source-edit.ts +353 -0
  663. package/src/ui-source/r3f-contract-resolver.ts +327 -0
  664. package/src/ui-source/r3f-diagnostic-index.ts +165 -0
  665. package/src/ui-source/r3f-environment-binding.ts +133 -0
  666. package/src/ui-source/r3f-joint-binding.ts +251 -0
  667. package/src/ui-source/r3f-lod-binding.ts +91 -0
  668. package/src/ui-source/r3f-particle-binding.ts +235 -0
  669. package/src/ui-source/r3f-physics-binding.ts +483 -0
  670. package/src/ui-source/r3f-project-contracts.ts +444 -0
  671. package/src/ui-source/relative-import-specifier.ts +34 -0
  672. package/src/ui-source/reparent-guard.ts +544 -0
  673. package/src/ui-source/source-edit-request.ts +97 -0
  674. package/src/ui-source/source-write-backend.ts +618 -0
  675. package/src/ui-source/syntactic-prop-specs.ts +296 -0
  676. package/src/ui-source/tier-source-write-backend.ts +279 -0
  677. package/src/ui-source/ts-ast.ts +171 -0
  678. package/src/ui-source/utility-class-support.ts +169 -0
  679. package/src/ui-source/write-component-default.ts +133 -0
  680. package/src/ui-source/writer.ts +1989 -0
  681. package/src/viewport-activation-timings.ts +840 -0
  682. package/src/viewport-authoring-policy.ts +186 -0
  683. package/src/viewport-controls-hint.ts +57 -0
  684. package/src/viewport-door.ts +237 -0
  685. package/src/viewport-shading-boundary.ts +12 -0
  686. package/src/vite-error-surface.ts +141 -0
  687. package/src/wait-until.ts +37 -0
  688. package/src/workspace-areas.ts +156 -0
  689. package/src/workspace-aux-commands.ts +11 -0
  690. package/src/workspace-available-documents.ts +127 -0
  691. package/src/workspace-core-utilities.ts +31 -0
  692. package/src/workspace-document-ids.ts +59 -0
  693. package/src/workspace-document-registry.ts +612 -0
  694. package/src/workspace-document-restore.ts +145 -0
  695. package/src/workspace-host-commands.ts +141 -0
  696. package/src/workspace-persistence-gate.ts +40 -0
  697. package/src/workspace-play-utilities.ts +44 -0
  698. package/src/workspace-presets.ts +425 -0
  699. package/src/workspace-regions.ts +294 -0
  700. package/src/workspace-state-persistence.ts +536 -0
  701. package/src/workspace-static-panels.ts +73 -0
  702. package/src/workspace-status-registry.ts +121 -0
  703. package/src/workspace-style.ts +239 -0
  704. package/src/workspace-utility-commands.ts +74 -0
  705. package/src/workspace-utility-registry.ts +263 -0
  706. package/src/workspace-viewport-rect.ts +97 -0
  707. package/src/world-adoption.ts +115 -0
  708. package/src/world-document-routing.ts +104 -0
  709. package/vite-plugin-creation-site-write.ts +184 -0
  710. package/vite-plugin-creation-site.ts +80 -0
  711. package/vite-plugin-game-static.ts +303 -0
  712. package/vite-plugin-module-doorways.ts +336 -0
  713. package/vite-plugin-product-contributions.ts +197 -0
  714. package/vite-plugin-project-game-static.ts +125 -0
  715. package/vite-plugin-project-jsx-js.ts +65 -0
  716. package/vite-plugin-project-root-absolute-assets.ts +359 -0
  717. package/vite-plugin-shared-react.ts +420 -0
  718. package/vite-plugin-shared-three.ts +203 -0
  719. package/vite-plugin-ui-oid.ts +2106 -0
@@ -0,0 +1,174 @@
1
+ /**
2
+ * Server-backed `StorageBackend` for the local (Node) editor.
3
+ *
4
+ * A thin adapter over the editor server's existing routes — it changes nothing
5
+ * about how the local editor talks to disk, it just presents that surface behind
6
+ * the shared interface. The backend is rooted at the project's `public/` folder,
7
+ * matching the server's `/__editor/assets` (list) and `/__editor/save-file`
8
+ * (write) routes; reads come from Vite's `/@fs/` static serving.
9
+ *
10
+ * Route mapping (paths are relative to `public/`):
11
+ * list → GET /__editor/assets?dir → { entries: [{name,type,size,mtime}] }
12
+ * write → POST /__editor/save-file ({path, content, encoding?})
13
+ * read → GET /@fs/{projectRoot}/public/{path}
14
+ * watch → EventSource /__editor/events (chokidar-backed)
15
+ *
16
+ * The CLI control channel, native dialogs, `export`, online asset library, and
17
+ * project/editor-state persistence are NOT file operations and live outside this
18
+ * interface (see types.ts and editor-api.ts).
19
+ */
20
+
21
+ import { bytesToBase64 } from '../bytes-codec';
22
+ import { assertEditorServerAnswered, editorServerJson } from '../editor-server-response';
23
+ import { sourceMutationAttribution } from '../editor-session-attribution';
24
+ import { handleProjectMutationFailure } from '../source-conflict';
25
+ import { dirAndBase, normalize } from './paths';
26
+ import type { DirEntry, Stat, StorageBackend, WatchCallback, WatchEvent } from './types';
27
+
28
+ const BASE = '/__editor';
29
+
30
+ interface ServerAssetEntry {
31
+ name: string;
32
+ type: 'file' | 'directory';
33
+ size: number;
34
+ mtime: number;
35
+ }
36
+
37
+ export class HttpStorage implements StorageBackend {
38
+ readonly id = 'http';
39
+
40
+ /** Absolute project root on the server (used for /@fs reads). */
41
+ constructor(private readonly projectRoot: string) {}
42
+
43
+ async read(path: string): Promise<string> {
44
+ const res = await fetch(`/@fs/${this.projectRoot}/public/${normalize(path)}`);
45
+ if (!res.ok) throw new Error(`HttpStorage.read '${normalize(path)}': HTTP ${res.status}`);
46
+ return res.text();
47
+ }
48
+
49
+ async readBytes(path: string): Promise<Uint8Array> {
50
+ const res = await fetch(`/@fs/${this.projectRoot}/public/${normalize(path)}`);
51
+ if (!res.ok) throw new Error(`HttpStorage.readBytes '${normalize(path)}': HTTP ${res.status}`);
52
+ return new Uint8Array(await res.arrayBuffer());
53
+ }
54
+
55
+ async write(path: string, data: string | Uint8Array): Promise<void> {
56
+ const body =
57
+ typeof data === 'string'
58
+ ? { path: normalize(path), content: data, ...sourceMutationAttribution() }
59
+ : {
60
+ path: normalize(path),
61
+ content: bytesToBase64(data),
62
+ encoding: 'base64' as const,
63
+ ...sourceMutationAttribution(),
64
+ };
65
+ const res = await fetch(`${BASE}/save-file`, {
66
+ method: 'POST',
67
+ headers: { 'Content-Type': 'application/json' },
68
+ body: JSON.stringify(body),
69
+ });
70
+ // This is the AUTOSAVE path. `!res.ok` alone let a page fallback report
71
+ // every save as written, so the editor kept showing saved work that no
72
+ // server had ever received.
73
+ assertEditorServerAnswered(res, `Write ${normalize(path)} failed`);
74
+ if (!res.ok) {
75
+ await handleProjectMutationFailure(res, {
76
+ label: `Write ${normalize(path)}`,
77
+ attempted: {
78
+ [`public/${normalize(path)}`]:
79
+ typeof data === 'string' ? data : `[${data.byteLength} binary bytes]`,
80
+ },
81
+ reapply: () => this.write(path, data),
82
+ });
83
+ }
84
+ }
85
+
86
+ async writeIfAbsent(path: string, data: string | Uint8Array): Promise<boolean> {
87
+ // Browser adaptation never uses HttpStorage: the Node endpoint owns its
88
+ // true `wx` write. Keep the interface honest for generic callers.
89
+ if (await this.exists(path)) return false;
90
+ await this.write(path, data);
91
+ return true;
92
+ }
93
+
94
+ async list(dir: string): Promise<DirEntry[]> {
95
+ const res = await fetch(`${BASE}/assets?${new URLSearchParams({ dir: normalize(dir) })}`);
96
+ const { entries } = await editorServerJson<{ entries: ServerAssetEntry[] }>(
97
+ res,
98
+ `HttpStorage.list '${normalize(dir)}' failed`,
99
+ );
100
+ return entries.map((e) => {
101
+ const out: DirEntry = {
102
+ name: e.name,
103
+ path: normalize(dir ? `${dir}/${e.name}` : e.name),
104
+ type: e.type === 'directory' ? 'dir' : 'file',
105
+ mtime: e.mtime,
106
+ };
107
+ if (e.type === 'file') out.size = e.size;
108
+ out.mtime = e.mtime;
109
+ return out;
110
+ });
111
+ }
112
+
113
+ async stat(path: string): Promise<Stat | null> {
114
+ // The server exposes listings, not a per-path stat. Derive from the parent
115
+ // listing — sufficient for the editor's needs (existence + type + size).
116
+ const [dir, base] = dirAndBase(path);
117
+ if (!base) return { path: '', type: 'dir', size: 0, mtime: 0 };
118
+ let entries: DirEntry[];
119
+ try {
120
+ entries = await this.list(dir);
121
+ } catch {
122
+ return null;
123
+ }
124
+ const hit = entries.find((e) => e.name === base);
125
+ return hit
126
+ ? { path: hit.path, type: hit.type, size: hit.size ?? 0, mtime: hit.mtime ?? 0 }
127
+ : null;
128
+ }
129
+
130
+ async exists(path: string): Promise<boolean> {
131
+ return (await this.stat(path)) !== null;
132
+ }
133
+
134
+ async mkdir(path: string): Promise<void> {
135
+ // The server has no empty-dir route; directories materialize when their
136
+ // first file is written (save-file creates parents). No-op here.
137
+ void path;
138
+ }
139
+
140
+ async remove(path: string): Promise<void> {
141
+ const res = await fetch(`${BASE}/save-file`, {
142
+ method: 'POST',
143
+ headers: { 'Content-Type': 'application/json' },
144
+ body: JSON.stringify({ path: normalize(path), delete: true, ...sourceMutationAttribution() }),
145
+ });
146
+ assertEditorServerAnswered(res, `Delete ${normalize(path)} failed`);
147
+ if (!res.ok) {
148
+ await handleProjectMutationFailure(res, {
149
+ label: `Delete ${normalize(path)}`,
150
+ attempted: { [`public/${normalize(path)}`]: null },
151
+ reapply: () => this.remove(path),
152
+ });
153
+ }
154
+ }
155
+
156
+ watch(callback: WatchCallback): () => void {
157
+ const source = new EventSource(`${BASE}/events`);
158
+ const handler = (ev: MessageEvent) => {
159
+ try {
160
+ const data = JSON.parse(ev.data) as { type?: string; file?: string; path?: string };
161
+ const path = data.path ?? data.file;
162
+ if (!path) return;
163
+ callback({ type: (data.type as WatchEvent['type']) ?? 'update', path: normalize(path) });
164
+ } catch {
165
+ // Ignore non-JSON keepalive frames.
166
+ }
167
+ };
168
+ source.addEventListener('message', handler);
169
+ return () => {
170
+ source.removeEventListener('message', handler);
171
+ source.close();
172
+ };
173
+ }
174
+ }
@@ -0,0 +1,75 @@
1
+ /**
2
+ * Storage backend selection — the `public/`-rooted file interface the editor's
3
+ * asset surfaces read and write through.
4
+ *
5
+ * ONE TIER, two implementations, and the second is a decorator:
6
+ * - `HttpStorage` — the session's own `/__editor/*` routes.
7
+ * - `HostFilesStorage` — the same view, written through `EditorHost.files`
8
+ * so a write is the WORKBENCH's own (U5).
9
+ * `MemStorage` is the design system's fixture backend and nothing else.
10
+ *
11
+ * Upstream code depends only on `StorageBackend` from `./types` and obtains
12
+ * an instance via `getStorageBackend()`.
13
+ */
14
+
15
+ import { getProjectDefinePath } from '../editor-mode';
16
+ import { filesProviderInstalled } from '../files/file-provider';
17
+ import { HostFilesStorage } from './host-files-storage';
18
+ import { HttpStorage } from './http-storage';
19
+ import type { StorageBackend } from './types';
20
+
21
+ export { HttpStorage } from './http-storage';
22
+ export { MemStorage } from './mem-storage';
23
+ export type { DirEntry, HostCapabilities, Stat, StorageBackend, WatchEvent } from './types';
24
+
25
+ let _backend: StorageBackend | null = null;
26
+ /** The tier's own backend, kept beside the active one so the frame decorator
27
+ * never becomes its own delegate — see {@link tierStorageBackend}. */
28
+ let _tier: StorageBackend | null = null;
29
+
30
+ /**
31
+ * THE TIER'S OWN backend — never the frame decorator, and the only thing the
32
+ * file door's host fill is allowed to stand on.
33
+ *
34
+ * Without this the fill would recurse: `projectFiles.read` falls back to
35
+ * `getStorageBackend()`, which under the frame is `HostFilesStorage`, whose
36
+ * `read` is `projectFiles.read`. One function, so the cycle cannot be written
37
+ * by accident.
38
+ */
39
+ export function tierStorageBackend(): StorageBackend {
40
+ if (_backend && !(_backend instanceof HostFilesStorage)) return _backend;
41
+ if (!_tier) _tier = new HttpStorage(getProjectDefinePath());
42
+ return _tier;
43
+ }
44
+
45
+ /**
46
+ * The active storage backend: the session's own, wrapped by the frame's file
47
+ * door once its provider has landed.
48
+ *
49
+ * UNDER THE CODE-OSS FRAME the file system is the WORKBENCH'S, not the
50
+ * session's (U5; ARCHITECTURE-CORE §The core is Code-OSS, "the storage
51
+ * backends → file system providers"). `HostFilesStorage` is the `public/`
52
+ * view onto `EditorHost.files`, so an asset write is the workbench's own write
53
+ * on the URI it already holds — the same property that closed U4's redo open
54
+ * for source files. Everything the file door does not carry (remove, mkdir,
55
+ * stat, list, watch) stays this tier's, which is why the decorator keeps it
56
+ * rather than replacing it.
57
+ *
58
+ * Read at FIRST USE rather than at module load: the bridge takes ownership
59
+ * before the editor mounts, but the provider arrives with the contribution's
60
+ * own services, after — see `files/file-provider.ts`.
61
+ */
62
+ export function getStorageBackend(): StorageBackend {
63
+ if (_backend) return _backend;
64
+ const tier = tierStorageBackend();
65
+ _backend = filesProviderInstalled() ? new HostFilesStorage(tier) : tier;
66
+ return _backend;
67
+ }
68
+
69
+ /** Override the active backend (the design system's fixture). */
70
+ export function setStorageBackend(backend: StorageBackend): void {
71
+ _backend = backend;
72
+ // An explicitly installed backend REPLACES the tier, so the file door's host
73
+ // fill stands on it too rather than on a stale one it would otherwise hold.
74
+ if (!(backend instanceof HostFilesStorage)) _tier = backend;
75
+ }
@@ -0,0 +1,149 @@
1
+ /**
2
+ * Pure in-memory `StorageBackend` — a virtual filesystem backed by a `Map`.
3
+ *
4
+ * Nothing touches disk; files live as bytes in JS and vanish on reload. The
5
+ * most "virtual" of the backends, and the simplest — the design system's
6
+ * fixture (`design-system-stories/fixtures/editor-runtime.tsx`) is what uses
7
+ * it: a story needs a project-shaped backend and must write nothing.
8
+ *
9
+ * Implements the same interface as every other backend, so it is a drop-in via
10
+ * `setStorageBackend(new MemStorage())`.
11
+ */
12
+
13
+ import { dirAndBase, normalize } from './paths';
14
+ import type { DirEntry, Stat, StorageBackend, WatchCallback, WatchEvent } from './types';
15
+
16
+ type Node = { type: 'file'; data: Uint8Array; mtime: number } | { type: 'dir'; mtime: number };
17
+
18
+ export class MemStorage implements StorageBackend {
19
+ readonly id = 'mem';
20
+
21
+ /** Normalized path → node. The root (`''`) is implicit. */
22
+ private readonly nodes = new Map<string, Node>();
23
+ private readonly watchers = new Set<WatchCallback>();
24
+
25
+ /** Optionally seed the VFS from a `{ path: contents }` map. */
26
+ constructor(seed?: Record<string, string | Uint8Array>) {
27
+ if (seed) for (const [path, data] of Object.entries(seed)) this.writeSync(path, data);
28
+ }
29
+
30
+ private emit(event: WatchEvent): void {
31
+ for (const cb of this.watchers) cb(event);
32
+ }
33
+
34
+ /** Ensure every ancestor directory of `path` exists. */
35
+ private ensureParents(path: string): void {
36
+ const parts = normalize(path).split('/');
37
+ parts.pop();
38
+ let cur = '';
39
+ for (const part of parts) {
40
+ cur = cur ? `${cur}/${part}` : part;
41
+ if (this.nodes.get(cur)?.type !== 'dir') this.nodes.set(cur, { type: 'dir', mtime: now() });
42
+ }
43
+ }
44
+
45
+ private writeSync(path: string, data: string | Uint8Array): boolean {
46
+ const norm = normalize(path);
47
+ this.ensureParents(norm);
48
+ const existed = this.nodes.get(norm)?.type === 'file';
49
+ const bytes = typeof data === 'string' ? new TextEncoder().encode(data) : new Uint8Array(data);
50
+ this.nodes.set(norm, { type: 'file', data: bytes, mtime: now() });
51
+ return existed;
52
+ }
53
+
54
+ async read(path: string): Promise<string> {
55
+ return new TextDecoder().decode(await this.readBytes(path));
56
+ }
57
+
58
+ async readBytes(path: string): Promise<Uint8Array> {
59
+ const node = this.nodes.get(normalize(path));
60
+ if (node?.type !== 'file')
61
+ throw new Error(`MemStorage.read: no such file '${normalize(path)}'`);
62
+ // Reads own their bytes, just like File/HTTP backends. Asset serving
63
+ // transfers this buffer to a worker; sharing the stored buffer would
64
+ // detach the file itself and break every subsequent read.
65
+ return node.data.slice();
66
+ }
67
+
68
+ async write(path: string, data: string | Uint8Array): Promise<void> {
69
+ const existed = this.writeSync(path, data);
70
+ this.emit({ type: existed ? 'update' : 'create', path: normalize(path) });
71
+ }
72
+
73
+ async writeIfAbsent(path: string, data: string | Uint8Array): Promise<boolean> {
74
+ if (await this.exists(path)) return false;
75
+ this.writeSync(path, data);
76
+ this.emit({ type: 'create', path: normalize(path) });
77
+ return true;
78
+ }
79
+
80
+ async list(dir: string): Promise<DirEntry[]> {
81
+ const dn = normalize(dir);
82
+ if (dn !== '' && this.nodes.get(dn)?.type !== 'dir') {
83
+ throw new Error(`MemStorage.list: no such directory '${dn}'`);
84
+ }
85
+ const entries: DirEntry[] = [];
86
+ for (const [path, node] of this.nodes) {
87
+ const [parent, base] = dirAndBase(path);
88
+ if (parent !== dn || !base) continue;
89
+ const entry: DirEntry = {
90
+ name: base,
91
+ path,
92
+ type: node.type === 'dir' ? 'dir' : 'file',
93
+ mtime: node.mtime,
94
+ };
95
+ if (node.type === 'file') entry.size = node.data.length;
96
+ entry.mtime = node.mtime;
97
+ entries.push(entry);
98
+ }
99
+ entries.sort((a, b) => {
100
+ if (a.type !== b.type) return a.type === 'dir' ? -1 : 1;
101
+ return a.name.localeCompare(b.name);
102
+ });
103
+ return entries;
104
+ }
105
+
106
+ async stat(path: string): Promise<Stat | null> {
107
+ const norm = normalize(path);
108
+ if (norm === '') return { path: '', type: 'dir', size: 0, mtime: 0 };
109
+ const node = this.nodes.get(norm);
110
+ if (!node) return null;
111
+ return node.type === 'file'
112
+ ? { path: norm, type: 'file', size: node.data.length, mtime: node.mtime }
113
+ : { path: norm, type: 'dir', size: 0, mtime: node.mtime };
114
+ }
115
+
116
+ async exists(path: string): Promise<boolean> {
117
+ return (await this.stat(path)) !== null;
118
+ }
119
+
120
+ async mkdir(path: string): Promise<void> {
121
+ const norm = normalize(path);
122
+ if (!norm || this.nodes.get(norm)?.type === 'dir') return;
123
+ this.ensureParents(norm);
124
+ this.nodes.set(norm, { type: 'dir', mtime: now() });
125
+ this.emit({ type: 'create', path: norm });
126
+ }
127
+
128
+ async remove(path: string): Promise<void> {
129
+ const norm = normalize(path);
130
+ if (!norm) return;
131
+ let removed = false;
132
+ for (const key of [...this.nodes.keys()]) {
133
+ if (key === norm || key.startsWith(`${norm}/`)) {
134
+ this.nodes.delete(key);
135
+ removed = true;
136
+ }
137
+ }
138
+ if (removed) this.emit({ type: 'remove', path: norm });
139
+ }
140
+
141
+ watch(callback: WatchCallback): () => void {
142
+ this.watchers.add(callback);
143
+ return () => this.watchers.delete(callback);
144
+ }
145
+ }
146
+
147
+ function now(): number {
148
+ return Date.now();
149
+ }
@@ -0,0 +1,44 @@
1
+ /**
2
+ * The one cross-realm mutual exclusion a browser storage backend has:
3
+ * `navigator.locks`, keyed by backend id + path.
4
+ *
5
+ * Two callers matter and they MUST agree on the name, which is why this is a
6
+ * shared function rather than a string built at each site — and why the name is
7
+ * derived from the NORMALIZED path here rather than from whatever each caller
8
+ * happens to hold. Sharing the function is not enough on its own: one caller
9
+ * passes an already-normalized path and the other passes a module constant, so
10
+ * agreement used to rest on that constant being spelled in normalized form.
11
+ * Respell it as `/.vgai/assets.json` and the two names diverge, both locks are
12
+ * "held", and mutual exclusion is silently gone with nothing failing. Deriving
13
+ * the name from `normalize()` makes the agreement structural.
14
+ *
15
+ * Callers:
16
+ * - the asset ledger's `.lock` compare-and-delete
17
+ * (`../asset-workflow/asset-ledger-backend.ts`) — several steps that must
18
+ * not interleave with each other OR with the create above.
19
+ *
20
+ * Scope, stated exactly: Web Locks span every same-origin realm — the two
21
+ * tabs on one project that motivate the ledger lock in the first place — and
22
+ * nothing else. A writer that is not same-origin JS (a Node process
23
+ * reaching the same files, i.e. `HttpStorage` racing the CLI) is not serialized
24
+ * by this, and cannot be from the browser side.
25
+ *
26
+ * Absent in a non-secure context and in Node (tests): callers then get the bare
27
+ * operation, which is the same exclusivity the platform itself offers.
28
+ */
29
+ import { normalize } from './paths';
30
+
31
+ export function withPathLock<T>(
32
+ backendId: string,
33
+ path: string,
34
+ operation: () => Promise<T>,
35
+ ): Promise<T> {
36
+ const locks = globalThis.navigator?.locks;
37
+ if (!locks) return operation();
38
+ // `LockManager.request`'s DOM typing infers its result from the callback's
39
+ // literal return type (`(lock) => T`), so an async callback types as
40
+ // `Promise<Promise<T>>`. The platform awaits the returned promise before
41
+ // releasing the lock — that flattening is the documented behavior, not an
42
+ // assumption — so the settled value really is `T`.
43
+ return locks.request(`vgai:${backendId}:${normalize(path)}`, operation) as Promise<T>;
44
+ }
@@ -0,0 +1,26 @@
1
+ /**
2
+ * Path helpers for storage backends. Paths are POSIX-style, root-relative,
3
+ * '/'-separated, with no leading/trailing slashes.
4
+ */
5
+
6
+ /** Split a path into non-empty segments, collapsing `.` and redundant slashes. */
7
+ export function segments(path: string): string[] {
8
+ return path.split('/').filter((s) => s.length > 0 && s !== '.');
9
+ }
10
+
11
+ /** Normalize to a canonical root-relative path (`''` for the root). */
12
+ export function normalize(path: string): string {
13
+ return segments(path).join('/');
14
+ }
15
+
16
+ /** Split into `[parentDir, baseName]`. Root entries have `parent === ''`. */
17
+ export function dirAndBase(path: string): [string, string] {
18
+ const segs = segments(path);
19
+ const base = segs.pop() ?? '';
20
+ return [segs.join('/'), base];
21
+ }
22
+
23
+ /** Join path parts into a normalized path. */
24
+ export function join(...parts: string[]): string {
25
+ return normalize(parts.join('/'));
26
+ }
@@ -0,0 +1,116 @@
1
+ /**
2
+ * Backend-agnostic file interface for the editor.
3
+ *
4
+ * The editor and engine read/write project files through one `StorageBackend`
5
+ * and never learn which implementation is behind it — the session's own
6
+ * `/__editor/*` routes, the frame's file door over them, or the design
7
+ * system's in-memory fixture.
8
+ *
9
+ * Scope — this interface deliberately covers ONLY what reduces to file
10
+ * operations. Three editor concerns do not, and are handled elsewhere:
11
+ * - native folder dialogs / "reveal in OS file manager" → `HostCapabilities`
12
+ * - the `vgai` CLI control channel (SSE + command RPC) → server-only, dropped
13
+ * in a pure-browser editor
14
+ * - `export` / packaging (spawns a build) → a client-side bundler in-browser
15
+ *
16
+ * `watch` is part of the interface but its semantics are backend-specific: a
17
+ * server backend reports real filesystem events (chokidar); a browser backend
18
+ * has no OS file-change notifications, so it derives events from its OWN writes
19
+ * (in a server-less editor the editor is the only writer — which is exactly the
20
+ * signal HMR needs).
21
+ *
22
+ * Paths are POSIX-style, project-root-relative, '/'-separated, no leading slash
23
+ * (e.g. `src/scripts/components/spin.ts`).
24
+ */
25
+
26
+ export type NodeType = 'file' | 'dir';
27
+
28
+ export interface Stat {
29
+ /** Normalized, root-relative path. */
30
+ path: string;
31
+ type: NodeType;
32
+ /** Byte length for files; 0 for directories. */
33
+ size: number;
34
+ /** Last-modified time, epoch ms (0 if the backend cannot report it). */
35
+ mtime: number;
36
+ }
37
+
38
+ export interface DirEntry {
39
+ /** Base name (no slashes). */
40
+ name: string;
41
+ /** Normalized, root-relative path. */
42
+ path: string;
43
+ type: NodeType;
44
+ /** Byte length for files (omitted for directories). */
45
+ size?: number;
46
+ /** Last-modified time, epoch ms (omitted if the backend cannot report it). */
47
+ mtime?: number;
48
+ }
49
+
50
+ export type WatchEventType = 'create' | 'update' | 'remove';
51
+
52
+ export interface WatchEvent {
53
+ type: WatchEventType;
54
+ /** Normalized, root-relative path of the affected node. */
55
+ path: string;
56
+ }
57
+
58
+ export type WatchCallback = (event: WatchEvent) => void;
59
+
60
+ /**
61
+ * The one file interface every storage backend implements. All methods take and
62
+ * return normalized, root-relative POSIX paths.
63
+ */
64
+ export interface StorageBackend {
65
+ /** Stable identifier for the active backend (for diagnostics/feature flags). */
66
+ readonly id: string;
67
+
68
+ /** Read a UTF-8 text file. Rejects if the path is missing or is a directory. */
69
+ read(path: string): Promise<string>;
70
+ /** Read raw bytes. Rejects if the path is missing or is a directory. */
71
+ readBytes(path: string): Promise<Uint8Array>;
72
+
73
+ /** Write a file, creating parent directories as needed. Emits a watch event. */
74
+ write(path: string, data: string | Uint8Array): Promise<void>;
75
+ /**
76
+ * Create a new file without replacing an existing one. Returns false when
77
+ * the path already exists. Browser handle APIs have no OS-level O_EXCL;
78
+ * HandleStorage serializes same-origin writers and rechecks at handle
79
+ * acquisition, while an external process may still win the final race.
80
+ */
81
+ writeIfAbsent(path: string, data: string | Uint8Array): Promise<boolean>;
82
+
83
+ /** Shallow directory listing. Rejects if the path is missing or is a file. */
84
+ list(dir: string): Promise<DirEntry[]>;
85
+
86
+ /** Stat a node, or resolve to `null` if it does not exist. */
87
+ stat(path: string): Promise<Stat | null>;
88
+
89
+ /** Convenience existence check. */
90
+ exists(path: string): Promise<boolean>;
91
+
92
+ /** Recursively create a directory (no-op if it already exists). */
93
+ mkdir(path: string): Promise<void>;
94
+
95
+ /** Recursively remove a file or directory (no-op if missing). Emits an event. */
96
+ remove(path: string): Promise<void>;
97
+
98
+ /** Subscribe to change events. Returns an unsubscribe function. */
99
+ watch(callback: WatchCallback): () => void;
100
+ }
101
+
102
+ /**
103
+ * Non-file host capabilities, kept separate from `StorageBackend` because they
104
+ * do not reduce to path operations. A backend may implement none of these.
105
+ */
106
+ export interface HostCapabilities {
107
+ /**
108
+ * Prompt the user to choose a project root and return a backend rooted there.
109
+ * Browser: `showDirectoryPicker()` (Chromium). Resolves to `null` if the user
110
+ * cancels. Absent entirely where unsupported.
111
+ */
112
+ pickProjectRoot?(): Promise<StorageBackend | null>;
113
+
114
+ /** Reveal a path in the OS file manager. Absent in the browser. */
115
+ reveal?(path: string): Promise<void>;
116
+ }