@elytracms/studio 0.0.1

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 (558) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +3 -0
  3. package/convex/assets.ts +107 -0
  4. package/convex/auth.config.ts +15 -0
  5. package/convex/auth.ts +50 -0
  6. package/convex/cliTokens.ts +63 -0
  7. package/convex/cms.ts +174 -0
  8. package/convex/content.ts +316 -0
  9. package/convex/delivery.ts +266 -0
  10. package/convex/functions.ts +35 -0
  11. package/convex/graphs.ts +51 -0
  12. package/convex/guard.ts +67 -0
  13. package/convex/http.ts +30 -0
  14. package/convex/members.ts +83 -0
  15. package/convex/publishing.ts +102 -0
  16. package/convex/references.ts +168 -0
  17. package/convex/schema.ts +173 -0
  18. package/convex/sync.ts +322 -0
  19. package/convex/tsconfig.json +12 -0
  20. package/convex/users.ts +23 -0
  21. package/convex/webhooks.ts +85 -0
  22. package/dist/components/assets/asset-library.d.ts +14 -0
  23. package/dist/components/assets/asset-library.js +191 -0
  24. package/dist/components/assets/asset-library.js.map +1 -0
  25. package/dist/components/assets/asset-metadata.d.ts +34 -0
  26. package/dist/components/assets/asset-metadata.js +40 -0
  27. package/dist/components/assets/asset-metadata.js.map +1 -0
  28. package/dist/components/assets/asset-search.d.ts +7 -0
  29. package/dist/components/assets/asset-search.js +12 -0
  30. package/dist/components/assets/asset-search.js.map +1 -0
  31. package/dist/components/assets/asset-selection.d.ts +17 -0
  32. package/dist/components/assets/asset-selection.js +33 -0
  33. package/dist/components/assets/asset-selection.js.map +1 -0
  34. package/dist/components/assets/assets-store.d.ts +51 -0
  35. package/dist/components/assets/assets-store.js +153 -0
  36. package/dist/components/assets/assets-store.js.map +1 -0
  37. package/dist/components/auth-context.d.ts +38 -0
  38. package/dist/components/auth-context.js +88 -0
  39. package/dist/components/auth-context.js.map +1 -0
  40. package/dist/components/backend-gate.d.ts +19 -0
  41. package/dist/components/backend-gate.js +63 -0
  42. package/dist/components/backend-gate.js.map +1 -0
  43. package/dist/components/breadcrumb-context.d.ts +39 -0
  44. package/dist/components/breadcrumb-context.js +38 -0
  45. package/dist/components/breadcrumb-context.js.map +1 -0
  46. package/dist/components/builder/blocks-model.d.ts +80 -0
  47. package/dist/components/builder/blocks-model.js +181 -0
  48. package/dist/components/builder/blocks-model.js.map +1 -0
  49. package/dist/components/builder/blocks-panel.d.ts +44 -0
  50. package/dist/components/builder/blocks-panel.js +147 -0
  51. package/dist/components/builder/blocks-panel.js.map +1 -0
  52. package/dist/components/builder/builder-store.d.ts +69 -0
  53. package/dist/components/builder/builder-store.js +294 -0
  54. package/dist/components/builder/builder-store.js.map +1 -0
  55. package/dist/components/builder/canvas-stylesheet.d.ts +4 -0
  56. package/dist/components/builder/canvas-stylesheet.js +24 -0
  57. package/dist/components/builder/canvas-stylesheet.js.map +1 -0
  58. package/dist/components/builder/canvas.d.ts +8 -0
  59. package/dist/components/builder/canvas.js +723 -0
  60. package/dist/components/builder/canvas.js.map +1 -0
  61. package/dist/components/builder/clipboard-actions.d.ts +93 -0
  62. package/dist/components/builder/clipboard-actions.js +246 -0
  63. package/dist/components/builder/clipboard-actions.js.map +1 -0
  64. package/dist/components/builder/composition-field-editor.d.ts +11 -0
  65. package/dist/components/builder/composition-field-editor.js +150 -0
  66. package/dist/components/builder/composition-field-editor.js.map +1 -0
  67. package/dist/components/builder/composition-scope.d.ts +16 -0
  68. package/dist/components/builder/composition-scope.js +7 -0
  69. package/dist/components/builder/composition-scope.js.map +1 -0
  70. package/dist/components/builder/drag-session.d.ts +41 -0
  71. package/dist/components/builder/drag-session.js +51 -0
  72. package/dist/components/builder/drag-session.js.map +1 -0
  73. package/dist/components/builder/fixture-thumbnail.d.ts +18 -0
  74. package/dist/components/builder/fixture-thumbnail.js +97 -0
  75. package/dist/components/builder/fixture-thumbnail.js.map +1 -0
  76. package/dist/components/builder/inline-edit.d.ts +142 -0
  77. package/dist/components/builder/inline-edit.js +136 -0
  78. package/dist/components/builder/inline-edit.js.map +1 -0
  79. package/dist/components/builder/insert-context.d.ts +14 -0
  80. package/dist/components/builder/insert-context.js +65 -0
  81. package/dist/components/builder/insert-context.js.map +1 -0
  82. package/dist/components/builder/insert-menu.d.ts +9 -0
  83. package/dist/components/builder/insert-menu.js +9 -0
  84. package/dist/components/builder/insert-menu.js.map +1 -0
  85. package/dist/components/builder/layout-inspector.d.ts +14 -0
  86. package/dist/components/builder/layout-inspector.js +84 -0
  87. package/dist/components/builder/layout-inspector.js.map +1 -0
  88. package/dist/components/builder/node-factory.d.ts +17 -0
  89. package/dist/components/builder/node-factory.js +90 -0
  90. package/dist/components/builder/node-factory.js.map +1 -0
  91. package/dist/components/builder/page-tree.d.ts +3 -0
  92. package/dist/components/builder/page-tree.js +207 -0
  93. package/dist/components/builder/page-tree.js.map +1 -0
  94. package/dist/components/builder/property-inspector.d.ts +1 -0
  95. package/dist/components/builder/property-inspector.js +233 -0
  96. package/dist/components/builder/property-inspector.js.map +1 -0
  97. package/dist/components/builder/rich-text-toolbar.d.ts +4 -0
  98. package/dist/components/builder/rich-text-toolbar.js +104 -0
  99. package/dist/components/builder/rich-text-toolbar.js.map +1 -0
  100. package/dist/components/builder/spacing-handles.d.ts +22 -0
  101. package/dist/components/builder/spacing-handles.js +213 -0
  102. package/dist/components/builder/spacing-handles.js.map +1 -0
  103. package/dist/components/cms/asset-picker.d.ts +12 -0
  104. package/dist/components/cms/asset-picker.js +60 -0
  105. package/dist/components/cms/asset-picker.js.map +1 -0
  106. package/dist/components/cms/bulk-actions.d.ts +60 -0
  107. package/dist/components/cms/bulk-actions.js +95 -0
  108. package/dist/components/cms/bulk-actions.js.map +1 -0
  109. package/dist/components/cms/bulk-bar.d.ts +23 -0
  110. package/dist/components/cms/bulk-bar.js +26 -0
  111. package/dist/components/cms/bulk-bar.js.map +1 -0
  112. package/dist/components/cms/cell-edit.d.ts +91 -0
  113. package/dist/components/cms/cell-edit.js +144 -0
  114. package/dist/components/cms/cell-edit.js.map +1 -0
  115. package/dist/components/cms/cell.d.ts +29 -0
  116. package/dist/components/cms/cell.js +127 -0
  117. package/dist/components/cms/cell.js.map +1 -0
  118. package/dist/components/cms/cms-index.d.ts +8 -0
  119. package/dist/components/cms/cms-index.js +23 -0
  120. package/dist/components/cms/cms-index.js.map +1 -0
  121. package/dist/components/cms/cms-store.d.ts +188 -0
  122. package/dist/components/cms/cms-store.js +702 -0
  123. package/dist/components/cms/cms-store.js.map +1 -0
  124. package/dist/components/cms/collection-table.d.ts +6 -0
  125. package/dist/components/cms/collection-table.js +250 -0
  126. package/dist/components/cms/collection-table.js.map +1 -0
  127. package/dist/components/cms/collections-sidebar.d.ts +9 -0
  128. package/dist/components/cms/collections-sidebar.js +25 -0
  129. package/dist/components/cms/collections-sidebar.js.map +1 -0
  130. package/dist/components/cms/detail-editor.d.ts +7 -0
  131. package/dist/components/cms/detail-editor.js +386 -0
  132. package/dist/components/cms/detail-editor.js.map +1 -0
  133. package/dist/components/cms/doc-state.d.ts +13 -0
  134. package/dist/components/cms/doc-state.js +18 -0
  135. package/dist/components/cms/doc-state.js.map +1 -0
  136. package/dist/components/cms/document-editor-context.d.ts +48 -0
  137. package/dist/components/cms/document-editor-context.js +23 -0
  138. package/dist/components/cms/document-editor-context.js.map +1 -0
  139. package/dist/components/cms/editable-cell.d.ts +22 -0
  140. package/dist/components/cms/editable-cell.js +176 -0
  141. package/dist/components/cms/editable-cell.js.map +1 -0
  142. package/dist/components/cms/field-control.d.ts +8 -0
  143. package/dist/components/cms/field-control.js +149 -0
  144. package/dist/components/cms/field-control.js.map +1 -0
  145. package/dist/components/cms/filter-builder.d.ts +12 -0
  146. package/dist/components/cms/filter-builder.js +84 -0
  147. package/dist/components/cms/filter-builder.js.map +1 -0
  148. package/dist/components/cms/import-export.d.ts +6 -0
  149. package/dist/components/cms/import-export.js +33 -0
  150. package/dist/components/cms/import-export.js.map +1 -0
  151. package/dist/components/cms/new-page-dialog.d.ts +22 -0
  152. package/dist/components/cms/new-page-dialog.js +42 -0
  153. package/dist/components/cms/new-page-dialog.js.map +1 -0
  154. package/dist/components/cms/reference-confirm.d.ts +25 -0
  155. package/dist/components/cms/reference-confirm.js +124 -0
  156. package/dist/components/cms/reference-confirm.js.map +1 -0
  157. package/dist/components/cms/relation-picker.d.ts +16 -0
  158. package/dist/components/cms/relation-picker.js +47 -0
  159. package/dist/components/cms/relation-picker.js.map +1 -0
  160. package/dist/components/cms/use-cell-edit.d.ts +33 -0
  161. package/dist/components/cms/use-cell-edit.js +125 -0
  162. package/dist/components/cms/use-cell-edit.js.map +1 -0
  163. package/dist/components/cms/versions-model.d.ts +15 -0
  164. package/dist/components/cms/versions-model.js +23 -0
  165. package/dist/components/cms/versions-model.js.map +1 -0
  166. package/dist/components/cms/versions-pane.d.ts +14 -0
  167. package/dist/components/cms/versions-pane.js +86 -0
  168. package/dist/components/cms/versions-pane.js.map +1 -0
  169. package/dist/components/cms/view-bar.d.ts +11 -0
  170. package/dist/components/cms/view-bar.js +80 -0
  171. package/dist/components/cms/view-bar.js.map +1 -0
  172. package/dist/components/collab/collab-context.d.ts +34 -0
  173. package/dist/components/collab/collab-context.js +52 -0
  174. package/dist/components/collab/collab-context.js.map +1 -0
  175. package/dist/components/collab/collab-seed.d.ts +27 -0
  176. package/dist/components/collab/collab-seed.js +42 -0
  177. package/dist/components/collab/collab-seed.js.map +1 -0
  178. package/dist/components/components/component-detail.d.ts +9 -0
  179. package/dist/components/components/component-detail.js +30 -0
  180. package/dist/components/components/component-detail.js.map +1 -0
  181. package/dist/components/components/component-status.d.ts +10 -0
  182. package/dist/components/components/component-status.js +30 -0
  183. package/dist/components/components/component-status.js.map +1 -0
  184. package/dist/components/components/components-index.d.ts +8 -0
  185. package/dist/components/components/components-index.js +42 -0
  186. package/dist/components/components/components-index.js.map +1 -0
  187. package/dist/components/components/field-inspector.d.ts +9 -0
  188. package/dist/components/components/field-inspector.js +38 -0
  189. package/dist/components/components/field-inspector.js.map +1 -0
  190. package/dist/components/components/fixture-runner.d.ts +10 -0
  191. package/dist/components/components/fixture-runner.js +24 -0
  192. package/dist/components/components/fixture-runner.js.map +1 -0
  193. package/dist/components/components/registry-browser.d.ts +4 -0
  194. package/dist/components/components/registry-browser.js +64 -0
  195. package/dist/components/components/registry-browser.js.map +1 -0
  196. package/dist/components/current-user-menu.d.ts +13 -0
  197. package/dist/components/current-user-menu.js +31 -0
  198. package/dist/components/current-user-menu.js.map +1 -0
  199. package/dist/components/dev-login-badge.d.ts +9 -0
  200. package/dist/components/dev-login-badge.js +18 -0
  201. package/dist/components/dev-login-badge.js.map +1 -0
  202. package/dist/components/extensions/extensions-view.d.ts +7 -0
  203. package/dist/components/extensions/extensions-view.js +126 -0
  204. package/dist/components/extensions/extensions-view.js.map +1 -0
  205. package/dist/components/guards.d.ts +27 -0
  206. package/dist/components/guards.js +46 -0
  207. package/dist/components/guards.js.map +1 -0
  208. package/dist/components/inspector/inspector-sidebar.d.ts +26 -0
  209. package/dist/components/inspector/inspector-sidebar.js +17 -0
  210. package/dist/components/inspector/inspector-sidebar.js.map +1 -0
  211. package/dist/components/operation-error.d.ts +17 -0
  212. package/dist/components/operation-error.js +54 -0
  213. package/dist/components/operation-error.js.map +1 -0
  214. package/dist/components/playground-badge.d.ts +10 -0
  215. package/dist/components/playground-badge.js +19 -0
  216. package/dist/components/playground-badge.js.map +1 -0
  217. package/dist/components/project-list.d.ts +15 -0
  218. package/dist/components/project-list.js +52 -0
  219. package/dist/components/project-list.js.map +1 -0
  220. package/dist/components/project-session.d.ts +46 -0
  221. package/dist/components/project-session.js +107 -0
  222. package/dist/components/project-session.js.map +1 -0
  223. package/dist/components/project-switcher.d.ts +11 -0
  224. package/dist/components/project-switcher.js +44 -0
  225. package/dist/components/project-switcher.js.map +1 -0
  226. package/dist/components/references/builder-deep-link.d.ts +12 -0
  227. package/dist/components/references/builder-deep-link.js +53 -0
  228. package/dist/components/references/builder-deep-link.js.map +1 -0
  229. package/dist/components/references/references-panel.d.ts +17 -0
  230. package/dist/components/references/references-panel.js +66 -0
  231. package/dist/components/references/references-panel.js.map +1 -0
  232. package/dist/components/routes/redirect-chain.d.ts +9 -0
  233. package/dist/components/routes/redirect-chain.js +16 -0
  234. package/dist/components/routes/redirect-chain.js.map +1 -0
  235. package/dist/components/routes/redirect-manager.d.ts +13 -0
  236. package/dist/components/routes/redirect-manager.js +24 -0
  237. package/dist/components/routes/redirect-manager.js.map +1 -0
  238. package/dist/components/routes/route-list.d.ts +35 -0
  239. package/dist/components/routes/route-list.js +69 -0
  240. package/dist/components/routes/route-list.js.map +1 -0
  241. package/dist/components/routes/routes-shell.d.ts +14 -0
  242. package/dist/components/routes/routes-shell.js +68 -0
  243. package/dist/components/routes/routes-shell.js.map +1 -0
  244. package/dist/components/section-nav.d.ts +17 -0
  245. package/dist/components/section-nav.js +33 -0
  246. package/dist/components/section-nav.js.map +1 -0
  247. package/dist/components/section-state.d.ts +24 -0
  248. package/dist/components/section-state.js +78 -0
  249. package/dist/components/section-state.js.map +1 -0
  250. package/dist/components/section-surface.d.ts +31 -0
  251. package/dist/components/section-surface.js +46 -0
  252. package/dist/components/section-surface.js.map +1 -0
  253. package/dist/components/sections.d.ts +38 -0
  254. package/dist/components/sections.js +72 -0
  255. package/dist/components/sections.js.map +1 -0
  256. package/dist/components/settings-form.d.ts +10 -0
  257. package/dist/components/settings-form.js +17 -0
  258. package/dist/components/settings-form.js.map +1 -0
  259. package/dist/components/studio-context.d.ts +22 -0
  260. package/dist/components/studio-context.js +48 -0
  261. package/dist/components/studio-context.js.map +1 -0
  262. package/dist/components/studio-project-screen.d.ts +19 -0
  263. package/dist/components/studio-project-screen.js +195 -0
  264. package/dist/components/studio-project-screen.js.map +1 -0
  265. package/dist/components/studio-shell.d.ts +18 -0
  266. package/dist/components/studio-shell.js +64 -0
  267. package/dist/components/studio-shell.js.map +1 -0
  268. package/dist/components/theme-context.d.ts +17 -0
  269. package/dist/components/theme-context.js +26 -0
  270. package/dist/components/theme-context.js.map +1 -0
  271. package/dist/components/workspace-gate.d.ts +12 -0
  272. package/dist/components/workspace-gate.js +27 -0
  273. package/dist/components/workspace-gate.js.map +1 -0
  274. package/dist/components/workspace-projects.d.ts +13 -0
  275. package/dist/components/workspace-projects.js +18 -0
  276. package/dist/components/workspace-projects.js.map +1 -0
  277. package/dist/lib/assets/delete-asset.d.ts +34 -0
  278. package/dist/lib/assets/delete-asset.js +34 -0
  279. package/dist/lib/assets/delete-asset.js.map +1 -0
  280. package/dist/lib/assets/image-dimensions.d.ts +18 -0
  281. package/dist/lib/assets/image-dimensions.js +26 -0
  282. package/dist/lib/assets/image-dimensions.js.map +1 -0
  283. package/dist/lib/assets/index.d.ts +9 -0
  284. package/dist/lib/assets/index.js +10 -0
  285. package/dist/lib/assets/index.js.map +1 -0
  286. package/dist/lib/assets/upload-state.d.ts +53 -0
  287. package/dist/lib/assets/upload-state.js +59 -0
  288. package/dist/lib/assets/upload-state.js.map +1 -0
  289. package/dist/lib/assets/upload.d.ts +56 -0
  290. package/dist/lib/assets/upload.js +125 -0
  291. package/dist/lib/assets/upload.js.map +1 -0
  292. package/dist/lib/auth/auth-adapter.d.ts +57 -0
  293. package/dist/lib/auth/auth-adapter.js +13 -0
  294. package/dist/lib/auth/auth-adapter.js.map +1 -0
  295. package/dist/lib/auth/convex-auth-adapter.d.ts +39 -0
  296. package/dist/lib/auth/convex-auth-adapter.js +171 -0
  297. package/dist/lib/auth/convex-auth-adapter.js.map +1 -0
  298. package/dist/lib/auth/dev-auto-login-adapter.d.ts +25 -0
  299. package/dist/lib/auth/dev-auto-login-adapter.js +40 -0
  300. package/dist/lib/auth/dev-auto-login-adapter.js.map +1 -0
  301. package/dist/lib/auth/index.d.ts +28 -0
  302. package/dist/lib/auth/index.js +61 -0
  303. package/dist/lib/auth/index.js.map +1 -0
  304. package/dist/lib/auth/local-auth-adapter.d.ts +57 -0
  305. package/dist/lib/auth/local-auth-adapter.js +78 -0
  306. package/dist/lib/auth/local-auth-adapter.js.map +1 -0
  307. package/dist/lib/auth/route-guard.d.ts +33 -0
  308. package/dist/lib/auth/route-guard.js +51 -0
  309. package/dist/lib/auth/route-guard.js.map +1 -0
  310. package/dist/lib/auth-errors.d.ts +42 -0
  311. package/dist/lib/auth-errors.js +74 -0
  312. package/dist/lib/auth-errors.js.map +1 -0
  313. package/dist/lib/bindings/section-bindings.d.ts +24 -0
  314. package/dist/lib/bindings/section-bindings.js +9 -0
  315. package/dist/lib/bindings/section-bindings.js.map +1 -0
  316. package/dist/lib/clipboard/index.d.ts +7 -0
  317. package/dist/lib/clipboard/index.js +8 -0
  318. package/dist/lib/clipboard/index.js.map +1 -0
  319. package/dist/lib/clipboard/os-clipboard.d.ts +46 -0
  320. package/dist/lib/clipboard/os-clipboard.js +105 -0
  321. package/dist/lib/clipboard/os-clipboard.js.map +1 -0
  322. package/dist/lib/clipboard/paste-issues.d.ts +34 -0
  323. package/dist/lib/clipboard/paste-issues.js +67 -0
  324. package/dist/lib/clipboard/paste-issues.js.map +1 -0
  325. package/dist/lib/clipboard/paste-target.d.ts +20 -0
  326. package/dist/lib/clipboard/paste-target.js +28 -0
  327. package/dist/lib/clipboard/paste-target.js.map +1 -0
  328. package/dist/lib/cms/published-documents.d.ts +30 -0
  329. package/dist/lib/cms/published-documents.js +75 -0
  330. package/dist/lib/cms/published-documents.js.map +1 -0
  331. package/dist/lib/cms-views/index.d.ts +9 -0
  332. package/dist/lib/cms-views/index.js +10 -0
  333. package/dist/lib/cms-views/index.js.map +1 -0
  334. package/dist/lib/cms-views/selection.d.ts +29 -0
  335. package/dist/lib/cms-views/selection.js +46 -0
  336. package/dist/lib/cms-views/selection.js.map +1 -0
  337. package/dist/lib/cms-views/view-model.d.ts +192 -0
  338. package/dist/lib/cms-views/view-model.js +353 -0
  339. package/dist/lib/cms-views/view-model.js.map +1 -0
  340. package/dist/lib/cms-views/views-store.d.ts +70 -0
  341. package/dist/lib/cms-views/views-store.js +129 -0
  342. package/dist/lib/cms-views/views-store.js.map +1 -0
  343. package/dist/lib/data/collection-content.d.ts +105 -0
  344. package/dist/lib/data/collection-content.js +196 -0
  345. package/dist/lib/data/collection-content.js.map +1 -0
  346. package/dist/lib/data/data-store.d.ts +97 -0
  347. package/dist/lib/data/data-store.js +205 -0
  348. package/dist/lib/data/data-store.js.map +1 -0
  349. package/dist/lib/data/index.d.ts +4 -0
  350. package/dist/lib/data/index.js +8 -0
  351. package/dist/lib/data/index.js.map +1 -0
  352. package/dist/lib/data/providers.d.ts +143 -0
  353. package/dist/lib/data/providers.js +255 -0
  354. package/dist/lib/data/providers.js.map +1 -0
  355. package/dist/lib/data/sample-capture.d.ts +30 -0
  356. package/dist/lib/data/sample-capture.js +70 -0
  357. package/dist/lib/data/sample-capture.js.map +1 -0
  358. package/dist/lib/data/sources-store.d.ts +42 -0
  359. package/dist/lib/data/sources-store.js +120 -0
  360. package/dist/lib/data/sources-store.js.map +1 -0
  361. package/dist/lib/dnd/drop-rules.d.ts +219 -0
  362. package/dist/lib/dnd/drop-rules.js +257 -0
  363. package/dist/lib/dnd/drop-rules.js.map +1 -0
  364. package/dist/lib/dnd/gap-drag.d.ts +66 -0
  365. package/dist/lib/dnd/gap-drag.js +95 -0
  366. package/dist/lib/dnd/gap-drag.js.map +1 -0
  367. package/dist/lib/locale/binding-fallback.d.ts +28 -0
  368. package/dist/lib/locale/binding-fallback.js +66 -0
  369. package/dist/lib/locale/binding-fallback.js.map +1 -0
  370. package/dist/lib/locale/fallback.d.ts +43 -0
  371. package/dist/lib/locale/fallback.js +52 -0
  372. package/dist/lib/locale/fallback.js.map +1 -0
  373. package/dist/lib/locale/index.d.ts +6 -0
  374. package/dist/lib/locale/index.js +7 -0
  375. package/dist/lib/locale/index.js.map +1 -0
  376. package/dist/lib/locale/locale-store.d.ts +40 -0
  377. package/dist/lib/locale/locale-store.js +61 -0
  378. package/dist/lib/locale/locale-store.js.map +1 -0
  379. package/dist/lib/locale/locale-switcher.d.ts +10 -0
  380. package/dist/lib/locale/locale-switcher.js +24 -0
  381. package/dist/lib/locale/locale-switcher.js.map +1 -0
  382. package/dist/lib/locale/route-variant.d.ts +14 -0
  383. package/dist/lib/locale/route-variant.js +11 -0
  384. package/dist/lib/locale/route-variant.js.map +1 -0
  385. package/dist/lib/locale/use-studio-locale.d.ts +10 -0
  386. package/dist/lib/locale/use-studio-locale.js +8 -0
  387. package/dist/lib/locale/use-studio-locale.js.map +1 -0
  388. package/dist/lib/operations/asset-repository.d.ts +15 -0
  389. package/dist/lib/operations/asset-repository.js +56 -0
  390. package/dist/lib/operations/asset-repository.js.map +1 -0
  391. package/dist/lib/operations/cms-persistence.d.ts +35 -0
  392. package/dist/lib/operations/cms-persistence.js +75 -0
  393. package/dist/lib/operations/cms-persistence.js.map +1 -0
  394. package/dist/lib/operations/graph-commands.d.ts +140 -0
  395. package/dist/lib/operations/graph-commands.js +86 -0
  396. package/dist/lib/operations/graph-commands.js.map +1 -0
  397. package/dist/lib/operations/graph-persistence.d.ts +27 -0
  398. package/dist/lib/operations/graph-persistence.js +35 -0
  399. package/dist/lib/operations/graph-persistence.js.map +1 -0
  400. package/dist/lib/operations/index.d.ts +13 -0
  401. package/dist/lib/operations/index.js +14 -0
  402. package/dist/lib/operations/index.js.map +1 -0
  403. package/dist/lib/operations/operations-package.d.ts +6 -0
  404. package/dist/lib/operations/operations-package.js +7 -0
  405. package/dist/lib/operations/operations-package.js.map +1 -0
  406. package/dist/lib/operations/persist-queue.d.ts +16 -0
  407. package/dist/lib/operations/persist-queue.js +18 -0
  408. package/dist/lib/operations/persist-queue.js.map +1 -0
  409. package/dist/lib/operations/session-hydration.d.ts +84 -0
  410. package/dist/lib/operations/session-hydration.js +112 -0
  411. package/dist/lib/operations/session-hydration.js.map +1 -0
  412. package/dist/lib/operations/studio-operations.d.ts +59 -0
  413. package/dist/lib/operations/studio-operations.js +92 -0
  414. package/dist/lib/operations/studio-operations.js.map +1 -0
  415. package/dist/lib/persistence/backend-mode.d.ts +69 -0
  416. package/dist/lib/persistence/backend-mode.js +120 -0
  417. package/dist/lib/persistence/backend-mode.js.map +1 -0
  418. package/dist/lib/persistence/convex-adapter.d.ts +34 -0
  419. package/dist/lib/persistence/convex-adapter.js +681 -0
  420. package/dist/lib/persistence/convex-adapter.js.map +1 -0
  421. package/dist/lib/persistence/convex-blob-storage.d.ts +57 -0
  422. package/dist/lib/persistence/convex-blob-storage.js +97 -0
  423. package/dist/lib/persistence/convex-blob-storage.js.map +1 -0
  424. package/dist/lib/persistence/convex-client.d.ts +19 -0
  425. package/dist/lib/persistence/convex-client.js +40 -0
  426. package/dist/lib/persistence/convex-client.js.map +1 -0
  427. package/dist/lib/persistence/index.d.ts +30 -0
  428. package/dist/lib/persistence/index.js +60 -0
  429. package/dist/lib/persistence/index.js.map +1 -0
  430. package/dist/lib/persona/labels.d.ts +23 -0
  431. package/dist/lib/persona/labels.js +122 -0
  432. package/dist/lib/persona/labels.js.map +1 -0
  433. package/dist/lib/rail.d.ts +11 -0
  434. package/dist/lib/rail.js +26 -0
  435. package/dist/lib/rail.js.map +1 -0
  436. package/dist/lib/references/impact.d.ts +64 -0
  437. package/dist/lib/references/impact.js +62 -0
  438. package/dist/lib/references/impact.js.map +1 -0
  439. package/dist/lib/references/index.d.ts +7 -0
  440. package/dist/lib/references/index.js +8 -0
  441. package/dist/lib/references/index.js.map +1 -0
  442. package/dist/lib/references/reference-model.d.ts +125 -0
  443. package/dist/lib/references/reference-model.js +242 -0
  444. package/dist/lib/references/reference-model.js.map +1 -0
  445. package/dist/lib/references/references-store.d.ts +65 -0
  446. package/dist/lib/references/references-store.js +221 -0
  447. package/dist/lib/references/references-store.js.map +1 -0
  448. package/dist/lib/registry/index.d.ts +65 -0
  449. package/dist/lib/registry/index.js +114 -0
  450. package/dist/lib/registry/index.js.map +1 -0
  451. package/dist/lib/registry/preview.d.ts +15 -0
  452. package/dist/lib/registry/preview.js +110 -0
  453. package/dist/lib/registry/preview.js.map +1 -0
  454. package/dist/lib/registry/project-components.d.ts +16 -0
  455. package/dist/lib/registry/project-components.js +152 -0
  456. package/dist/lib/registry/project-components.js.map +1 -0
  457. package/dist/lib/routing/index.d.ts +10 -0
  458. package/dist/lib/routing/index.js +11 -0
  459. package/dist/lib/routing/index.js.map +1 -0
  460. package/dist/lib/routing/routing-analysis.d.ts +26 -0
  461. package/dist/lib/routing/routing-analysis.js +37 -0
  462. package/dist/lib/routing/routing-analysis.js.map +1 -0
  463. package/dist/lib/routing/routing-store.d.ts +50 -0
  464. package/dist/lib/routing/routing-store.js +72 -0
  465. package/dist/lib/routing/routing-store.js.map +1 -0
  466. package/dist/lib/starters/kit-session.d.ts +5 -0
  467. package/dist/lib/starters/kit-session.js +17 -0
  468. package/dist/lib/starters/kit-session.js.map +1 -0
  469. package/dist/lib/theme.d.ts +21 -0
  470. package/dist/lib/theme.js +32 -0
  471. package/dist/lib/theme.js.map +1 -0
  472. package/dist/lib/utils.d.ts +11 -0
  473. package/dist/lib/utils.js +28 -0
  474. package/dist/lib/utils.js.map +1 -0
  475. package/dist/lib/webhooks/config.d.ts +15 -0
  476. package/dist/lib/webhooks/config.js +64 -0
  477. package/dist/lib/webhooks/config.js.map +1 -0
  478. package/dist/lib/webhooks/dispatcher.d.ts +67 -0
  479. package/dist/lib/webhooks/dispatcher.js +61 -0
  480. package/dist/lib/webhooks/dispatcher.js.map +1 -0
  481. package/dist/lib/webhooks/index.d.ts +11 -0
  482. package/dist/lib/webhooks/index.js +10 -0
  483. package/dist/lib/webhooks/index.js.map +1 -0
  484. package/dist/lib/webhooks/signing.d.ts +15 -0
  485. package/dist/lib/webhooks/signing.js +24 -0
  486. package/dist/lib/webhooks/signing.js.map +1 -0
  487. package/dist/lib/webhooks/tags.d.ts +25 -0
  488. package/dist/lib/webhooks/tags.js +173 -0
  489. package/dist/lib/webhooks/tags.js.map +1 -0
  490. package/dist/lib/working-graph.d.ts +82 -0
  491. package/dist/lib/working-graph.js +113 -0
  492. package/dist/lib/working-graph.js.map +1 -0
  493. package/dist/lib/workspace/index.d.ts +109 -0
  494. package/dist/lib/workspace/index.js +206 -0
  495. package/dist/lib/workspace/index.js.map +1 -0
  496. package/dist/lib/workspace/switcher-source.d.ts +39 -0
  497. package/dist/lib/workspace/switcher-source.js +23 -0
  498. package/dist/lib/workspace/switcher-source.js.map +1 -0
  499. package/dist/lib/workspace/workspace-source.d.ts +47 -0
  500. package/dist/lib/workspace/workspace-source.js +67 -0
  501. package/dist/lib/workspace/workspace-source.js.map +1 -0
  502. package/dist/router/index.d.ts +32 -0
  503. package/dist/router/index.js +32 -0
  504. package/dist/router/index.js.map +1 -0
  505. package/dist/router/match.d.ts +75 -0
  506. package/dist/router/match.js +87 -0
  507. package/dist/router/match.js.map +1 -0
  508. package/dist/router/search.d.ts +22 -0
  509. package/dist/router/search.js +16 -0
  510. package/dist/router/search.js.map +1 -0
  511. package/dist/ui/avatar.d.ts +17 -0
  512. package/dist/ui/avatar.js +38 -0
  513. package/dist/ui/avatar.js.map +1 -0
  514. package/dist/ui/badge.d.ts +9 -0
  515. package/dist/ui/badge.js +23 -0
  516. package/dist/ui/badge.js.map +1 -0
  517. package/dist/ui/button.d.ts +11 -0
  518. package/dist/ui/button.js +30 -0
  519. package/dist/ui/button.js.map +1 -0
  520. package/dist/ui/card.d.ts +11 -0
  521. package/dist/ui/card.js +23 -0
  522. package/dist/ui/card.js.map +1 -0
  523. package/dist/ui/dialog.d.ts +12 -0
  524. package/dist/ui/dialog.js +27 -0
  525. package/dist/ui/dialog.js.map +1 -0
  526. package/dist/ui/dropdown-menu.d.ts +15 -0
  527. package/dist/ui/dropdown-menu.js +24 -0
  528. package/dist/ui/dropdown-menu.js.map +1 -0
  529. package/dist/ui/field.d.ts +15 -0
  530. package/dist/ui/field.js +14 -0
  531. package/dist/ui/field.js.map +1 -0
  532. package/dist/ui/index.d.ts +14 -0
  533. package/dist/ui/index.js +15 -0
  534. package/dist/ui/index.js.map +1 -0
  535. package/dist/ui/input.d.ts +3 -0
  536. package/dist/ui/input.js +7 -0
  537. package/dist/ui/input.js.map +1 -0
  538. package/dist/ui/inspector.d.ts +18 -0
  539. package/dist/ui/inspector.js +14 -0
  540. package/dist/ui/inspector.js.map +1 -0
  541. package/dist/ui/layout.d.ts +45 -0
  542. package/dist/ui/layout.js +48 -0
  543. package/dist/ui/layout.js.map +1 -0
  544. package/dist/ui/panel.d.ts +12 -0
  545. package/dist/ui/panel.js +20 -0
  546. package/dist/ui/panel.js.map +1 -0
  547. package/dist/ui/separator.d.ts +6 -0
  548. package/dist/ui/separator.js +7 -0
  549. package/dist/ui/separator.js.map +1 -0
  550. package/dist/ui/toolbar.d.ts +9 -0
  551. package/dist/ui/toolbar.js +16 -0
  552. package/dist/ui/toolbar.js.map +1 -0
  553. package/dist/ui/typography.d.ts +50 -0
  554. package/dist/ui/typography.js +43 -0
  555. package/dist/ui/typography.js.map +1 -0
  556. package/package.json +149 -0
  557. package/src/styles/studio.css +101 -0
  558. package/src/styles/tokens.css +63 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"redirect-manager.js","sourceRoot":"","sources":["../../../src/components/routes/redirect-manager.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,35 @@
1
+ import type { RouteRecord } from '@elytracms/cms-core';
2
+ import type { RouteConflict } from '@elytracms/studio/lib/routing';
3
+ /** The slice of a graph page the route list needs for linking/labelling. */
4
+ export interface PageSummary {
5
+ id: string;
6
+ name: string;
7
+ }
8
+ export interface RouteListProps {
9
+ projectId: string;
10
+ routes: readonly RouteRecord[];
11
+ /** Engine-sourced `route-conflict` issues, indexed by route id (both sides). */
12
+ conflicts: ReadonlyMap<string, RouteConflict[]>;
13
+ pages: readonly PageSummary[];
14
+ }
15
+ /**
16
+ * Every route of the project (EC-170), read-only (EC-207 "routes as code"):
17
+ * static paths, dynamic patterns with `:param` segments rendered distinctly, and
18
+ * per-locale variants — each row linking to its page/template/document. Routes
19
+ * are authored in `elytra.config.ts`; this list only views them. Conflicts from
20
+ * the engine's structured issues render inline with deep links to the
21
+ * counterpart row.
22
+ */
23
+ export declare function RouteList({ projectId, routes, conflicts, pages }: RouteListProps): import("react").JSX.Element;
24
+ /** A route pattern with `:param` segments rendered distinctly (EC-170). */
25
+ export declare function PatternView({ pattern }: {
26
+ pattern: string;
27
+ }): import("react").JSX.Element;
28
+ /**
29
+ * Inline conflict block: the engine's `route-conflict` message plus a deep
30
+ * link to the counterpart row (same-page anchor; rows highlight on `:target`).
31
+ */
32
+ export declare function ConflictNotice({ routeId, conflicts, }: {
33
+ routeId: string;
34
+ conflicts: readonly RouteConflict[];
35
+ }): import("react").JSX.Element;
@@ -0,0 +1,69 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { Link, STUDIO_PROJECT_ROUTE, studioPath } from '@elytracms/studio/router';
3
+ import { CircleAlert, Globe } from 'lucide-react';
4
+ import { Badge, Code, Row, Spacer, Stack, Text } from '@elytracms/studio/ui';
5
+ import { patternSegments } from '@elytracms/studio/lib/routing';
6
+ /**
7
+ * Every route of the project (EC-170), read-only (EC-207 "routes as code"):
8
+ * static paths, dynamic patterns with `:param` segments rendered distinctly, and
9
+ * per-locale variants — each row linking to its page/template/document. Routes
10
+ * are authored in `elytra.config.ts`; this list only views them. Conflicts from
11
+ * the engine's structured issues render inline with deep links to the
12
+ * counterpart row.
13
+ */
14
+ export function RouteList({ projectId, routes, conflicts, pages }) {
15
+ const sorted = [...routes].sort((a, b) => a.pattern === b.pattern
16
+ ? (a.locale ?? '').localeCompare(b.locale ?? '')
17
+ : a.pattern.localeCompare(b.pattern));
18
+ return (_jsxs(Stack, { gap: "none", className: "min-h-0", children: [_jsxs(Row, { gap: "2", className: "h-12 shrink-0 border-b border-border px-4", children: [_jsx(Text, { size: "sm", weight: "semibold", children: "Routes" }), _jsx(Text, { size: "xs", tone: "subtle", mono: true, children: routes.length })] }), _jsxs(Stack, { gap: "3", className: "p-4", children: [sorted.length === 0 ? (_jsx(Text, { size: "sm", tone: "muted", children: "No routes defined. Add routes in elytra.config.ts to bind URL patterns to pages or templates." })) : null, _jsx("ul", { className: "flex flex-col gap-2", "data-testid": "route-list", children: sorted.map((route) => (_jsx(RouteRow, { projectId: projectId, route: route, conflicts: conflicts.get(route.id) ?? [], pages: pages }, route.id))) })] })] }));
19
+ }
20
+ function RouteRow({ projectId, route, conflicts, pages, }) {
21
+ const hasConflict = conflicts.length > 0;
22
+ return (_jsxs("li", { id: `route-${route.id}`, "data-testid": `route-row-${route.id}`, className: 'rounded-md border p-3 transition-colors target:ring-2 target:ring-ring/60 ' +
23
+ (hasConflict ? 'border-destructive/40 bg-destructive/5' : 'border-border bg-card/40'), children: [_jsxs(Row, { gap: "2", wrap: true, children: [_jsx(PatternView, { pattern: route.pattern }), _jsx(LocaleBadge, { locale: route.locale }), _jsx(Spacer, {}), hasConflict ? (_jsx(Badge, { variant: "error", "data-testid": `route-status-${route.id}`, children: "conflict" })) : (_jsx(Badge, { variant: "success", "data-testid": `route-status-${route.id}`, children: "ok" }))] }), _jsx(Row, { gap: "2", wrap: true, className: "mt-2", children: _jsx(RouteTarget, { projectId: projectId, route: route, pages: pages }) }), hasConflict ? _jsx(ConflictNotice, { routeId: route.id, conflicts: conflicts }) : null] }));
24
+ }
25
+ /** A route pattern with `:param` segments rendered distinctly (EC-170). */
26
+ export function PatternView({ pattern }) {
27
+ const segments = patternSegments(pattern);
28
+ return (_jsxs("span", { className: "inline-flex flex-wrap items-center font-mono text-sm", "data-testid": "pattern", children: [_jsx("span", { className: "text-muted-foreground", children: "/" }), segments.map((segment, index) => (_jsxs("span", { className: "inline-flex items-center", children: [segment.param ? (_jsx("span", { "data-param": segment.text, className: "rounded-sm border border-primary/30 bg-primary/10 px-1 text-primary", children: segment.text })) : (_jsx("span", { className: "text-foreground", children: segment.text })), index < segments.length - 1 ? _jsx("span", { className: "text-muted-foreground", children: "/" }) : null] }, `${segment.text}-${index}`)))] }));
29
+ }
30
+ function LocaleBadge({ locale }) {
31
+ if (!locale) {
32
+ return (_jsxs(Badge, { variant: "outline", children: [_jsx(Globe, {}), " all locales"] }));
33
+ }
34
+ return (_jsxs(Badge, { variant: "info", children: [_jsx(Globe, {}), " ", locale] }));
35
+ }
36
+ /** The page/template/document a route renders, deep-linked where a surface exists. */
37
+ function RouteTarget({ projectId, route, pages, }) {
38
+ // EC-187: every target is a single `document` ref. A page target is the
39
+ // `page` collection; a template target is a `:param` placeholder id;
40
+ // anything else is a concrete linked document.
41
+ if (!route.document) {
42
+ return (_jsx(Badge, { variant: "warning", "data-testid": `route-no-target-${route.id}`, children: "no target" }));
43
+ }
44
+ if (route.document.collection === 'page') {
45
+ const pageId = route.document.id;
46
+ const page = pages.find((candidate) => candidate.id === pageId);
47
+ return (_jsxs(Row, { gap: "1", children: [_jsx(Text, { size: "xs", tone: "muted", children: "page" }), _jsx(Link, { to: STUDIO_PROJECT_ROUTE, params: { projectId, _splat: studioPath.builder() }, className: "text-xs font-medium text-primary underline-offset-2 hover:underline", children: page?.name ?? pageId }), !page ? _jsx(Badge, { variant: "warning", children: "not in graph" }) : null] }));
48
+ }
49
+ if (route.document.id.startsWith(':')) {
50
+ return (_jsxs(Row, { gap: "1", children: [_jsx(Text, { size: "xs", tone: "muted", children: "template" }), _jsx(Code, { children: route.document.collection })] }));
51
+ }
52
+ return (_jsxs(Row, { gap: "1", children: [_jsx(Text, { size: "xs", tone: "muted", children: "document" }), _jsxs(Link, { to: STUDIO_PROJECT_ROUTE, params: {
53
+ projectId,
54
+ _splat: studioPath.cmsDocument(route.document.collection, route.document.id),
55
+ }, className: "text-xs font-medium text-primary underline-offset-2 hover:underline", children: [route.document.collection, "/", route.document.id] })] }));
56
+ }
57
+ /**
58
+ * Inline conflict block: the engine's `route-conflict` message plus a deep
59
+ * link to the counterpart row (same-page anchor; rows highlight on `:target`).
60
+ */
61
+ export function ConflictNotice({ routeId, conflicts, }) {
62
+ return (_jsx(Stack, { gap: "1", className: "mt-2 rounded-md border border-destructive/30 bg-destructive/10 p-2", children: conflicts.map((conflict, index) => (_jsxs(Row, { gap: "2", align: "start", children: [_jsx(CircleAlert, { className: "mt-0.5 size-3.5 shrink-0 text-destructive" }), _jsxs(Stack, { gap: "1", className: "min-w-0", children: [_jsx(Text, { size: "xs", className: "text-destructive", "data-testid": `conflict-${routeId}`,
63
+ // The engine message names both routes by their raw ids
64
+ // (`r-blog-slug-en`) — kept inspectable on hover, never shown as
65
+ // visible copy. The editor sees the patterns on the rows + the link
66
+ // below (EC-192).
67
+ title: conflict.issue.message, children: "Matches the same URLs as another route." }), conflict.otherRouteId ? (_jsx("a", { href: `#route-${conflict.otherRouteId}`, className: "text-xs font-medium text-destructive underline underline-offset-2", "data-testid": `conflict-link-${routeId}`, children: "View conflicting route" })) : null] })] }, `${conflict.otherRouteId}-${index}`))) }));
68
+ }
69
+ //# sourceMappingURL=route-list.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"route-list.js","sourceRoot":"","sources":["../../../src/components/routes/route-list.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,14 @@
1
+ import type { Project } from '@elytracms/studio-core';
2
+ /**
3
+ * The Routes surface (EC-170, made read-only by EC-207 "routes as code"):
4
+ * every route and redirect of the project, with the engine's structured issues
5
+ * (route conflicts, redirect loops) rendered inline. Routes and redirects are
6
+ * authored in `elytra.config.ts` and read from the resolved config project
7
+ * (`resolveDeploymentRoutes`/`resolveDeploymentRedirects`) — NEVER from the
8
+ * backend. This surface only views them; conflict/loop detection comes from the
9
+ * canonical `@elytracms/cms-core` router, never from parallel UI-side logic. The
10
+ * page list (CMS `page` collection) is read only to label route targets.
11
+ */
12
+ export declare function RoutesShell({ project }: {
13
+ project: Project;
14
+ }): import("react").JSX.Element;
@@ -0,0 +1,68 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { useCallback, useEffect, useMemo, useState } from 'react';
3
+ import { createRouter } from '@elytracms/cms-core';
4
+ import { Badge, Heading, Row, Spacer, Stack, Text } from '@elytracms/studio/ui';
5
+ import { getStudioOperations } from '@elytracms/studio/lib/operations';
6
+ import { conflictsByRoute } from '@elytracms/studio/lib/routing';
7
+ import { resolveDeploymentRedirects, resolveDeploymentRoutes } from '@elytracms/studio/lib/workspace';
8
+ import { OperationErrorBanner } from '../operation-error';
9
+ import { RouteList } from './route-list';
10
+ import { RedirectManager } from './redirect-manager';
11
+ /** The body-is-a-canvas page collection (EC-187): routable page documents. */
12
+ const PAGE_COLLECTION = 'page';
13
+ /**
14
+ * Routable pages come from the `page` CMS collection (EC-192) — the documents an
15
+ * editor actually creates — not the builder's single synthetic working page.
16
+ * `documents.list` returns persisted records wrapping each document; map each to
17
+ * a `{ id, name }` summary for the route target labels.
18
+ */
19
+ function pageSummaries(records) {
20
+ return records.map(({ document }) => {
21
+ const name = document.values?.['name'];
22
+ return { id: document.id, name: typeof name === 'string' && name.length > 0 ? name : document.id };
23
+ });
24
+ }
25
+ /**
26
+ * The Routes surface (EC-170, made read-only by EC-207 "routes as code"):
27
+ * every route and redirect of the project, with the engine's structured issues
28
+ * (route conflicts, redirect loops) rendered inline. Routes and redirects are
29
+ * authored in `elytra.config.ts` and read from the resolved config project
30
+ * (`resolveDeploymentRoutes`/`resolveDeploymentRedirects`) — NEVER from the
31
+ * backend. This surface only views them; conflict/loop detection comes from the
32
+ * canonical `@elytracms/cms-core` router, never from parallel UI-side logic. The
33
+ * page list (CMS `page` collection) is read only to label route targets.
34
+ */
35
+ export function RoutesShell({ project }) {
36
+ const projectId = project.id;
37
+ // Routes & redirects are config-sourced (EC-207): resolved synchronously from
38
+ // the active `elytra.config.ts` project, never fetched from the backend.
39
+ const routes = useMemo(() => resolveDeploymentRoutes(), []);
40
+ const redirects = useMemo(() => resolveDeploymentRedirects(), []);
41
+ const [pages, setPages] = useState([]);
42
+ const [loadError, setLoadError] = useState(null);
43
+ // Page documents feed the route target labels (read-only display). A failure
44
+ // here is non-fatal: the routes still render; the page labels just fall back
45
+ // to ids. The error banner surfaces any connection problem.
46
+ const reloadPages = useCallback(async () => {
47
+ const { operations } = await getStudioOperations();
48
+ const pageDocs = await operations.documents.list({ projectId, collection: PAGE_COLLECTION });
49
+ if (pageDocs.ok) {
50
+ setPages(pageSummaries(pageDocs.value));
51
+ setLoadError(null);
52
+ }
53
+ else {
54
+ setLoadError(pageDocs.error);
55
+ }
56
+ }, [projectId]);
57
+ useEffect(() => {
58
+ void reloadPages();
59
+ }, [reloadPages]);
60
+ // The engine: one router over the config-resolved records. Its structured
61
+ // issues are the single source of conflict/loop truth for this surface.
62
+ const router = useMemo(() => createRouter(routes, redirects, {
63
+ defaultLocale: project.settings.defaultLocale,
64
+ }), [routes, redirects, project.settings.defaultLocale]);
65
+ const conflicts = useMemo(() => conflictsByRoute(router.issues), [router]);
66
+ return (_jsxs(Stack, { gap: "none", className: "min-h-full", "data-testid": "routes-shell", children: [_jsxs(Row, { gap: "3", className: "shrink-0 border-b border-border px-4 py-3 sm:px-6", children: [_jsxs(Stack, { gap: "1", children: [_jsx(Heading, { level: 2, size: "h3", children: "Routes & redirects" }), _jsxs(Text, { size: "xs", tone: "muted", children: ["Routes & redirects are defined in ", _jsx("code", { children: "elytra.config.ts" }), ". Conflicts and loops are detected by the canonical route engine \u2014 never silently."] })] }), _jsx(Spacer, {}), loadError ? (_jsx(OperationErrorBanner, { error: loadError, onDismiss: () => void reloadPages() })) : null, router.issues.length > 0 ? (_jsxs(Badge, { variant: "error", "data-testid": "routing-issue-count", children: [router.issues.length, " issue", router.issues.length === 1 ? '' : 's'] })) : (_jsx(Badge, { variant: "success", children: "no issues" }))] }), _jsxs("div", { className: "grid min-h-0 flex-1 grid-cols-1 xl:grid-cols-[minmax(0,5fr)_minmax(0,4fr)]", children: [_jsx("section", { "aria-label": "Routes", className: "min-w-0 border-b border-border xl:border-b-0 xl:border-r", children: _jsx(RouteList, { projectId: projectId, routes: routes, conflicts: conflicts, pages: pages }) }), _jsx("section", { "aria-label": "Redirects", className: "min-w-0", children: _jsx(RedirectManager, { redirects: redirects, followRedirects: router.followRedirects }) })] })] }));
67
+ }
68
+ //# sourceMappingURL=routes-shell.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"routes-shell.js","sourceRoot":"","sources":["../../../src/components/routes/routes-shell.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,17 @@
1
+ import type { ProjectId, SectionAvailabilityMap } from '@elytracms/studio-core';
2
+ import type { StudioNavId } from './sections';
3
+ export interface SectionNavProps {
4
+ projectId: ProjectId;
5
+ activeSection: StudioNavId | null;
6
+ availability: SectionAvailabilityMap;
7
+ /** User-toggled collapse (EC-214) — icons only when collapsed, persisted by the shell. */
8
+ collapsed: boolean;
9
+ onToggleCollapsed: () => void;
10
+ }
11
+ /**
12
+ * Vertical section rail (brief §8.1). Availability-aware: `available`/`planned`
13
+ * are navigable; `unavailable` is rendered disabled. User-collapsible to an
14
+ * icon rail (EC-214) — the preference persists, and the active section carries a
15
+ * strong highlight (accent fill + a leading marker bar).
16
+ */
17
+ export declare function SectionNav({ projectId, activeSection, availability, collapsed, onToggleCollapsed, }: SectionNavProps): import("react").JSX.Element;
@@ -0,0 +1,33 @@
1
+ import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { Link, STUDIO_PROJECT_ROUTE, useLocation } from '@elytracms/studio/router';
3
+ import { PanelLeftClose, PanelLeftOpen } from 'lucide-react';
4
+ import { cn } from '@elytracms/studio/lib/utils';
5
+ import { SECTION_NAV_ITEMS, activeSectionFromPath, navAvailabilityOf } from './sections';
6
+ /**
7
+ * Vertical section rail (brief §8.1). Availability-aware: `available`/`planned`
8
+ * are navigable; `unavailable` is rendered disabled. User-collapsible to an
9
+ * icon rail (EC-214) — the preference persists, and the active section carries a
10
+ * strong highlight (accent fill + a leading marker bar).
11
+ */
12
+ export function SectionNav({ projectId, activeSection, availability, collapsed, onToggleCollapsed, }) {
13
+ // Recover the active id from the path if the shell didn't supply one — the
14
+ // shared parser is the single source of truth for the section segment index.
15
+ const { pathname } = useLocation();
16
+ const active = activeSection ?? activeSectionFromPath(pathname);
17
+ return (_jsxs("nav", { "aria-label": "Sections", className: cn('flex shrink-0 flex-col gap-0.5 border-r border-border bg-card/40 p-2 transition-[width] duration-150', collapsed ? 'w-[3.5rem]' : 'w-56'), children: [SECTION_NAV_ITEMS.map((item) => {
18
+ const state = navAvailabilityOf(availability, item.id);
19
+ const isActive = item.id === active;
20
+ const Icon = item.icon;
21
+ const body = (_jsxs(_Fragment, { children: [isActive ? (_jsx("span", { className: "absolute inset-y-1.5 left-0 w-0.5 rounded-full bg-primary", "aria-hidden": true })) : null, _jsx(Icon, { className: "size-4 shrink-0" }), collapsed ? null : (_jsx("span", { className: "min-w-0 flex-1 truncate", children: item.label })), state === 'planned' && !collapsed ? (_jsx("span", { className: "size-1.5 shrink-0 rounded-full bg-warning", "aria-hidden": true, title: "Planned" })) : null] }));
22
+ const base = cn('group relative flex h-9 items-center gap-2.5 rounded-md text-sm transition-colors', collapsed ? 'justify-center px-0' : 'px-3');
23
+ // EC-221: an unavailable section is absent from the rail (not greyed) —
24
+ // e.g. Extensions, cut from the v1 nav (vision §5). It stays reachable by
25
+ // URL for Milestone E revival; the rail simply doesn't advertise it.
26
+ if (state === 'unavailable')
27
+ return null;
28
+ return (_jsx(Link, { to: STUDIO_PROJECT_ROUTE, params: { projectId, _splat: item.id }, title: item.label, "aria-current": isActive ? 'page' : undefined, className: cn(base, isActive
29
+ ? 'bg-accent font-medium text-accent-foreground'
30
+ : 'text-muted-foreground hover:bg-muted hover:text-foreground'), children: body }, item.id));
31
+ }), _jsx("button", { type: "button", onClick: onToggleCollapsed, "aria-label": collapsed ? 'Expand sidebar' : 'Collapse sidebar', "aria-pressed": collapsed, title: collapsed ? 'Expand sidebar' : 'Collapse sidebar', className: cn('mt-auto flex h-9 items-center gap-2.5 rounded-md text-sm text-muted-foreground transition-colors hover:bg-muted hover:text-foreground', collapsed ? 'justify-center px-0' : 'px-3'), children: collapsed ? (_jsx(PanelLeftOpen, { className: "size-4 shrink-0" })) : (_jsxs(_Fragment, { children: [_jsx(PanelLeftClose, { className: "size-4 shrink-0" }), _jsx("span", { className: "min-w-0 flex-1 truncate text-left", children: "Collapse" })] })) })] }));
32
+ }
33
+ //# sourceMappingURL=section-nav.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"section-nav.js","sourceRoot":"","sources":["../../src/components/section-nav.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,24 @@
1
+ import type { ReactNode } from 'react';
2
+ import type { SectionAvailability, SectionState } from '@elytracms/studio-core';
3
+ /**
4
+ * Resolve the runtime state of a section (brief §8.1, §11). A `forced` value
5
+ * (e.g. from a `?state=` param) wins, making every state reachable
6
+ * deterministically; otherwise availability decides.
7
+ */
8
+ export declare function resolveSectionState(availability: SectionAvailability, forced?: SectionState | null): SectionState;
9
+ export interface SectionStateViewProps {
10
+ state: Exclude<SectionState, 'working'>;
11
+ /** Section-specific heading, e.g. "CMS" — overrides the generic preset title. */
12
+ title?: string;
13
+ description?: ReactNode;
14
+ action?: ReactNode;
15
+ className?: string;
16
+ }
17
+ /** Loading uses a skeleton; the rest use a centered placeholder. Consistent across sections. */
18
+ export declare function SectionStateView({ state, title, description, action, className, }: SectionStateViewProps): import("react").JSX.Element;
19
+ /** Shimmer skeleton standing in for an in-flight section load. */
20
+ export declare function SectionSkeleton({ className }: {
21
+ className?: string;
22
+ }): import("react").JSX.Element;
23
+ /** The full set of forceable states, for fixtures and the state switcher. */
24
+ export declare const FORCEABLE_STATES: readonly SectionState[];
@@ -0,0 +1,78 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { CircleAlert, Clock, Inbox, Loader2, Lock } from 'lucide-react';
3
+ import { Badge, Heading, Stack, Text } from '@elytracms/studio/ui';
4
+ import { cn } from '@elytracms/studio/lib/utils';
5
+ /**
6
+ * Resolve the runtime state of a section (brief §8.1, §11). A `forced` value
7
+ * (e.g. from a `?state=` param) wins, making every state reachable
8
+ * deterministically; otherwise availability decides.
9
+ */
10
+ export function resolveSectionState(availability, forced) {
11
+ if (forced)
12
+ return forced;
13
+ if (availability === 'planned')
14
+ return 'planned';
15
+ if (availability === 'unavailable')
16
+ return 'unavailable';
17
+ return 'working';
18
+ }
19
+ const PRESETS = {
20
+ empty: {
21
+ icon: Inbox,
22
+ title: 'Nothing here yet',
23
+ description: 'This section has no content for the active project.',
24
+ badge: { label: 'empty', variant: 'outline' },
25
+ },
26
+ loading: {
27
+ icon: Loader2,
28
+ title: 'Loading…',
29
+ description: 'Fetching the latest state for this section.',
30
+ badge: { label: 'loading', variant: 'info' },
31
+ spin: true,
32
+ },
33
+ error: {
34
+ icon: CircleAlert,
35
+ title: 'Something went wrong',
36
+ description: 'This section could not be loaded. Try again in a moment.',
37
+ badge: { label: 'error', variant: 'error' },
38
+ },
39
+ unavailable: {
40
+ icon: Lock,
41
+ title: 'Not available',
42
+ description: 'This section is not available for the active project.',
43
+ badge: { label: 'unavailable', variant: 'outline' },
44
+ },
45
+ planned: {
46
+ icon: Clock,
47
+ title: 'Planned',
48
+ description: 'This surface is planned and not yet enabled for this project.',
49
+ badge: { label: 'planned', variant: 'warning' },
50
+ },
51
+ };
52
+ /** Loading uses a skeleton; the rest use a centered placeholder. Consistent across sections. */
53
+ export function SectionStateView({ state, title, description, action, className, }) {
54
+ if (state === 'loading')
55
+ return _jsx(SectionSkeleton, { className: className });
56
+ const preset = PRESETS[state];
57
+ const Icon = preset.icon;
58
+ const tone = state === 'error'
59
+ ? 'border-destructive/30 bg-destructive/5'
60
+ : state === 'planned'
61
+ ? 'border-warning/30 bg-warning/5'
62
+ : 'border-border bg-card/40';
63
+ return (_jsx("div", { "data-section-state": state, className: cn('grid min-h-[18rem] place-items-center p-8', className), children: _jsxs(Stack, { gap: "3", align: "center", className: cn('max-w-sm rounded-xl border border-dashed px-8 py-10 text-center', tone), children: [_jsx("span", { className: "grid size-11 place-items-center rounded-lg border border-border bg-background text-muted-foreground", children: _jsx(Icon, { className: "size-5" }) }), _jsxs(Stack, { gap: "1", align: "center", children: [_jsx(Heading, { level: 2, size: "h3", children: title ?? preset.title }), _jsx(Text, { size: "sm", tone: "muted", children: description ?? preset.description })] }), _jsx(Badge, { variant: preset.badge.variant, children: preset.badge.label }), action ? _jsx("div", { className: "pt-1", children: action }) : null] }) }));
64
+ }
65
+ /** Shimmer skeleton standing in for an in-flight section load. */
66
+ export function SectionSkeleton({ className }) {
67
+ return (_jsxs("div", { "data-section-state": "loading", className: cn('space-y-4 p-6', className), "aria-busy": true, children: [_jsx("div", { className: "h-7 w-48 animate-pulse rounded-md bg-muted" }), _jsx("div", { className: "grid gap-3 sm:grid-cols-2 lg:grid-cols-3", children: Array.from({ length: 6 }).map((_, i) => (_jsx("div", { className: "h-28 animate-pulse rounded-xl bg-muted/70" }, i))) })] }));
68
+ }
69
+ /** The full set of forceable states, for fixtures and the state switcher. */
70
+ export const FORCEABLE_STATES = [
71
+ 'working',
72
+ 'empty',
73
+ 'loading',
74
+ 'error',
75
+ 'unavailable',
76
+ 'planned',
77
+ ];
78
+ //# sourceMappingURL=section-state.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"section-state.js","sourceRoot":"","sources":["../../src/components/section-state.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,31 @@
1
+ import type { ReactNode } from 'react';
2
+ import type { Project, ProjectId, SectionId, SectionState } from '@elytracms/studio-core';
3
+ /** Parse a `?state=` search param into a SectionState (undefined when absent/invalid). */
4
+ export declare function parseSectionState(raw: unknown): SectionState | undefined;
5
+ export interface SectionSurfaceProps {
6
+ project: Project;
7
+ section: SectionId;
8
+ /** Forced state from `?state=`; overrides availability. */
9
+ forcedState?: SectionState;
10
+ /** Working-state content. When omitted, a phase placeholder is shown. */
11
+ children?: ReactNode;
12
+ }
13
+ /**
14
+ * Resolves a section's deterministic state (brief §8.1, §11) and renders it: the
15
+ * working content (or a phase placeholder) when `working`, else a consistent
16
+ * state view. A small state switcher makes every state reachable for inspection.
17
+ */
18
+ export declare function SectionSurface({ project, section, forcedState, children }: SectionSurfaceProps): import("react").JSX.Element;
19
+ /** Placeholder for an available section whose live surface lands in a later phase. */
20
+ export declare function PhasePlaceholder({ section }: {
21
+ section: SectionId;
22
+ }): import("react").JSX.Element;
23
+ /**
24
+ * Deterministic state switcher (brief §11). Links to the same section with each
25
+ * `?state=` value so agents/humans can reproduce every state by URL or click.
26
+ */
27
+ export declare function StateSwitcher({ projectId, section, current, }: {
28
+ projectId: ProjectId;
29
+ section: SectionId;
30
+ current?: SectionState;
31
+ }): import("react").JSX.Element;
@@ -0,0 +1,46 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { Link, STUDIO_PROJECT_ROUTE } from '@elytracms/studio/router';
3
+ import { ArrowUpRight } from 'lucide-react';
4
+ import { availabilityOf, sectionStateSchema } from '@elytracms/studio-core';
5
+ import { Badge, Button, Code, Row, Stack, Text } from '@elytracms/studio/ui';
6
+ import { cn } from '@elytracms/studio/lib/utils';
7
+ import { resolveSectionState, SectionStateView } from './section-state';
8
+ import { sectionNavItem } from './sections';
9
+ /** Parse a `?state=` search param into a SectionState (undefined when absent/invalid). */
10
+ export function parseSectionState(raw) {
11
+ const parsed = sectionStateSchema.safeParse(raw);
12
+ return parsed.success ? parsed.data : undefined;
13
+ }
14
+ /**
15
+ * Resolves a section's deterministic state (brief §8.1, §11) and renders it: the
16
+ * working content (or a phase placeholder) when `working`, else a consistent
17
+ * state view. A small state switcher makes every state reachable for inspection.
18
+ */
19
+ export function SectionSurface({ project, section, forcedState, children }) {
20
+ const availability = availabilityOf(project.settings.sectionAvailability, section);
21
+ const state = resolveSectionState(availability, forcedState);
22
+ return (_jsxs(Stack, { gap: "none", className: "min-h-full", children: [_jsx(StateSwitcher, { projectId: project.id, section: section, current: forcedState }), state === 'working' ? ((children ?? _jsx(PhasePlaceholder, { section: section }))) : (_jsx(SectionStateView, { state: state, title: sectionNavItem(section).label }))] }));
23
+ }
24
+ /** Placeholder for an available section whose live surface lands in a later phase. */
25
+ export function PhasePlaceholder({ section }) {
26
+ const item = sectionNavItem(section);
27
+ const Icon = item.icon;
28
+ return (_jsx("div", { "data-section-state": "working", className: "grid flex-1 place-items-center p-8", children: _jsxs(Stack, { gap: "3", align: "center", className: "max-w-md text-center", children: [_jsx("span", { className: "grid size-12 place-items-center rounded-xl border border-border bg-card text-primary", children: _jsx(Icon, { className: "size-6" }) }), _jsxs(Stack, { gap: "1", align: "center", children: [_jsxs(Text, { weight: "semibold", children: [item.label, " is enabled"] }), _jsxs(Text, { size: "sm", tone: "muted", children: [item.description, " The full surface arrives in ", item.phase, "."] })] }), _jsx(Badge, { variant: "primary", children: item.phase })] }) }));
29
+ }
30
+ /**
31
+ * Deterministic state switcher (brief §11). Links to the same section with each
32
+ * `?state=` value so agents/humans can reproduce every state by URL or click.
33
+ */
34
+ export function StateSwitcher({ projectId, section, current, }) {
35
+ const states = ['working', 'empty', 'loading', 'error', 'unavailable', 'planned'];
36
+ const activeKey = current ?? 'default';
37
+ return (_jsxs(Row, { gap: "1", wrap: true, className: "shrink-0 border-b border-dashed border-border/70 px-4 py-2 sm:px-6", "data-testid": "state-switcher", children: [_jsx(Text, { size: "xs", tone: "subtle", mono: true, className: "mr-1", children: "state" }), _jsx(Link, { to: STUDIO_PROJECT_ROUTE, params: { projectId, _splat: section }, search: {}, className: cn('rounded-md px-2 py-0.5 font-mono text-xs transition-colors', activeKey === 'default'
38
+ ? 'bg-accent text-accent-foreground'
39
+ : 'text-muted-foreground hover:bg-muted hover:text-foreground'), children: "default" }), states.map((s) => {
40
+ const active = s === activeKey;
41
+ return (_jsx(Link, { to: STUDIO_PROJECT_ROUTE, params: { projectId, _splat: section }, search: { state: s }, className: cn('rounded-md px-2 py-0.5 font-mono text-xs transition-colors', active
42
+ ? 'bg-accent text-accent-foreground'
43
+ : 'text-muted-foreground hover:bg-muted hover:text-foreground'), children: s }, s));
44
+ }), _jsx(Code, { tone: "muted", className: "ml-2 hidden sm:inline-flex", children: activeKey === 'default' ? 'auto' : `?state=${activeKey}` }), _jsx("span", { className: "flex-1" }), _jsx(Button, { variant: "ghost", size: "sm", asChild: true, className: "hidden md:inline-flex", children: _jsxs(Link, { to: "/", className: "gap-1", children: ["Docs ", _jsx(ArrowUpRight, {})] }) })] }));
45
+ }
46
+ //# sourceMappingURL=section-surface.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"section-surface.js","sourceRoot":"","sources":["../../src/components/section-surface.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,38 @@
1
+ import type { LucideIcon } from 'lucide-react';
2
+ import type { Project, SectionAvailability, SectionAvailabilityMap, SectionId } from '@elytracms/studio-core';
3
+ /**
4
+ * App-level navigation ids: the studio-core sections plus surfaces registered
5
+ * by the app itself. `routes` (EC-170) is the first app-registered surface —
6
+ * it lives next to the CMS in the rail and rides on the CMS availability,
7
+ * since routes/redirects are CMS routing concerns (`@elytracms/cms-core`).
8
+ */
9
+ export type StudioNavId = SectionId | 'routes';
10
+ export interface SectionNavItem {
11
+ id: StudioNavId;
12
+ label: string;
13
+ description: string;
14
+ icon: LucideIcon;
15
+ phase: string;
16
+ }
17
+ /** Navigation items in canonical order (brief §8.1 + EC-170). */
18
+ export declare const SECTION_NAV_ITEMS: readonly SectionNavItem[];
19
+ export declare function sectionNavItem(id: StudioNavId): SectionNavItem;
20
+ /**
21
+ * Availability for a nav id. App-registered surfaces map onto the section
22
+ * whose data they manage: Routes follows the CMS availability.
23
+ */
24
+ export declare function navAvailabilityOf(map: SectionAvailabilityMap, id: StudioNavId): SectionAvailability;
25
+ /**
26
+ * The section a project should open to: the first non-`unavailable` section in
27
+ * canonical order. Settings is always available, so this never returns null.
28
+ */
29
+ export declare function firstAvailableSection(project: Project): SectionId;
30
+ /**
31
+ * Parse the active nav id out of a studio pathname `/$projectId/<section>[/...]`
32
+ * (incl. the app-registered Routes surface, EC-170). Returns null for the bare
33
+ * project URL or an unknown segment. The section is the SECOND path segment —
34
+ * directly after the projectId; there is no `/p` prefix (EC-220). The single
35
+ * source of truth for active-section detection: the shell breadcrumb and the
36
+ * nav rail both read it, so the segment index lives in exactly one place.
37
+ */
38
+ export declare function activeSectionFromPath(pathname: string): StudioNavId | null;
@@ -0,0 +1,72 @@
1
+ import { Blocks, Database, Image, Puzzle, Settings, Signpost } from 'lucide-react';
2
+ import { SECTIONS, SECTION_IDS, availabilityOf, sectionIdSchema } from '@elytracms/studio-core';
3
+ /** Which Studio phase delivers each section's live surface (for placeholders). */
4
+ const SECTION_PHASE = {
5
+ components: 'Phase 4',
6
+ cms: 'Phase 6',
7
+ routes: 'Milestone B',
8
+ assets: 'Phase 6',
9
+ extensions: 'Phase 11',
10
+ settings: 'Phase 2',
11
+ };
12
+ const ICONS = {
13
+ components: Blocks,
14
+ cms: Database,
15
+ routes: Signpost,
16
+ assets: Image,
17
+ extensions: Puzzle,
18
+ settings: Settings,
19
+ };
20
+ /** Descriptor for the app-registered Routes surface (EC-170). */
21
+ const ROUTES_DESCRIPTOR = {
22
+ id: 'routes',
23
+ label: 'Routes',
24
+ description: 'View the resolved URL routes & redirects (defined in elytra.config.ts).',
25
+ };
26
+ /** Canonical nav order: studio-core order with Routes slotted after CMS. */
27
+ const NAV_IDS = SECTION_IDS.flatMap((id) => id === 'cms' ? [id, 'routes'] : [id]);
28
+ function descriptorOf(id) {
29
+ return id === 'routes' ? ROUTES_DESCRIPTOR : SECTIONS[id];
30
+ }
31
+ /** Navigation items in canonical order (brief §8.1 + EC-170). */
32
+ export const SECTION_NAV_ITEMS = NAV_IDS.map((id) => ({
33
+ id,
34
+ label: descriptorOf(id).label,
35
+ description: descriptorOf(id).description,
36
+ icon: ICONS[id],
37
+ phase: SECTION_PHASE[id],
38
+ }));
39
+ export function sectionNavItem(id) {
40
+ return SECTION_NAV_ITEMS.find((item) => item.id === id);
41
+ }
42
+ /**
43
+ * Availability for a nav id. App-registered surfaces map onto the section
44
+ * whose data they manage: Routes follows the CMS availability.
45
+ */
46
+ export function navAvailabilityOf(map, id) {
47
+ return availabilityOf(map, id === 'routes' ? 'cms' : id);
48
+ }
49
+ /**
50
+ * The section a project should open to: the first non-`unavailable` section in
51
+ * canonical order. Settings is always available, so this never returns null.
52
+ */
53
+ export function firstAvailableSection(project) {
54
+ const found = SECTION_IDS.find((id) => availabilityOf(project.settings.sectionAvailability, id) !== 'unavailable');
55
+ return found ?? 'settings';
56
+ }
57
+ /**
58
+ * Parse the active nav id out of a studio pathname `/$projectId/<section>[/...]`
59
+ * (incl. the app-registered Routes surface, EC-170). Returns null for the bare
60
+ * project URL or an unknown segment. The section is the SECOND path segment —
61
+ * directly after the projectId; there is no `/p` prefix (EC-220). The single
62
+ * source of truth for active-section detection: the shell breadcrumb and the
63
+ * nav rail both read it, so the segment index lives in exactly one place.
64
+ */
65
+ export function activeSectionFromPath(pathname) {
66
+ const segment = pathname.split('/')[2] ?? '';
67
+ if (segment === 'routes')
68
+ return 'routes';
69
+ const parsed = sectionIdSchema.safeParse(segment);
70
+ return parsed.success ? parsed.data : null;
71
+ }
72
+ //# sourceMappingURL=sections.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sections.js","sourceRoot":"","sources":["../../src/components/sections.ts"],"names":[],"mappings":"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"}