@astryxdesign/cli 0.6.3 → 0.6.4-canary.0e1fbdb

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 (728) hide show
  1. package/CHANGELOG.md +194 -0
  2. package/README.md +152 -107
  3. package/api/blog/blog.doc.mjs +1 -0
  4. package/api/build/_adapter.d.mts +50 -0
  5. package/api/build/_adapter.mjs +60 -0
  6. package/api/build/build.doc.mjs +22 -10
  7. package/api/build/build.test.mjs +219 -8
  8. package/api/build/build.type.d.mts +91 -2
  9. package/api/build/build.type.mjs +52 -8
  10. package/api/build/help/help.d.mts +12 -5
  11. package/api/build/help/help.mjs +69 -6
  12. package/api/build/kit/kit.d.mts +4 -1
  13. package/api/build/kit/kit.mjs +208 -53
  14. package/api/build/kit/rank.d.mts +44 -0
  15. package/api/build/kit/rank.mjs +432 -0
  16. package/api/build/kit/rank.test.mjs +196 -0
  17. package/api/component/_adapter.d.mts +31 -12
  18. package/api/component/_adapter.mjs +79 -15
  19. package/api/component/component.d.mts +6 -3
  20. package/api/component/component.doc.mjs +49 -19
  21. package/api/component/component.mjs +339 -22
  22. package/api/component/component.test.mjs +38 -0
  23. package/api/component/component.type.d.mts +47 -11
  24. package/api/component/component.type.mjs +76 -24
  25. package/api/component/detail/blocks/blocks.d.mts +2 -1
  26. package/api/component/detail/blocks/blocks.mjs +4 -3
  27. package/api/component/list/list.d.mts +0 -5
  28. package/api/component/list/list.mjs +40 -11
  29. package/api/discover/_adapter.d.mts +114 -6
  30. package/api/discover/_adapter.mjs +372 -17
  31. package/api/discover/_adapter.test.mjs +215 -0
  32. package/api/discover/_catalog-view.d.mts +115 -0
  33. package/api/discover/_catalog-view.mjs +203 -0
  34. package/api/discover/_catalog-view.test.mjs +128 -0
  35. package/api/discover/detail/detail.d.mts +18 -6
  36. package/api/discover/detail/detail.mjs +67 -13
  37. package/api/discover/detail/detail.test.mjs +85 -0
  38. package/api/discover/detail/item/item.d.mts +26 -0
  39. package/api/discover/detail/item/item.mjs +78 -0
  40. package/api/discover/detail/item/item.test.mjs +73 -0
  41. package/api/discover/discover.d.mts +3 -9
  42. package/api/discover/discover.doc.mjs +62 -18
  43. package/api/discover/discover.mjs +220 -36
  44. package/api/discover/discover.test.mjs +11 -2
  45. package/api/discover/discover.type.d.mts +150 -11
  46. package/api/discover/discover.type.mjs +107 -17
  47. package/api/discover/list/list.d.mts +20 -6
  48. package/api/discover/list/list.mjs +45 -12
  49. package/api/discover/list/list.test.mjs +46 -0
  50. package/api/discover/search/search.d.mts +18 -16
  51. package/api/discover/search/search.mjs +102 -56
  52. package/api/discover/search/search.test.mjs +144 -10
  53. package/api/docs/_adapter.d.mts +277 -41
  54. package/api/docs/_adapter.mjs +993 -108
  55. package/api/docs/compiled-topics.test.mjs +78 -0
  56. package/api/docs/detail/detail.mjs +22 -63
  57. package/api/docs/detail/section/section.d.mts +1 -1
  58. package/api/docs/detail/section/section.mjs +54 -19
  59. package/api/docs/detail/section/section.test.mjs +50 -0
  60. package/api/docs/docOverlays.test.mjs +27 -1
  61. package/api/docs/docs.d.mts +10 -3
  62. package/api/docs/docs.doc.mjs +55 -16
  63. package/api/docs/docs.mjs +53 -10
  64. package/api/docs/docs.type.d.mts +221 -5
  65. package/api/docs/docs.type.mjs +153 -11
  66. package/api/docs/index/index.d.mts +18 -0
  67. package/api/docs/index/index.mjs +40 -0
  68. package/api/docs/index/index.test.mjs +62 -0
  69. package/api/docs/list/list.mjs +28 -12
  70. package/api/docs/node/node.d.mts +43 -0
  71. package/api/docs/node/node.mjs +192 -0
  72. package/api/docs/reference-blocks.test.mjs +406 -0
  73. package/api/doctor/doctor.d.mts +104 -1
  74. package/api/doctor/doctor.doc.mjs +18 -8
  75. package/api/doctor/doctor.mjs +635 -7
  76. package/api/doctor/doctor.test.mjs +732 -11
  77. package/api/doctor/doctor.type.d.mts +1 -1
  78. package/api/doctor/doctor.type.mjs +1 -1
  79. package/api/gap-report/gap-report.doc.mjs +27 -14
  80. package/api/hook/_adapter.mjs +19 -5
  81. package/api/hook/hook.doc.mjs +7 -3
  82. package/api/hook/hook.type.d.mts +3 -3
  83. package/api/hook/hook.type.mjs +11 -11
  84. package/api/hook/list/list.d.mts +2 -2
  85. package/api/hook/list/list.mjs +69 -17
  86. package/api/index.d.mts +2 -1
  87. package/api/index.mjs +6 -3
  88. package/api/init/init.doc.mjs +22 -12
  89. package/api/init/init.test.mjs +41 -1
  90. package/api/init/remove/remove.mjs +1 -1
  91. package/api/init/run/run.mjs +20 -10
  92. package/api/integration/add-contribution.component-names.test.mjs +120 -0
  93. package/api/integration/add-contribution.d.mts +2 -1
  94. package/api/integration/add-contribution.mjs +130 -15
  95. package/api/integration/add-contribution.test.mjs +258 -7
  96. package/api/integration/add-helpers.d.mts +5 -2
  97. package/api/integration/add-helpers.mjs +36 -9
  98. package/api/integration/add-theme.mjs +56 -65
  99. package/api/integration/add-theme.test.mjs +139 -21
  100. package/api/integration/authoring-checks.mjs +138 -28
  101. package/api/integration/authoring-checks.test.mjs +179 -7
  102. package/api/integration/authoring-checks.type.mjs +6 -1
  103. package/api/integration/integration-authoring.type.d.mts +3 -1
  104. package/api/integration/integration-authoring.type.mjs +2 -0
  105. package/api/integration/integration-block-exports.test.mjs +10 -6
  106. package/api/integration/integrationAdd.doc.mjs +14 -4
  107. package/api/integration/integrationAddAgentDoc.doc.mjs +1 -0
  108. package/api/integration/integrationAddCodemod.doc.mjs +1 -0
  109. package/api/integration/integrationAddComponent.doc.mjs +2 -1
  110. package/api/integration/integrationAddDoc.doc.mjs +8 -1
  111. package/api/integration/integrationAddTemplate.doc.mjs +1 -0
  112. package/api/integration/integrationAddTheme.doc.mjs +6 -5
  113. package/api/integration/integrationComponentConflicts.doc.mjs +1 -0
  114. package/api/integration/integrationDocConflicts.doc.mjs +2 -1
  115. package/api/integration/integrationPackCheck.doc.mjs +5 -4
  116. package/api/integration/integrationTemplateConflicts.doc.d.mts +3 -0
  117. package/api/integration/integrationTemplateConflicts.doc.mjs +4 -0
  118. package/api/integration/pack-check.lifecycle-output.test.mjs +107 -0
  119. package/api/integration/pack-check.mjs +160 -11
  120. package/api/integration/pack-check.test.mjs +477 -47
  121. package/api/integration/pack-check.type.d.mts +26 -2
  122. package/api/integration/pack-check.type.mjs +15 -2
  123. package/api/integration/summarizeIssues.doc.mjs +1 -0
  124. package/api/integration/template-conflict-compatibility.test.mjs +73 -0
  125. package/api/integration/validate-integration-fixes.test.mjs +1389 -0
  126. package/api/integration/validate-integration.mjs +52 -102
  127. package/api/integration/validate-integration.test.mjs +179 -26
  128. package/api/integration/validate-unread-theme-folders.test.mjs +110 -0
  129. package/api/integration/validateIntegration.doc.mjs +3 -2
  130. package/api/json/assertResponse.doc.mjs +2 -1
  131. package/api/json/envelope-types.test.mjs +76 -0
  132. package/api/json/index.ts +2 -0
  133. package/api/json/isError.doc.mjs +2 -1
  134. package/api/json/parseResponse.doc.mjs +3 -2
  135. package/api/layout/_adapter.mjs +20 -5
  136. package/api/layout/expand/expand.mjs +7 -5
  137. package/api/layout/expand/expand.path-safety.test.mjs +53 -0
  138. package/api/layout/grammar/grammar.mjs +2 -1
  139. package/api/layout/layoutCheck.doc.mjs +1 -0
  140. package/api/layout/layoutExpand.doc.mjs +2 -1
  141. package/api/layout/layoutGrammar.doc.mjs +1 -0
  142. package/api/search/search-return-type.test.mjs +54 -0
  143. package/api/search/search.d.mts +89 -12
  144. package/api/search/search.doc.mjs +8 -2
  145. package/api/search/search.mjs +697 -97
  146. package/api/search/search.type.d.mts +15 -3
  147. package/api/search/search.type.mjs +5 -2
  148. package/api/swizzle/copy/copy.mjs +28 -11
  149. package/api/swizzle/swizzle.doc.mjs +8 -5
  150. package/api/swizzle/swizzle.type.d.mts +2 -2
  151. package/api/swizzle/swizzle.type.mjs +2 -2
  152. package/api/template/copy/copy.mjs +18 -24
  153. package/api/template/copy/copy.test.mjs +26 -0
  154. package/api/template/list/list.mjs +1 -0
  155. package/api/template/table-floating-bulk-actions.test.mjs +66 -0
  156. package/api/template/template-integration.test.mjs +1072 -3
  157. package/api/template/template-suffix.test.mjs +41 -21
  158. package/api/template/template.d.mts +1 -1
  159. package/api/template/template.doc.mjs +32 -9
  160. package/api/template/template.mjs +45 -8
  161. package/api/template/template.type.d.mts +12 -14
  162. package/api/template/template.type.mjs +15 -14
  163. package/api/theme/_adapter.d.mts +2 -3
  164. package/api/theme/_adapter.mjs +4 -5
  165. package/api/theme/add/add.binary.test.mjs +84 -0
  166. package/api/theme/add/add.mjs +31 -22
  167. package/api/theme/add/add.rollback.test.mjs +158 -0
  168. package/api/theme/add/add.staging.test.mjs +83 -0
  169. package/api/theme/add/add.test.mjs +14 -1
  170. package/api/theme/build/build.family.test.mjs +7 -12
  171. package/api/theme/build/build.mjs +140 -59
  172. package/api/theme/build/build.public-component-vars.test.mjs +1 -1
  173. package/api/theme/build/build.receipt-doc.test.mjs +111 -0
  174. package/api/theme/build/build.rollback.test.mjs +148 -0
  175. package/api/theme/build/build.test.mjs +127 -0
  176. package/api/theme/build/font-warning.mjs +3 -3
  177. package/api/theme/build/font-warning.test.mjs +5 -2
  178. package/api/theme/generateTonalPalette.doc.mjs +2 -2
  179. package/api/theme/integration-themes.test.mjs +39 -28
  180. package/api/theme/list/list.test.mjs +19 -20
  181. package/api/theme/listThemes.doc.mjs +6 -5
  182. package/api/theme/palette/generate/generate.mjs +8 -3
  183. package/api/theme/palette/generate/generate.test.mjs +96 -0
  184. package/api/theme/palette/generate/generator.d.mts +10 -13
  185. package/api/theme/palette/generate/generator.mjs +15 -4
  186. package/api/theme/palette/generate/generator.test.mjs +10 -0
  187. package/api/theme/template/template.mjs +11 -2
  188. package/api/theme/template/template.test.mjs +20 -0
  189. package/api/theme/theme.type.d.mts +170 -11
  190. package/api/theme/theme.type.mjs +94 -27
  191. package/api/theme/themeAdd.doc.mjs +12 -12
  192. package/api/theme/themeBuild.doc.mjs +21 -17
  193. package/api/theme/themeList.doc.mjs +6 -3
  194. package/api/theme/themeListAvailable.doc.mjs +6 -3
  195. package/api/theme/themePaletteGenerate.doc.mjs +16 -8
  196. package/api/theme/themeTargets.doc.mjs +4 -2
  197. package/api/theme/themeTemplate.doc.mjs +8 -3
  198. package/api/upgrade/_adapter.d.mts +32 -5
  199. package/api/upgrade/_adapter.mjs +139 -22
  200. package/api/upgrade/list/list.mjs +2 -1
  201. package/api/upgrade/list/list.test.mjs +73 -0
  202. package/api/upgrade/project-context.test.mjs +272 -0
  203. package/api/upgrade/provider-agreement.test.mjs +152 -0
  204. package/api/upgrade/run/files-changed.test.mjs +111 -0
  205. package/api/upgrade/run/run.mjs +358 -59
  206. package/api/upgrade/status/status.mjs +2 -2
  207. package/api/upgrade/upgrade.doc.mjs +32 -23
  208. package/api/upgrade/upgrade.type.d.mts +43 -5
  209. package/api/upgrade/upgrade.type.mjs +29 -13
  210. package/assets/codemods/__tests__/registry.test.mjs +1 -0
  211. package/assets/codemods/__tests__/runner.test.mjs +332 -8
  212. package/assets/codemods/file-count.test.mjs +163 -0
  213. package/assets/codemods/integration-discovery.mjs +48 -4
  214. package/assets/codemods/integration-discovery.test.mjs +73 -0
  215. package/assets/codemods/integration-runner.mjs +59 -7
  216. package/assets/codemods/integration-runner.protection.test.mjs +153 -0
  217. package/assets/codemods/registry.mjs +1 -0
  218. package/assets/codemods/run-codemod.mjs +177 -34
  219. package/assets/codemods/runner.mjs +353 -104
  220. package/assets/codemods/term-log.mjs +32 -8
  221. package/assets/codemods/term-log.test.mjs +19 -1
  222. package/assets/codemods/transform-prop.mjs +109 -0
  223. package/assets/codemods/transform-prop.test.mjs +95 -0
  224. package/assets/codemods/transforms/v0.0.14/__tests__/rename-status-variants.test.mjs +86 -165
  225. package/assets/codemods/transforms/v0.0.14/rename-status-variants.mjs +72 -210
  226. package/assets/codemods/transforms/v0.1.8/__tests__/rename-avatar-size-scale.test.mjs +83 -115
  227. package/assets/codemods/transforms/v0.1.8/rename-avatar-size-scale.mjs +57 -186
  228. package/assets/codemods/transforms/v0.3.0/__tests__/unwrap-authoring-factories.test.mjs +27 -5
  229. package/assets/codemods/transforms/v0.3.0/unwrap-authoring-factories.mjs +20 -5
  230. package/assets/codemods/transforms/v0.6.0/__tests__/next-codemods.test.mjs +47 -0
  231. package/assets/codemods/transforms/v0.6.0/rename-resizable-pixel-bounds.mjs +57 -10
  232. package/assets/codemods/transforms/v0.6.4/__tests__/migrate-native-picker-to-presentation.test.mjs +63 -0
  233. package/assets/codemods/transforms/v0.6.4/__tests__/migrate-theme-catalog-to-descriptors.test.mjs +220 -0
  234. package/assets/codemods/transforms/v0.6.4/index.mjs +31 -0
  235. package/assets/codemods/transforms/v0.6.4/migrate-native-picker-to-presentation.mjs +148 -0
  236. package/assets/codemods/transforms/v0.6.4/migrate-theme-catalog-to-descriptors.mjs +141 -0
  237. package/assets/docs/README.md +12 -1
  238. package/assets/docs/authoring.doc.mjs +14 -0
  239. package/assets/docs/browser-support.doc.mjs +11 -11
  240. package/assets/docs/color.doc.mjs +8 -2
  241. package/assets/docs/elevation.doc.mjs +6 -4
  242. package/assets/docs/getting-started.doc.mjs +6 -17
  243. package/assets/docs/icons.doc.mjs +2 -21
  244. package/assets/docs/illustrations.doc.mjs +7 -15
  245. package/assets/docs/internationalization.doc.mjs +7 -5
  246. package/assets/docs/layout.doc.dense.mjs +132 -84
  247. package/assets/docs/layout.doc.mjs +134 -78
  248. package/assets/docs/migration.doc.mjs +19 -21
  249. package/assets/docs/motion.doc.mjs +16 -3
  250. package/assets/docs/principles.doc.dense.mjs +5 -5
  251. package/assets/docs/principles.doc.mjs +14 -6
  252. package/assets/docs/principles.doc.zh.mjs +6 -6
  253. package/assets/docs/shape.doc.mjs +8 -3
  254. package/assets/docs/spacing.doc.mjs +7 -2
  255. package/assets/docs/styling-libraries.doc.mjs +10 -6
  256. package/assets/docs/styling.doc.mjs +22 -26
  257. package/assets/docs/theme.doc.dense.mjs +58 -18
  258. package/assets/docs/theme.doc.mjs +60 -50
  259. package/assets/docs/theme.doc.zh.mjs +9 -8
  260. package/assets/docs/tokens.doc.dense.mjs +2 -2
  261. package/assets/docs/tokens.doc.mjs +390 -9
  262. package/assets/docs/tokens.doc.zh.mjs +2 -2
  263. package/assets/docs/tree/add-a-component.doc.mjs +75 -0
  264. package/assets/docs/tree/add-a-theme.doc.mjs +85 -0
  265. package/assets/docs/tree/add-a-topic.doc.mjs +144 -0
  266. package/assets/docs/tree/agent-guidance.doc.mjs +138 -0
  267. package/assets/docs/tree/api.doc.mjs +30 -0
  268. package/assets/docs/tree/block-template.doc.mjs +130 -0
  269. package/assets/docs/tree/build-the-template.doc.mjs +28 -0
  270. package/assets/docs/tree/building-blocks.doc.mjs +46 -0
  271. package/assets/docs/tree/check-your-docs.doc.mjs +137 -0
  272. package/assets/docs/tree/checks.doc.mjs +119 -0
  273. package/assets/docs/tree/cli.doc.mjs +23 -0
  274. package/assets/docs/tree/codemods.doc.mjs +147 -0
  275. package/assets/docs/tree/commands.doc.mjs +25 -0
  276. package/assets/docs/tree/component-family.doc.mjs +113 -0
  277. package/assets/docs/tree/component-imports.doc.mjs +69 -0
  278. package/assets/docs/tree/component-lookups.doc.mjs +149 -0
  279. package/assets/docs/tree/components.doc.mjs +23 -0
  280. package/assets/docs/tree/configuration.doc.mjs +23 -0
  281. package/assets/docs/tree/debug-and-gap-reports.doc.mjs +182 -0
  282. package/assets/docs/tree/define-the-theme.doc.mjs +118 -0
  283. package/assets/docs/tree/describe-the-component.doc.mjs +57 -0
  284. package/assets/docs/tree/docs.doc.mjs +21 -0
  285. package/assets/docs/tree/document-the-template.doc.mjs +28 -0
  286. package/assets/docs/tree/document-the-theme.doc.mjs +68 -0
  287. package/assets/docs/tree/export-template-assets.doc.mjs +147 -0
  288. package/assets/docs/tree/extend-or-replace.doc.mjs +103 -0
  289. package/assets/docs/tree/fonts-and-assets.doc.mjs +106 -0
  290. package/assets/docs/tree/generate-a-palette.doc.mjs +66 -0
  291. package/assets/docs/tree/grade-template-with-agent.doc.mjs +105 -0
  292. package/assets/docs/tree/help.doc.mjs +16 -0
  293. package/assets/docs/tree/integrations.doc.mjs +40 -0
  294. package/assets/docs/tree/links.doc.mjs +98 -0
  295. package/assets/docs/tree/package-and-test.doc.mjs +32 -0
  296. package/assets/docs/tree/page-template.doc.mjs +71 -0
  297. package/assets/docs/tree/publishing.doc.mjs +111 -0
  298. package/assets/docs/tree/quick-start.doc.mjs +272 -0
  299. package/assets/docs/tree/replace-a-core-component.doc.mjs +104 -0
  300. package/assets/docs/tree/replace-a-core-template.doc.mjs +172 -0
  301. package/assets/docs/tree/sections-and-placement.doc.mjs +108 -0
  302. package/assets/docs/tree/see-it-in-an-app.doc.mjs +59 -0
  303. package/assets/docs/tree/ship.doc.mjs +16 -0
  304. package/assets/docs/tree/short-and-findable.doc.mjs +108 -0
  305. package/assets/docs/tree/single-component.doc.mjs +165 -0
  306. package/assets/docs/tree/start-a-template.doc.mjs +143 -0
  307. package/assets/docs/tree/subcomponent.doc.mjs +115 -0
  308. package/assets/docs/tree/template-assets.doc.mjs +64 -0
  309. package/assets/docs/tree/template-doc-overview.doc.mjs +109 -0
  310. package/assets/docs/tree/template-fonts.doc.mjs +102 -0
  311. package/assets/docs/tree/template-grading-rubric.doc.mjs +452 -0
  312. package/assets/docs/tree/template-icons.doc.mjs +97 -0
  313. package/assets/docs/tree/template-images-media.doc.mjs +127 -0
  314. package/assets/docs/tree/template-styles.doc.mjs +93 -0
  315. package/assets/docs/tree/templates.doc.mjs +34 -0
  316. package/assets/docs/tree/test-in-an-app.doc.mjs +115 -0
  317. package/assets/docs/tree/test-template-in-app.doc.mjs +128 -0
  318. package/assets/docs/tree/themes.doc.mjs +39 -0
  319. package/assets/docs/tree/troubleshooting.doc.mjs +149 -0
  320. package/assets/docs/tree/upgrading.doc.mjs +103 -0
  321. package/assets/docs/tree/use-a-theme-in-an-app.doc.mjs +51 -0
  322. package/assets/docs/tree/verify-packed-template.doc.mjs +77 -0
  323. package/assets/docs/tree/versioning.doc.mjs +161 -0
  324. package/assets/docs/tree/write-good-templates.doc.mjs +64 -0
  325. package/assets/docs/tree/write-the-template-file.doc.mjs +154 -0
  326. package/assets/docs/typography.doc.mjs +24 -4
  327. package/assets/docs/working-with-ai.doc.mjs +34 -26
  328. package/assets/templates/blocks/components/CheckboxList/CheckboxListSelectAllPattern.doc.mjs +1 -1
  329. package/assets/templates/blocks/components/CheckboxList/CheckboxListSelectAllPattern.tsx +1 -3
  330. package/assets/templates/blocks/components/DateInput/DateInputDateRange.tsx +1 -1
  331. package/assets/templates/blocks/components/InternationalizationProvider/InternationalizationProvider01ShippedLocale.tsx +1 -1
  332. package/assets/templates/blocks/components/Item/ItemDocumentTabs.doc.mjs +14 -0
  333. package/assets/templates/blocks/components/Item/ItemDocumentTabs.tsx +100 -0
  334. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaInlineRail.doc.mjs +14 -0
  335. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaInlineRail.tsx +61 -0
  336. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaOverscrollChaining.doc.mjs +14 -0
  337. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaOverscrollChaining.tsx +126 -0
  338. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaShowcase.doc.mjs +15 -0
  339. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaShowcase.tsx +86 -0
  340. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaStickyGroupHeaders.doc.mjs +14 -0
  341. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaStickyGroupHeaders.tsx +99 -0
  342. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaStickyPassthrough.doc.mjs +14 -0
  343. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaStickyPassthrough.tsx +122 -0
  344. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaTwoAxisBoard.doc.mjs +14 -0
  345. package/assets/templates/blocks/components/ScrollableArea/ScrollableAreaTwoAxisBoard.tsx +95 -0
  346. package/assets/templates/blocks/components/Table/TableBulkActionsTable.doc.mjs +14 -0
  347. package/assets/templates/blocks/components/Table/TableBulkActionsTable.tsx +71 -0
  348. package/assets/templates/blocks/components/Table/TableFloatingBulkActionsTable.doc.mjs +19 -0
  349. package/assets/templates/blocks/components/Table/TableFloatingBulkActionsTable.tsx +139 -0
  350. package/assets/templates/blocks/components/TimeInput/TimeInputConstrained.tsx +1 -0
  351. package/assets/templates/blocks/components/Timer/TimerFormats.doc.mjs +14 -0
  352. package/assets/templates/blocks/components/Timer/TimerFormats.tsx +34 -0
  353. package/assets/templates/blocks/components/Timer/TimerInline.doc.mjs +14 -0
  354. package/assets/templates/blocks/components/Timer/TimerInline.tsx +14 -0
  355. package/assets/templates/blocks/components/Timer/TimerShowcase.doc.mjs +13 -0
  356. package/assets/templates/blocks/components/Timer/TimerShowcase.tsx +47 -0
  357. package/assets/templates/blocks/components/Timer/TimerTypography.doc.mjs +14 -0
  358. package/assets/templates/blocks/components/Timer/TimerTypography.tsx +31 -0
  359. package/assets/templates/blocks/components/Toolbar/ToolbarTableFilter.doc.mjs +19 -3
  360. package/assets/templates/blocks/components/Toolbar/ToolbarTableFilter.tsx +383 -65
  361. package/assets/templates/pages/table-tree/page.tsx +1704 -0
  362. package/assets/templates/pages/table-tree/template.doc.mjs +12 -0
  363. package/assets/templates/themes/butter/butterTheme.doc.mjs +11 -0
  364. package/assets/templates/themes/chocolate/chocolateTheme.doc.mjs +11 -0
  365. package/assets/templates/themes/gothic/gothicTheme.doc.mjs +11 -0
  366. package/assets/templates/themes/matcha/matchaTheme.doc.mjs +11 -0
  367. package/assets/templates/themes/neutral/neutralTheme.doc.mjs +11 -0
  368. package/assets/templates/themes/stone/stoneTheme.doc.mjs +11 -0
  369. package/assets/templates/themes/y2k/y2kTheme.doc.mjs +11 -0
  370. package/authoring/_shared/contract.ts +22 -0
  371. package/authoring/codemod/codemod.doc.mjs +7 -2
  372. package/authoring/codemod/parse.d.mts +8 -8
  373. package/authoring/codemod/parse.mjs +8 -6
  374. package/authoring/codemod/type.ts +12 -0
  375. package/authoring/config/config.doc.mjs +11 -3
  376. package/authoring/config/debug-composition.test.mjs +92 -0
  377. package/authoring/config/parse.d.mts +15 -13
  378. package/authoring/config/parse.mjs +27 -8
  379. package/authoring/config/parse.test.mjs +8 -0
  380. package/authoring/config/type.ts +29 -6
  381. package/authoring/debug/debug.doc.d.mts +11 -0
  382. package/authoring/debug/debug.doc.mjs +182 -0
  383. package/authoring/debug/parse.d.mts +8 -8
  384. package/authoring/debug/parse.mjs +3 -3
  385. package/authoring/discover/discover.doc.d.mts +13 -0
  386. package/authoring/discover/discover.doc.mjs +138 -0
  387. package/authoring/discover/parse.d.mts +24 -0
  388. package/authoring/discover/parse.mjs +128 -0
  389. package/authoring/discover/parse.test.mjs +124 -0
  390. package/authoring/discover/type.ts +87 -0
  391. package/authoring/doctypes/_schema.d.mts +792 -24
  392. package/authoring/doctypes/_schema.mjs +549 -39
  393. package/authoring/doctypes/base/graph-fields.doc.d.mts +9 -0
  394. package/authoring/doctypes/base/graph-fields.doc.mjs +64 -0
  395. package/authoring/doctypes/base/type.ts +43 -0
  396. package/authoring/doctypes/command/command.doc.mjs +4 -3
  397. package/authoring/doctypes/command/parse.d.mts +2 -2
  398. package/authoring/doctypes/command/parse.mjs +1 -1
  399. package/authoring/doctypes/command/type.ts +5 -4
  400. package/authoring/doctypes/component/component.doc.mjs +12 -3
  401. package/authoring/doctypes/component/parse.d.mts +2 -2
  402. package/authoring/doctypes/component/parse.mjs +1 -1
  403. package/authoring/doctypes/component/type.ts +14 -5
  404. package/authoring/doctypes/doctypes-new.test.mjs +48 -6
  405. package/authoring/doctypes/enum/enum.doc.mjs +1 -1
  406. package/authoring/doctypes/enum/parse.d.mts +2 -2
  407. package/authoring/doctypes/enum/parse.mjs +1 -1
  408. package/authoring/doctypes/enum/type.ts +4 -2
  409. package/authoring/doctypes/function/function.doc.mjs +7 -2
  410. package/authoring/doctypes/function/parse.d.mts +2 -2
  411. package/authoring/doctypes/function/parse.mjs +1 -1
  412. package/authoring/doctypes/function/type.ts +9 -4
  413. package/authoring/doctypes/hook/hook.doc.mjs +4 -0
  414. package/authoring/doctypes/hook/parse.d.mts +2 -2
  415. package/authoring/doctypes/hook/parse.mjs +1 -1
  416. package/authoring/doctypes/hook/type.ts +5 -4
  417. package/authoring/doctypes/legacy.d.mts +8 -6
  418. package/authoring/doctypes/legacy.mjs +5 -4
  419. package/authoring/doctypes/load-contract.test.mjs +233 -0
  420. package/authoring/doctypes/namespace/namespace.doc.d.mts +9 -0
  421. package/authoring/doctypes/namespace/namespace.doc.mjs +128 -0
  422. package/authoring/doctypes/namespace/parse.d.mts +12 -0
  423. package/authoring/doctypes/namespace/parse.mjs +25 -0
  424. package/authoring/doctypes/namespace/parse.test.mjs +163 -0
  425. package/authoring/doctypes/namespace/type.ts +74 -0
  426. package/authoring/doctypes/parse.d.mts +22 -18
  427. package/authoring/doctypes/parse.mjs +22 -11
  428. package/authoring/doctypes/parse.test.mjs +77 -3
  429. package/authoring/doctypes/reference/parse.d.mts +2 -2
  430. package/authoring/doctypes/reference/parse.mjs +8 -5
  431. package/authoring/doctypes/reference/reference.doc.mjs +55 -6
  432. package/authoring/doctypes/reference/type.ts +75 -7
  433. package/authoring/doctypes/schema/parse.d.mts +2 -2
  434. package/authoring/doctypes/schema/parse.mjs +1 -1
  435. package/authoring/doctypes/schema/schema.doc.mjs +2 -2
  436. package/authoring/doctypes/schema/type.ts +4 -4
  437. package/authoring/doctypes/template/parse.d.mts +94 -1
  438. package/authoring/doctypes/template/parse.mjs +40 -2
  439. package/authoring/doctypes/template/parse.test.mjs +26 -2
  440. package/authoring/doctypes/template/template.doc.mjs +13 -3
  441. package/authoring/doctypes/template/type.ts +13 -2
  442. package/authoring/doctypes/theme/parse.d.mts +35 -0
  443. package/authoring/doctypes/theme/parse.mjs +76 -0
  444. package/authoring/doctypes/theme/theme.doc.d.mts +9 -0
  445. package/authoring/doctypes/theme/theme.doc.mjs +79 -0
  446. package/authoring/doctypes/theme/type.ts +42 -0
  447. package/authoring/doctypes/types.ts +12 -10
  448. package/authoring/gap-report/gap-report.doc.d.mts +12 -0
  449. package/authoring/gap-report/gap-report.doc.mjs +183 -0
  450. package/authoring/gap-report/parse.d.mts +10 -10
  451. package/authoring/gap-report/parse.mjs +6 -6
  452. package/authoring/gap-report/type.ts +1 -1
  453. package/authoring/identity/identity.doc.d.mts +9 -0
  454. package/authoring/identity/identity.doc.mjs +61 -0
  455. package/authoring/identity/type.ts +132 -0
  456. package/authoring/index.d.mts +3 -0
  457. package/authoring/index.d.ts +62 -17
  458. package/authoring/index.mjs +4 -1
  459. package/authoring/integration/integration.doc.mjs +22 -13
  460. package/authoring/integration/parse.d.mts +2 -2
  461. package/authoring/integration/parse.mjs +1 -1
  462. package/authoring/integration/parse.test.mjs +10 -1
  463. package/authoring/integration/schema.d.mts +6 -4
  464. package/authoring/integration/schema.mjs +9 -3
  465. package/authoring/integration/type.ts +19 -8
  466. package/authoring/shadcn/receipt.d.mts +6 -6
  467. package/clients/cli/__tests__/cliManifest.test.ts +27 -29
  468. package/clients/cli/command-load-failure.test.mjs +83 -0
  469. package/clients/cli/commands/blog.doc.mjs +1 -1
  470. package/clients/cli/commands/blog.mjs +23 -8
  471. package/clients/cli/commands/blog.test.mjs +42 -1
  472. package/clients/cli/commands/build-theme.adaptations.test.mjs +100 -1
  473. package/clients/cli/commands/build-theme.ascii-output.test.mjs +161 -0
  474. package/clients/cli/commands/build-theme.flag-docs.test.mjs +110 -0
  475. package/clients/cli/commands/build-theme.mjs +16 -50
  476. package/clients/cli/commands/build-theme.path-safety.test.mjs +86 -1
  477. package/clients/cli/commands/build-theme.variants.test.mjs +76 -0
  478. package/clients/cli/commands/build.doc.mjs +16 -8
  479. package/clients/cli/commands/build.exit-codes-doc.test.mjs +50 -0
  480. package/clients/cli/commands/build.mjs +137 -114
  481. package/clients/cli/commands/build.playbook.test.mjs +75 -0
  482. package/clients/cli/commands/build.text-fields.test.mjs +81 -0
  483. package/clients/cli/commands/component/index.mjs +153 -61
  484. package/clients/cli/commands/component-batch.test.mjs +341 -0
  485. package/clients/cli/commands/component-ownership.test.mjs +92 -3
  486. package/clients/cli/commands/component-package.test.mjs +46 -0
  487. package/clients/cli/commands/component-resolution.test.mjs +21 -0
  488. package/clients/cli/commands/component.doc.mjs +28 -10
  489. package/clients/cli/commands/component.test.mjs +19 -0
  490. package/clients/cli/commands/detail-levels.test.mjs +2 -2
  491. package/clients/cli/commands/discover.broken-integration.test.mjs +52 -5
  492. package/clients/cli/commands/discover.components-flag.test.mjs +97 -0
  493. package/clients/cli/commands/discover.doc.mjs +55 -9
  494. package/clients/cli/commands/discover.mjs +393 -118
  495. package/clients/cli/commands/discover.sources.test.mjs +267 -0
  496. package/clients/cli/commands/discover.text-projection.test.mjs +103 -0
  497. package/clients/cli/commands/docs.doc.mjs +28 -6
  498. package/clients/cli/commands/docs.mjs +295 -38
  499. package/clients/cli/commands/doctor-integration-components.doc.mjs +1 -1
  500. package/clients/cli/commands/doctor-integration-docs.doc.mjs +6 -5
  501. package/clients/cli/commands/doctor-integration-templates.doc.mjs +15 -8
  502. package/clients/cli/commands/doctor-integration-validate.doc.mjs +1 -1
  503. package/clients/cli/commands/doctor-integration.doc.mjs +1 -1
  504. package/clients/cli/commands/doctor-integration.package-json.test.mjs +53 -0
  505. package/clients/cli/commands/doctor-integration.test.mjs +143 -8
  506. package/clients/cli/commands/doctor.doc.mjs +4 -2
  507. package/clients/cli/commands/doctor.mjs +108 -37
  508. package/clients/cli/commands/doctor.test.mjs +42 -0
  509. package/clients/cli/commands/gap-report.doc.mjs +27 -15
  510. package/clients/cli/commands/gap-report.test.mjs +72 -0
  511. package/clients/cli/commands/hook/index.mjs +7 -17
  512. package/clients/cli/commands/hook.doc.mjs +1 -1
  513. package/clients/cli/commands/hook.text-projection.test.mjs +45 -0
  514. package/clients/cli/commands/init.doc.mjs +24 -10
  515. package/clients/cli/commands/init.flag-help.test.mjs +153 -0
  516. package/clients/cli/commands/integration-add.controls.test.mjs +132 -0
  517. package/clients/cli/commands/integration-add.doc.mjs +39 -13
  518. package/clients/cli/commands/integration-authoring.test.mjs +74 -19
  519. package/clients/cli/commands/integration-pack.doc.mjs +6 -10
  520. package/clients/cli/commands/integration-real-world.test.mjs +4 -10
  521. package/clients/cli/commands/integration-verify.doc.mjs +22 -0
  522. package/clients/cli/commands/integration.doc.mjs +5 -5
  523. package/clients/cli/commands/integration.mjs +75 -43
  524. package/clients/cli/commands/interactive-guard.test.mjs +101 -24
  525. package/clients/cli/commands/json-contract.test.mjs +33 -0
  526. package/clients/cli/commands/layout-check.doc.mjs +15 -4
  527. package/clients/cli/commands/layout-expand.doc.mjs +22 -5
  528. package/clients/cli/commands/layout-grammar.doc.mjs +1 -1
  529. package/clients/cli/commands/layout.doc.mjs +3 -3
  530. package/clients/cli/commands/layout.mjs +21 -9
  531. package/clients/cli/commands/layout.path-help.test.mjs +33 -0
  532. package/clients/cli/commands/layout.stdin-cap.test.mjs +47 -0
  533. package/clients/cli/commands/layout.text-fields.test.mjs +39 -0
  534. package/clients/cli/commands/manifest.doc.mjs +2 -2
  535. package/clients/cli/commands/no-prompt-wording.test.mjs +94 -0
  536. package/clients/cli/commands/search.doc.mjs +16 -6
  537. package/clients/cli/commands/search.mjs +49 -11
  538. package/clients/cli/commands/search.test.mjs +92 -0
  539. package/clients/cli/commands/setup-nudge.test.mjs +6 -0
  540. package/clients/cli/commands/swizzle.doc.mjs +4 -3
  541. package/clients/cli/commands/swizzle.path-safety.test.mjs +42 -0
  542. package/clients/cli/commands/template.doc.mjs +53 -14
  543. package/clients/cli/commands/template.flag-help.test.mjs +117 -0
  544. package/clients/cli/commands/template.mjs +4 -91
  545. package/clients/cli/commands/template.path-help.test.mjs +40 -0
  546. package/clients/cli/commands/text-json-parity.test.mjs +725 -0
  547. package/clients/cli/commands/theme-add.doc.mjs +5 -4
  548. package/clients/cli/commands/theme-build.doc.mjs +8 -7
  549. package/clients/cli/commands/theme-list.doc.mjs +2 -2
  550. package/clients/cli/commands/theme-palette-generate.doc.mjs +12 -7
  551. package/clients/cli/commands/theme-palette-generate.test.mjs +19 -0
  552. package/clients/cli/commands/theme-palette.doc.mjs +2 -3
  553. package/clients/cli/commands/theme-targets.behavior.test.mjs +4 -3
  554. package/clients/cli/commands/theme-targets.doc.mjs +3 -3
  555. package/clients/cli/commands/theme-template.behavior.test.mjs +12 -0
  556. package/clients/cli/commands/theme-template.doc.mjs +2 -2
  557. package/clients/cli/commands/theme.doc.mjs +3 -2
  558. package/clients/cli/commands/upgrade.ascii-output.test.mjs +87 -0
  559. package/clients/cli/commands/upgrade.doc.mjs +83 -12
  560. package/clients/cli/commands/upgrade.file-protection.test.mjs +228 -0
  561. package/clients/cli/commands/upgrade.flag-help.test.mjs +188 -0
  562. package/clients/cli/commands/upgrade.hook-output.test.mjs +88 -0
  563. package/clients/cli/commands/upgrade.mjs +29 -7
  564. package/clients/cli/formatters/index.mjs +164 -1
  565. package/clients/cli/formatters/index.test.mjs +97 -0
  566. package/clients/cli/index.mjs +47 -34
  567. package/clients/cli/latest-version-env.test.mjs +50 -0
  568. package/clients/cli/lib/cli-error.test.mjs +7 -0
  569. package/clients/cli/lib/component-format.mjs +9 -9
  570. package/clients/cli/lib/component-format.test.mjs +1 -1
  571. package/clients/cli/lib/define-command.mjs +56 -6
  572. package/clients/cli/lib/define-command.test.mjs +54 -0
  573. package/clients/cli/lib/doc-text-ascii.test.mjs +82 -0
  574. package/clients/cli/lib/exit-codes.test.mjs +113 -0
  575. package/clients/cli/lib/hook-format.mjs +19 -10
  576. package/clients/cli/lib/json-shim.mjs +62 -16
  577. package/clients/cli/lib/json-shim.test.mjs +83 -0
  578. package/clients/cli/lib/manifest.d.ts +2 -0
  579. package/clients/cli/lib/manifest.mjs +53 -6
  580. package/clients/cli/lib/manifest.test.mjs +22 -2
  581. package/clients/cli/lib/parse-error-format.test.mjs +81 -0
  582. package/foundation/agent-docs/agent-docs.d.mts +7 -2
  583. package/foundation/agent-docs/agent-docs.mjs +83 -13
  584. package/foundation/agent-docs/agent-docs.path-safety.test.mjs +266 -4
  585. package/foundation/config/integration-debug.test.mjs +28 -3
  586. package/foundation/config/project-themes.test.mjs +11 -19
  587. package/foundation/config/project.d.mts +20 -11
  588. package/foundation/config/project.mjs +263 -91
  589. package/foundation/config/project.test.mjs +270 -21
  590. package/foundation/discovery/authoring-self-docs.d.mts +87 -0
  591. package/foundation/discovery/authoring-self-docs.mjs +237 -0
  592. package/foundation/discovery/authoring-self-docs.test.mjs +174 -0
  593. package/foundation/discovery/authoring-surface.d.mts +74 -0
  594. package/foundation/discovery/authoring-surface.mjs +525 -0
  595. package/foundation/discovery/authoring-surface.test.mjs +392 -0
  596. package/foundation/discovery/cli-self-docs.d.mts +119 -0
  597. package/foundation/discovery/cli-self-docs.mjs +504 -0
  598. package/foundation/discovery/cli-self-docs.test.mjs +395 -0
  599. package/foundation/discovery/component-discovery.d.mts +39 -1
  600. package/foundation/discovery/component-discovery.mjs +50 -1
  601. package/foundation/discovery/component-loader.d.mts +35 -38
  602. package/foundation/discovery/component-loader.mjs +53 -222
  603. package/foundation/discovery/docs-discovery.d.mts +119 -11
  604. package/foundation/discovery/docs-discovery.mjs +427 -108
  605. package/foundation/discovery/docs-discovery.test.mjs +386 -20
  606. package/foundation/discovery/docs-output-budget.d.mts +28 -0
  607. package/foundation/discovery/docs-output-budget.mjs +50 -0
  608. package/foundation/discovery/docs-section-key.d.mts +116 -0
  609. package/foundation/discovery/docs-section-key.mjs +322 -0
  610. package/foundation/discovery/docs-section-key.test.mjs +246 -0
  611. package/foundation/discovery/template-adapter.d.mts +113 -11
  612. package/foundation/discovery/template-adapter.fixture-refs.test.mjs +248 -0
  613. package/foundation/discovery/template-adapter.integration-isolation.test.mjs +94 -0
  614. package/foundation/discovery/template-adapter.mjs +774 -83
  615. package/foundation/discovery/template-adapter.test.mjs +57 -0
  616. package/foundation/discovery/template-conflict-release.d.mts +13 -0
  617. package/foundation/discovery/template-conflict-release.mjs +40 -0
  618. package/foundation/discovery/template-conflict-release.test.mjs +40 -0
  619. package/foundation/discovery/theme-discovery.d.mts +67 -7
  620. package/foundation/discovery/theme-discovery.mjs +916 -186
  621. package/foundation/discovery/theme-discovery.test.mjs +613 -219
  622. package/foundation/discovery/theming-targets.test.mjs +4 -0
  623. package/foundation/doc-compiler/bundle.d.mts +47 -0
  624. package/foundation/doc-compiler/bundle.mjs +278 -0
  625. package/foundation/doc-compiler/bundle.test.mjs +266 -0
  626. package/foundation/doc-compiler/compile.d.mts +343 -0
  627. package/foundation/doc-compiler/compile.mjs +558 -0
  628. package/foundation/doc-compiler/diagnostics.d.mts +126 -0
  629. package/foundation/doc-compiler/diagnostics.mjs +305 -0
  630. package/foundation/doc-compiler/doc-compiler.test.mjs +714 -0
  631. package/foundation/doc-compiler/doc-loads.test.mjs +1643 -0
  632. package/foundation/doc-compiler/import.d.mts +24 -0
  633. package/foundation/doc-compiler/import.mjs +59 -0
  634. package/foundation/doc-compiler/inputs.d.mts +102 -0
  635. package/foundation/doc-compiler/inputs.mjs +291 -0
  636. package/foundation/doc-compiler/inputs.test.mjs +298 -0
  637. package/foundation/doc-compiler/ir.d.mts +22 -0
  638. package/foundation/doc-compiler/ir.mjs +471 -0
  639. package/foundation/doc-compiler/lenses.d.mts +36 -0
  640. package/foundation/doc-compiler/lenses.mjs +173 -0
  641. package/foundation/doc-compiler/links.d.mts +162 -0
  642. package/foundation/doc-compiler/links.mjs +294 -0
  643. package/foundation/doc-compiler/links.test.mjs +192 -0
  644. package/foundation/doc-compiler/lower-doc.test.mjs +495 -0
  645. package/foundation/doc-compiler/overlays.d.mts +37 -0
  646. package/foundation/doc-compiler/overlays.mjs +206 -0
  647. package/foundation/doc-compiler/parse-readable.d.mts +9 -0
  648. package/foundation/doc-compiler/parse-readable.mjs +29 -0
  649. package/foundation/doc-compiler/read.d.mts +127 -0
  650. package/foundation/doc-compiler/read.mjs +325 -0
  651. package/foundation/doc-compiler/read.test.mjs +313 -0
  652. package/foundation/doc-compiler/source.d.mts +33 -0
  653. package/foundation/doc-compiler/source.mjs +128 -0
  654. package/foundation/doc-compiler/tree.d.mts +292 -0
  655. package/foundation/doc-compiler/tree.mjs +881 -0
  656. package/foundation/fs/file-protection.d.mts +33 -0
  657. package/foundation/fs/file-protection.mjs +825 -0
  658. package/foundation/fs/file-protection.test.mjs +250 -0
  659. package/foundation/fs/module-loader.d.mts +1 -0
  660. package/foundation/fs/module-loader.mjs +50 -1
  661. package/foundation/fs/module-loader.stdout.test.mjs +332 -0
  662. package/foundation/fs/path-safety.d.mts +3 -2
  663. package/foundation/fs/path-safety.mjs +49 -19
  664. package/foundation/fs/path-safety.test.mjs +50 -0
  665. package/foundation/fs/publish-file-hardlink-unavailable.test.mjs +129 -94
  666. package/foundation/identity/provider-identity.d.mts +90 -0
  667. package/foundation/identity/provider-identity.mjs +320 -0
  668. package/foundation/identity/provider-identity.test.mjs +254 -0
  669. package/foundation/identity/providers.d.mts +7 -0
  670. package/foundation/identity/providers.mjs +16 -0
  671. package/foundation/integrations/autolink.d.mts +58 -1
  672. package/foundation/integrations/autolink.mjs +143 -45
  673. package/foundation/integrations/autolink.test.mjs +1 -1
  674. package/foundation/integrations/cli-requirement.d.mts +65 -0
  675. package/foundation/integrations/cli-requirement.mjs +189 -0
  676. package/foundation/integrations/cli-requirement.test.mjs +89 -0
  677. package/foundation/integrations/contribution-fixes.d.mts +145 -0
  678. package/foundation/integrations/contribution-fixes.mjs +1284 -0
  679. package/foundation/integrations/contribution-inventory.d.mts +3 -2
  680. package/foundation/integrations/contribution-inventory.mjs +28 -25
  681. package/foundation/integrations/contribution-inventory.test.mjs +86 -27
  682. package/foundation/integrations/integration-warnings.d.mts +9 -2
  683. package/foundation/integrations/integration-warnings.mjs +52 -21
  684. package/foundation/integrations/integration-warnings.test.mjs +74 -1
  685. package/foundation/integrations/integrations.d.mts +63 -3
  686. package/foundation/integrations/integrations.mjs +122 -9
  687. package/foundation/integrations/integrations.test.mjs +415 -1
  688. package/foundation/integrations/provider-conflicts.test.mjs +125 -0
  689. package/foundation/integrations/provider-ledger.test.mjs +275 -0
  690. package/foundation/integrations/provider-resolution.d.mts +152 -0
  691. package/foundation/integrations/provider-resolution.mjs +576 -0
  692. package/foundation/integrations/provider-resolution.test.mjs +369 -0
  693. package/foundation/integrations/theme-descriptor.d.mts +8 -0
  694. package/foundation/integrations/theme-descriptor.mjs +44 -0
  695. package/foundation/integrations/validate-contributions.d.mts +2 -0
  696. package/foundation/integrations/validate-contributions.mjs +131 -29
  697. package/foundation/response/base.d.ts +8 -4
  698. package/foundation/response/batch.type.d.mts +33 -0
  699. package/foundation/response/batch.type.mjs +34 -0
  700. package/foundation/response/error-codes.d.mts +3 -1
  701. package/foundation/response/error-codes.d.ts +2 -0
  702. package/foundation/response/error-codes.doc.mjs +19 -12
  703. package/foundation/response/error-codes.mjs +8 -2
  704. package/foundation/response/error-codes.test.mjs +166 -14
  705. package/foundation/response/json-contract.test.mjs +57 -17
  706. package/foundation/response/json.d.mts +4 -2
  707. package/foundation/response/json.mjs +8 -10
  708. package/foundation/response/response-types.doc.d.mts +7 -2
  709. package/foundation/response/response-types.doc.mjs +69 -25
  710. package/foundation/response/response-types.doc.test.mjs +181 -0
  711. package/foundation/response/response.doc.mjs +12 -11
  712. package/foundation/text/string-utils.d.mts +8 -0
  713. package/foundation/text/string-utils.mjs +40 -10
  714. package/foundation/xle/expand.d.mts +2 -0
  715. package/foundation/xle/expand.mjs +4 -3
  716. package/foundation/xle/expand.test.mjs +54 -0
  717. package/foundation/xle/xle.test.mjs +13 -0
  718. package/package.json +10 -11
  719. package/api/docs/docs.test.mjs +0 -83
  720. package/api/docs/integrationDocs.test.mjs +0 -208
  721. package/api/search/search.test.mjs +0 -389
  722. package/assets/docs/cli-integrations.doc.mjs +0 -367
  723. package/assets/templates/themes/manifest.json +0 -95
  724. package/clients/cli/commands/docs.test.mjs +0 -102
  725. package/clients/cli/lib/update-check.mjs +0 -83
  726. package/clients/cli/lib/update-check.test.mjs +0 -137
  727. package/clients/cli/update-hint-commands.test.mjs +0 -54
  728. package/foundation/agent-docs/agent-docs.test.mjs +0 -1141
@@ -0,0 +1,881 @@
1
+ // Copyright (c) Meta Platforms, Inc. and affiliates.
2
+
3
+ /**
4
+ * @file The docs tree: one home for every doc that a namespace places or
5
+ * adopts (spec:AST-046).
6
+ *
7
+ * @input Namespace docs, guides that name a parent with `placement`, and typed
8
+ * docs that belong to a discovery group (a CLI typed doc's `namespace`).
9
+ * @output {@link buildDocsTree}: every node by route, each with one parent and
10
+ * ordered children per slot, plus one diagnostic for each placement that
11
+ * failed. {@link loadDocsTree} builds the CLI's own tree once per process.
12
+ * @position Between discovery and the readers: `astryx docs <route>`,
13
+ * `astryx doctor`, and the docsite build all read this tree. The CLI's docs
14
+ * and each integration's have a home here, and a flat topic's home is the
15
+ * generated Unorganized level.
16
+ * A namespace never scans files and never lists its children: a child names
17
+ * its parent, or a namespace adopts a discovery group.
18
+ */
19
+
20
+ import * as fs from 'node:fs';
21
+ import * as path from 'node:path';
22
+ import {CLI_ROOT} from '../fs/paths.mjs';
23
+ import {loadCliSelfDocs} from '../discovery/cli-self-docs.mjs';
24
+ import {routeSegment} from '../discovery/docs-section-key.mjs';
25
+ import {diagnostic, sortDiagnostics} from './diagnostics.mjs';
26
+ import {readDocView} from './read.mjs';
27
+ import {packageSource} from './source.mjs';
28
+ import {createDocId} from '../identity/provider-identity.mjs';
29
+ import {CLI_PROVIDER_ID} from '../identity/providers.mjs';
30
+
31
+ export {routeSegment};
32
+
33
+ /** Where the CLI keeps the docs that only the tree reads. */
34
+ export const TREE_DOCS_DIR = path.join(CLI_ROOT, 'assets', 'docs', 'tree');
35
+
36
+ /** The package that owns the CLI's own docs. */
37
+ const CLI_PROVIDER = '@astryxdesign/cli';
38
+
39
+ /** One route segment: lowercase letters and digits joined by single hyphens. */
40
+ export const ROUTE_SEGMENT_RE = /^[a-z0-9]+(?:-[a-z0-9]+)*$/;
41
+
42
+ /**
43
+ * The generated level that `groupBy: 'kind'` makes for each kind: its route
44
+ * segment, title, and summary.
45
+ * @type {Readonly<Record<string, {segment: string, title: string, summary: string}>>}
46
+ */
47
+ export const KIND_GROUPS = Object.freeze({
48
+ command: {
49
+ segment: 'commands',
50
+ title: 'Commands',
51
+ summary: 'Every command and subcommand.',
52
+ },
53
+ function: {
54
+ segment: 'functions',
55
+ title: 'Functions',
56
+ summary: 'Every function: its signature, parameters, returns, and errors.',
57
+ },
58
+ schema: {
59
+ segment: 'schemas',
60
+ title: 'Schemas',
61
+ summary: 'Data shapes, field by field.',
62
+ },
63
+ enum: {
64
+ segment: 'enums',
65
+ title: 'Enums',
66
+ summary:
67
+ 'Every fixed list of values, such as error codes and response types.',
68
+ },
69
+ generic: {segment: 'guides', title: 'Guides', summary: 'Every guide.'},
70
+ });
71
+
72
+ /**
73
+ * @typedef {import('../../authoring/doctypes/namespace/type').NamespaceDoc} NamespaceDoc
74
+ * @typedef {import('../../authoring/doctypes/base/type').DocPlacement} DocPlacement
75
+ * @typedef {import('./diagnostics.mjs').CompilerDiagnostic} CompilerDiagnostic
76
+ */
77
+
78
+ /**
79
+ * @typedef {object} TreeNamespaceInput
80
+ * @property {string} provider the package that owns the namespace
81
+ * @property {string} providerId the provider's ProviderId (its manifest
82
+ * `providerId`, else its package name); node ids are built from it
83
+ * @property {number} [rank] which provider wins a contested route: the CLI's
84
+ * own docs are 0, then each integration in configured order
85
+ * @property {string} source `<package>/<path>` of its file
86
+ * @property {NamespaceDoc} doc
87
+ */
88
+
89
+ /**
90
+ * @typedef {object} TreeDocInput
91
+ * @property {string} provider the package that authored the doc
92
+ * @property {string} providerId the provider's ProviderId (its manifest
93
+ * `providerId`, else its package name); node ids are built from it
94
+ * @property {number} [rank] which provider wins a contested route: the CLI's
95
+ * own docs are 0, then each integration in configured order
96
+ * @property {string} source
97
+ * @property {import('../../authoring/doctypes/base/type').AuthoredDocKind} kind
98
+ * the authored kind: `generic`, `command`, `function`, `schema`, or `enum`
99
+ * @property {string} name the doc's stable name
100
+ * @property {string} title
101
+ * @property {string} summary
102
+ * @property {string | null} group the discovery group adoption reads, or null
103
+ * @property {DocPlacement | undefined} placement
104
+ * @property {any} [ref] what a reader needs to open the doc, carried as given
105
+ */
106
+
107
+ /**
108
+ * @typedef {object} TreeSlot
109
+ * @property {string} name
110
+ * @property {string} title
111
+ * @property {string[]} children child routes, in reading order
112
+ */
113
+
114
+ /**
115
+ * A flat topic: a reference topic that no namespace places. The tree gives it
116
+ * a home in the generated Unorganized level, under its own name.
117
+ * @typedef {object} TreeTopicInput
118
+ * @property {string} provider the package that owns the topic
119
+ * @property {string} providerId the provider's ProviderId
120
+ * @property {string} name the topic's name, which stays its route
121
+ * @property {string} title
122
+ * @property {string} summary
123
+ * @property {string} source where the topic comes from, for diagnostics
124
+ * @property {string[]} [aliases] every other name the topic answers to: the
125
+ * topics it replaced, directly or through a chain
126
+ */
127
+
128
+ /** The route of the generated level that holds every flat topic. */
129
+ export const UNORGANIZED = 'unorganized';
130
+
131
+ /**
132
+ * @typedef {object} TreeNode
133
+ * @property {string | null} id the doc's DocId, built from its provider's
134
+ * ProviderId, kind, and name: stable when the route moves; null on a
135
+ * generated level, which has no authored doc
136
+ * @property {string} route
137
+ * @property {string} kind `namespace` or the doc's authored kind
138
+ * @property {string} provider the package that owns it
139
+ * @property {string} providerId its provider's ProviderId
140
+ * @property {string} name
141
+ * @property {string} title
142
+ * @property {string} summary
143
+ * @property {string[]} [keywords] an authored namespace's search keywords
144
+ * @property {string | null} parent the parent's route; null at the top
145
+ * @property {string | null} slot the parent slot this node sits in
146
+ * @property {number | null} order
147
+ * @property {boolean} generated made by the compiler (a `groupBy: 'kind'`
148
+ * level, or the Unorganized level), not authored
149
+ * @property {TreeSlot[]} slots a namespace's slots; empty for a leaf
150
+ * @property {string} source
151
+ * @property {any} [ref]
152
+ */
153
+
154
+ /**
155
+ * @typedef {object} DocsTree
156
+ * @property {Map<string, TreeNode>} nodes by route, in route order
157
+ * @property {CompilerDiagnostic[]} diagnostics sorted
158
+ * @property {(route: string) => TreeNode | undefined} get
159
+ * @property {(route: string) => TreeNode | undefined} getFolded the node at a
160
+ * route compared without case, as topic names are
161
+ * @property {() => TreeNode[]} roots the namespaces with no parent
162
+ * @property {(node: TreeNode) => TreeNode[]} ancestors top first, not the node
163
+ */
164
+
165
+ /** @param {string} a @param {string} b */
166
+ const byText = (a, b) => (a < b ? -1 : a > b ? 1 : 0);
167
+
168
+ /**
169
+ * The namespace a `placement.parent` names: `namespace:<name>` in the doc's own
170
+ * package, or `<package>/namespace/<name>` spelled out. In phase 1 a parent
171
+ * must belong to the doc's own package.
172
+ * @param {string} parent
173
+ * @param {string} provider
174
+ * @param {Map<string, TreeNamespaceInput>} declared by `provider\0name`
175
+ * @returns {{key: string} | {error: string}}
176
+ */
177
+ function resolveParent(parent, provider, declared) {
178
+ let owner = provider;
179
+ let name;
180
+ const short = /^namespace:(.+)$/u.exec(parent);
181
+ const qualified = /^(.+)\/namespace\/([^/]+)$/u.exec(parent);
182
+ if (short) {
183
+ name = short[1];
184
+ } else if (qualified) {
185
+ [, owner, name] = qualified;
186
+ } else {
187
+ return {
188
+ error: `placement.parent "${parent}" is not a namespace reference. Write "namespace:<name>".`,
189
+ };
190
+ }
191
+ if (owner !== provider) {
192
+ return {
193
+ error: `placement.parent "${parent}" belongs to ${owner}. A doc can only be placed in a namespace of its own package (${provider}).`,
194
+ };
195
+ }
196
+ const key = `${owner}\u0000${name}`;
197
+ if (!declared.has(key)) {
198
+ return {
199
+ error: `placement.parent "${parent}" names no namespace; ${provider} declares ${
200
+ [...declared.values()]
201
+ .filter(ns => ns.provider === provider)
202
+ .map(ns => `"${ns.doc.name}"`)
203
+ .sort(byText)
204
+ .join(', ') || 'none'
205
+ }.`,
206
+ };
207
+ }
208
+ return {key};
209
+ }
210
+
211
+ /**
212
+ * Build the tree. Pure: the same inputs give the same tree, whatever order
213
+ * they arrive in.
214
+ *
215
+ * A doc's home is decided once, in this order: its explicit `placement`, then
216
+ * the one adoption rule in its package that matches its group and kind. A
217
+ * placement that fails withdraws the doc; it never falls back to adoption. A
218
+ * doc with neither is a flat topic: it keeps its flat name as its route, and its
219
+ * home is the generated Unorganized level. The CLI keeps its own routes: an
220
+ * integration's node that would take one is withdrawn with a diagnostic.
221
+ *
222
+ * @param {{namespaces: TreeNamespaceInput[], docs: TreeDocInput[], topics?: TreeTopicInput[]}} inputs
223
+ * @returns {DocsTree}
224
+ */
225
+ export function buildDocsTree({namespaces, docs, topics = []}) {
226
+ /** @type {CompilerDiagnostic[]} */
227
+ const diagnostics = [];
228
+ /** @param {string} code @param {{provider: string, source: string}} at @param {string} message @param {string} [field] */
229
+ const report = (code, at, message, field) =>
230
+ diagnostics.push(
231
+ diagnostic(code, {
232
+ provider: at.provider,
233
+ source: at.source,
234
+ message,
235
+ ...(field ? {field} : {}),
236
+ }),
237
+ );
238
+
239
+ // Routes the CLI's own docs keep (spec:AST-046 FR11): the name of each of
240
+ // its flat topics, and the generated Unorganized level. Its namespaces keep
241
+ // theirs by rank, because they go into the tree first. Routes compare
242
+ // without case, as topic names do, so `CLI` claims `cli`.
243
+ const cliRoutes = new Set(topics.length > 0 ? [UNORGANIZED] : []);
244
+ for (const topic of topics) {
245
+ if (topic.provider === CLI_PROVIDER) cliRoutes.add(topic.name.toLowerCase());
246
+ }
247
+ // Every other name a topic answers to (the topics it replaced, directly or
248
+ // through a chain) is that topic's route too: `astryx docs <name>` opens the
249
+ // replacement, so no other doc can hold it.
250
+ /** @type {Map<string, TreeTopicInput>} */
251
+ const aliasRoutes = new Map();
252
+ for (const topic of topics) {
253
+ for (const alias of topic.aliases ?? []) {
254
+ aliasRoutes.set(alias.toLowerCase(), topic);
255
+ }
256
+ }
257
+
258
+ // Namespaces by package and name.
259
+ /** @type {Map<string, TreeNamespaceInput>} */
260
+ const declared = new Map();
261
+ const sortedNamespaces = [...namespaces].sort(
262
+ (a, b) =>
263
+ (a.rank ?? 0) - (b.rank ?? 0) ||
264
+ byText(a.provider, b.provider) ||
265
+ byText(a.doc.name, b.doc.name) ||
266
+ byText(a.source, b.source),
267
+ );
268
+ for (const input of sortedNamespaces) {
269
+ const {name} = input.doc;
270
+ if (!ROUTE_SEGMENT_RE.test(name)) {
271
+ report(
272
+ 'invalid_namespace',
273
+ input,
274
+ `Namespace "${name}" is not a route segment. Use lowercase letters and digits joined by single hyphens.`,
275
+ 'name',
276
+ );
277
+ continue;
278
+ }
279
+ const key = `${input.provider}\u0000${name}`;
280
+ const first = declared.get(key);
281
+ if (first) {
282
+ report(
283
+ 'invalid_namespace',
284
+ input,
285
+ `Namespace "${name}" is declared twice in ${input.provider}: ${first.source} and ${input.source}.`,
286
+ 'name',
287
+ );
288
+ continue;
289
+ }
290
+ declared.set(key, input);
291
+ }
292
+
293
+ // Each namespace's parent, checked against the parent's slots.
294
+ /** @type {Map<string, {parentKey: string, slot: string, order: number | null} | null>} */
295
+ const parentOf = new Map();
296
+ for (const [key, input] of declared) {
297
+ const {placement} = input.doc;
298
+ if (placement == null) {
299
+ parentOf.set(key, null);
300
+ continue;
301
+ }
302
+ const home = checkPlacement(placement, 'namespace', input, declared);
303
+ if ('error' in home) {
304
+ report('invalid_placement', input, home.error, 'placement');
305
+ continue;
306
+ }
307
+ parentOf.set(key, {
308
+ parentKey: home.key,
309
+ slot: home.slot,
310
+ order: placement.order ?? null,
311
+ });
312
+ }
313
+
314
+ // Routes, top-down. A cycle, or an ancestor that was withdrawn, leaves a
315
+ // namespace (and everything under it) out of the tree.
316
+ /** @type {Map<string, string | null>} */
317
+ const routeOf = new Map();
318
+ /** @param {string} key @param {Set<string>} seen @returns {string | null} */
319
+ const routeFor = (key, seen) => {
320
+ if (routeOf.has(key))
321
+ return /** @type {string | null} */ (routeOf.get(key));
322
+ if (!parentOf.has(key) || seen.has(key)) return null;
323
+ seen.add(key);
324
+ const home = parentOf.get(key);
325
+ const name = /** @type {TreeNamespaceInput} */ (declared.get(key)).doc.name;
326
+ const parentRoute = home == null ? '' : routeFor(home.parentKey, seen);
327
+ const route =
328
+ parentRoute == null
329
+ ? null
330
+ : parentRoute === ''
331
+ ? name
332
+ : `${parentRoute}/${name}`;
333
+ routeOf.set(key, route);
334
+ return route;
335
+ };
336
+ for (const [key, input] of declared) {
337
+ if (routeFor(key, new Set()) == null && parentOf.has(key)) {
338
+ report(
339
+ 'invalid_placement',
340
+ input,
341
+ `Namespace "${input.doc.name}" has no route: its placement forms a cycle, or a namespace above it was withdrawn.`,
342
+ 'placement',
343
+ );
344
+ }
345
+ }
346
+
347
+ /** @type {Map<string, TreeNode>} */
348
+ const nodes = new Map();
349
+ /** @type {Map<string, TreeNode>} nodes by route, compared without case */
350
+ const byFoldedRoute = new Map();
351
+ /** @param {TreeNode} node */
352
+ const nodeLabel = node => node.id ?? `the generated level "${node.route}"`;
353
+ /** @param {TreeNode} node @param {{provider: string, source: string}} at */
354
+ const addNode = (node, at) => {
355
+ const folded = node.route.toLowerCase();
356
+ if (node.provider !== CLI_PROVIDER && cliRoutes.has(folded)) {
357
+ report(
358
+ 'duplicate_route',
359
+ at,
360
+ `${nodeLabel(node)} takes the route "${node.route}", which the CLI's own docs keep. Rename it.`,
361
+ );
362
+ return false;
363
+ }
364
+ const alias = aliasRoutes.get(folded);
365
+ if (
366
+ alias != null &&
367
+ node.provider !== CLI_PROVIDER &&
368
+ node.ref?.flatTopic !== alias.name
369
+ ) {
370
+ report(
371
+ 'duplicate_route',
372
+ at,
373
+ `${nodeLabel(node)} takes the route "${node.route}", which the topic "${alias.name}" also answers to, because it replaced a topic of that name. Rename it.`,
374
+ );
375
+ return false;
376
+ }
377
+ const taken = byFoldedRoute.get(folded);
378
+ if (taken) {
379
+ report(
380
+ 'duplicate_route',
381
+ at,
382
+ `${nodeLabel(node)} and ${nodeLabel(taken)} both have the route "${node.route}". Rename or move one of them.`,
383
+ );
384
+ return false;
385
+ }
386
+ nodes.set(node.route, node);
387
+ byFoldedRoute.set(folded, node);
388
+ return true;
389
+ };
390
+
391
+ // Parents before children, so a namespace placed in a withdrawn namespace
392
+ // is withdrawn before anything is placed in it.
393
+ const parentsFirst = [...declared].sort(
394
+ ([a], [b]) =>
395
+ String(routeOf.get(a) ?? '').split('/').length -
396
+ String(routeOf.get(b) ?? '').split('/').length,
397
+ );
398
+ for (const [key, input] of parentsFirst) {
399
+ const route = routeOf.get(key);
400
+ if (route == null) continue;
401
+ const home = parentOf.get(key);
402
+ if (home != null && routeOf.get(home.parentKey) == null) {
403
+ routeOf.set(key, null);
404
+ report(
405
+ 'invalid_placement',
406
+ input,
407
+ `Namespace "${input.doc.name}" has no route: the namespace it is placed in was withdrawn.`,
408
+ 'placement',
409
+ );
410
+ continue;
411
+ }
412
+ const parentRoute =
413
+ home == null ? null : /** @type {string} */ (routeOf.get(home.parentKey));
414
+ const added = addNode(
415
+ {
416
+ id: createDocId(input.providerId, 'namespace', input.doc.name),
417
+ route,
418
+ kind: 'namespace',
419
+ provider: input.provider,
420
+ providerId: input.providerId,
421
+ name: input.doc.name,
422
+ title: input.doc.title,
423
+ summary: input.doc.summary,
424
+ ...(Array.isArray(input.doc.keywords)
425
+ ? {keywords: input.doc.keywords}
426
+ : {}),
427
+ parent: parentRoute,
428
+ slot: home?.slot ?? null,
429
+ order: home?.order ?? null,
430
+ generated: false,
431
+ ref: {selfDoc: input.doc},
432
+ slots: Object.entries(input.doc.slots).map(([name, slot]) => ({
433
+ name,
434
+ title: slot.title,
435
+ children: [],
436
+ })),
437
+ source: input.source,
438
+ },
439
+ input,
440
+ );
441
+ // A withdrawn namespace has no route, so a namespace placed in it is
442
+ // withdrawn too, and a doc placed in it says so.
443
+ if (!added) routeOf.set(key, null);
444
+ }
445
+
446
+ // Docs: explicit placement, else one adoption rule, else no home.
447
+ const sortedDocs = [...docs].sort(
448
+ (a, b) =>
449
+ (a.rank ?? 0) - (b.rank ?? 0) ||
450
+ byText(a.provider, b.provider) ||
451
+ byText(a.kind, b.kind) ||
452
+ byText(a.name, b.name) ||
453
+ byText(a.source, b.source),
454
+ );
455
+ for (const doc of sortedDocs) {
456
+ /** @type {{parentRoute: string, slot: string, order: number | null} | null} */
457
+ let home = null;
458
+ if (doc.placement != null) {
459
+ const placed = checkPlacement(doc.placement, doc.kind, doc, declared);
460
+ if ('error' in placed) {
461
+ report('invalid_placement', doc, placed.error, 'placement');
462
+ continue;
463
+ }
464
+ const parentRoute = routeOf.get(placed.key);
465
+ if (parentRoute == null) {
466
+ report(
467
+ 'invalid_placement',
468
+ doc,
469
+ `placement.parent "${doc.placement.parent}" names a namespace that has no route.`,
470
+ 'placement',
471
+ );
472
+ continue;
473
+ }
474
+ home = {
475
+ parentRoute,
476
+ slot: placed.slot,
477
+ order: doc.placement.order ?? null,
478
+ };
479
+ } else if (doc.group != null) {
480
+ const matches = adoptionsFor(doc, declared, routeOf);
481
+ if (matches.length > 1) {
482
+ report(
483
+ 'overlapping_adoption',
484
+ doc,
485
+ `${doc.provider}/${doc.kind}/${doc.name} is adopted by ${matches
486
+ .map(m => `"${m.namespace.doc.name}"`)
487
+ .join(' and ')}; exactly one namespace may adopt a doc.`,
488
+ );
489
+ continue;
490
+ }
491
+ if (matches.length === 1) {
492
+ const [{key, rule, namespace}] = matches;
493
+ const nsRoute = /** @type {string} */ (routeOf.get(key));
494
+ if (rule.groupBy === 'kind') {
495
+ const group = KIND_GROUPS[doc.kind] ?? {
496
+ segment: `${routeSegment(doc.kind)}s`,
497
+ title: doc.kind,
498
+ summary: `Every ${doc.kind} doc.`,
499
+ };
500
+ const groupRoute = `${nsRoute}/${group.segment}`;
501
+ if (!nodes.has(groupRoute)) {
502
+ const kinds = rule.source.kinds ?? [];
503
+ addNode(
504
+ {
505
+ id: null,
506
+ route: groupRoute,
507
+ kind: 'namespace',
508
+ provider: namespace.provider,
509
+ providerId: namespace.providerId,
510
+ name: group.segment,
511
+ title: group.title,
512
+ summary: group.summary,
513
+ parent: nsRoute,
514
+ slot: rule.into,
515
+ order: kinds.includes(/** @type {any} */ (doc.kind))
516
+ ? kinds.indexOf(/** @type {any} */ (doc.kind))
517
+ : null,
518
+ generated: true,
519
+ slots: [{name: 'items', title: group.title, children: []}],
520
+ source: namespace.source,
521
+ },
522
+ namespace,
523
+ );
524
+ }
525
+ const groupNode = nodes.get(groupRoute);
526
+ if (!groupNode?.generated) continue;
527
+ home = {parentRoute: groupRoute, slot: 'items', order: null};
528
+ } else {
529
+ home = {parentRoute: nsRoute, slot: rule.into, order: null};
530
+ }
531
+ }
532
+ }
533
+ if (home == null) continue;
534
+ const segment = routeSegment(doc.name);
535
+ if (segment === '') {
536
+ report(
537
+ 'invalid_placement',
538
+ doc,
539
+ `${doc.provider}/${doc.kind}/${doc.name} has no route segment: its name holds no letters or digits.`,
540
+ 'name',
541
+ );
542
+ continue;
543
+ }
544
+ addNode(
545
+ {
546
+ id: createDocId(doc.providerId, doc.kind, doc.name),
547
+ route: `${home.parentRoute}/${segment}`,
548
+ kind: doc.kind,
549
+ provider: doc.provider,
550
+ providerId: doc.providerId,
551
+ name: doc.name,
552
+ title: doc.title,
553
+ summary: doc.summary,
554
+ parent: home.parentRoute,
555
+ slot: home.slot,
556
+ order: home.order,
557
+ generated: false,
558
+ slots: [],
559
+ source: doc.source,
560
+ ...(doc.ref === undefined ? {} : {ref: doc.ref}),
561
+ },
562
+ doc,
563
+ );
564
+ }
565
+
566
+ // The generated Unorganized level (spec:AST-046 FR12): every flat topic sits
567
+ // here, in the order the topic list reads, so every doc has a home in the
568
+ // tree. A topic keeps its own name as its route.
569
+ if (topics.length > 0) {
570
+ const home = {
571
+ id: null,
572
+ route: UNORGANIZED,
573
+ kind: 'namespace',
574
+ provider: CLI_PROVIDER,
575
+ providerId: CLI_PROVIDER_ID,
576
+ name: UNORGANIZED,
577
+ title: 'Unorganized',
578
+ summary:
579
+ 'Every topic that no section places yet. Each keeps its own name; open one by it.',
580
+ parent: null,
581
+ slot: null,
582
+ order: null,
583
+ generated: true,
584
+ slots: [{name: 'topics', title: 'Topics', children: []}],
585
+ source: 'generated',
586
+ };
587
+ if (addNode(home, {provider: CLI_PROVIDER, source: 'generated'})) {
588
+ topics.forEach((topic, i) => {
589
+ addNode(
590
+ {
591
+ id: createDocId(topic.providerId, 'generic', topic.name),
592
+ route: topic.name,
593
+ kind: 'generic',
594
+ provider: topic.provider,
595
+ providerId: topic.providerId,
596
+ name: topic.name,
597
+ title: topic.title,
598
+ summary: topic.summary,
599
+ parent: UNORGANIZED,
600
+ slot: 'topics',
601
+ order: i,
602
+ generated: false,
603
+ slots: [],
604
+ source: topic.source,
605
+ ref: {flatTopic: topic.name},
606
+ },
607
+ topic,
608
+ );
609
+ });
610
+ }
611
+ }
612
+
613
+ // Children, per slot, in reading order: order, then title, then id.
614
+ for (const node of nodes.values()) {
615
+ if (node.parent == null) continue;
616
+ const parent = nodes.get(node.parent);
617
+ parent?.slots
618
+ .find(slot => slot.name === node.slot)
619
+ ?.children.push(node.route);
620
+ }
621
+ for (const node of nodes.values()) {
622
+ for (const slot of node.slots) {
623
+ slot.children.sort((a, b) => {
624
+ const x = /** @type {TreeNode} */ (nodes.get(a));
625
+ const y = /** @type {TreeNode} */ (nodes.get(b));
626
+ return (
627
+ (x.order ?? Infinity) - (y.order ?? Infinity) ||
628
+ byText(x.title.toLowerCase(), y.title.toLowerCase()) ||
629
+ byText(x.id ?? x.route, y.id ?? y.route)
630
+ );
631
+ });
632
+ }
633
+ }
634
+
635
+ // A topic that answers, through `replaces`, to a route the CLI's own docs
636
+ // keep cannot have it: the CLI's doc opens there. Say so, against the topic.
637
+ for (const topic of topics) {
638
+ if (topic.provider === CLI_PROVIDER) continue;
639
+ for (const alias of topic.aliases ?? []) {
640
+ const holder = byFoldedRoute.get(alias.toLowerCase());
641
+ if (holder != null && holder.provider === CLI_PROVIDER) {
642
+ report(
643
+ 'duplicate_route',
644
+ topic,
645
+ `The topic "${topic.name}" answers to "${alias}" through replaces, but the CLI's own docs keep that route, so \`astryx docs ${alias}\` opens theirs. Drop that replacement.`,
646
+ );
647
+ }
648
+ }
649
+ }
650
+
651
+ const sorted = new Map([...nodes.entries()].sort(([a], [b]) => byText(a, b)));
652
+ return {
653
+ nodes: sorted,
654
+ diagnostics: sortDiagnostics(diagnostics),
655
+ get: route => sorted.get(route),
656
+ getFolded: route => byFoldedRoute.get(String(route).toLowerCase()),
657
+ roots: () => [...sorted.values()].filter(node => node.parent == null),
658
+ ancestors: node => {
659
+ /** @type {TreeNode[]} */
660
+ const chain = [];
661
+ let parent = node.parent == null ? undefined : sorted.get(node.parent);
662
+ while (parent) {
663
+ chain.unshift(parent);
664
+ parent = parent.parent == null ? undefined : sorted.get(parent.parent);
665
+ }
666
+ return chain;
667
+ },
668
+ };
669
+ }
670
+
671
+ /**
672
+ * Check a placement against the namespace it names: the namespace exists in
673
+ * the doc's own package, the slot is one it declares, and the slot accepts the
674
+ * doc's kind.
675
+ * @param {DocPlacement} placement
676
+ * @param {string} kind
677
+ * @param {{provider: string}} at
678
+ * @param {Map<string, TreeNamespaceInput>} declared
679
+ * @returns {{key: string, slot: string} | {error: string}}
680
+ */
681
+ function checkPlacement(placement, kind, at, declared) {
682
+ const target = resolveParent(placement.parent, at.provider, declared);
683
+ if ('error' in target) return target;
684
+ const parent = /** @type {TreeNamespaceInput} */ (declared.get(target.key));
685
+ const slotNames = Object.keys(parent.doc.slots);
686
+ const slot = placement.slot ?? (slotNames.length === 1 ? slotNames[0] : null);
687
+ if (slot == null) {
688
+ return {
689
+ error: `placement names no slot, and namespace "${parent.doc.name}" has ${slotNames.length} (${slotNames.join(', ')}). Name one with placement.slot.`,
690
+ };
691
+ }
692
+ const declaredSlot = parent.doc.slots[slot];
693
+ if (declaredSlot == null) {
694
+ return {
695
+ error: `placement.slot "${slot}" is not a slot of namespace "${parent.doc.name}"; it declares ${slotNames.join(', ')}.`,
696
+ };
697
+ }
698
+ if (!declaredSlot.accepts.kinds.includes(/** @type {any} */ (kind))) {
699
+ return {
700
+ error: `slot "${slot}" of namespace "${parent.doc.name}" does not accept ${kind} docs; it accepts ${declaredSlot.accepts.kinds.join(', ')}.`,
701
+ };
702
+ }
703
+ return {key: target.key, slot};
704
+ }
705
+
706
+ /**
707
+ * Every adoption rule in the doc's own package that matches its group and
708
+ * kind, from namespaces that have a route.
709
+ * @param {TreeDocInput} doc
710
+ * @param {Map<string, TreeNamespaceInput>} declared
711
+ * @param {Map<string, string | null>} routeOf
712
+ */
713
+ function adoptionsFor(doc, declared, routeOf) {
714
+ /** @type {Array<{key: string, namespace: TreeNamespaceInput, rule: NonNullable<NamespaceDoc['adopts']>[number]}>} */
715
+ const matches = [];
716
+ for (const [key, namespace] of declared) {
717
+ if (namespace.provider !== doc.provider || routeOf.get(key) == null)
718
+ continue;
719
+ for (const rule of namespace.doc.adopts ?? []) {
720
+ if (rule.source.group !== doc.group) continue;
721
+ if (
722
+ rule.source.kinds &&
723
+ !rule.source.kinds.includes(/** @type {any} */ (doc.kind))
724
+ ) {
725
+ continue;
726
+ }
727
+ matches.push({key, namespace, rule});
728
+ }
729
+ }
730
+ return matches;
731
+ }
732
+
733
+ /**
734
+ * The files under {@link TREE_DOCS_DIR}, sorted.
735
+ * @param {string} [dir]
736
+ * @returns {string[]}
737
+ */
738
+ export function treeDocFiles(dir = TREE_DOCS_DIR) {
739
+ if (!fs.existsSync(dir)) return [];
740
+ return fs
741
+ .readdirSync(dir)
742
+ .filter(file => /^[\w-]+\.doc\.mjs$/u.test(file))
743
+ .sort(byText)
744
+ .map(file => path.join(dir, file));
745
+ }
746
+
747
+ /**
748
+ * The CLI's own tree inputs: the namespace docs and guides under
749
+ * assets/docs/tree, and, unless left out, every typed self-doc with its
750
+ * `namespace` group. A file that fails to load or parse is a diagnostic, never
751
+ * a thrown error.
752
+ * @param {{selfDocs?: boolean, dir?: string}} [options]
753
+ * @returns {Promise<{namespaces: TreeNamespaceInput[], docs: TreeDocInput[], diagnostics: CompilerDiagnostic[]}>}
754
+ */
755
+ export async function loadTreeInputs({
756
+ selfDocs = true,
757
+ dir = TREE_DOCS_DIR,
758
+ } = {}) {
759
+ /** @type {TreeNamespaceInput[]} */
760
+ const namespaces = [];
761
+ /** @type {TreeDocInput[]} */
762
+ const docs = [];
763
+ /** @type {CompilerDiagnostic[]} */
764
+ const diagnostics = [];
765
+ for (const file of treeDocFiles(dir)) {
766
+ const source = packageSource(file);
767
+ const at = {provider: CLI_PROVIDER, source};
768
+ let doc;
769
+ try {
770
+ doc = await readDocView(file, {
771
+ root: 'tree',
772
+ provider: CLI_PROVIDER,
773
+ loader: 'native',
774
+ strict: true,
775
+ });
776
+ } catch (error) {
777
+ diagnostics.push(
778
+ diagnostic('invalid_doc', {
779
+ ...at,
780
+ message: error instanceof Error ? error.message : String(error),
781
+ }),
782
+ );
783
+ continue;
784
+ }
785
+ const stem = path.basename(file, '.doc.mjs');
786
+ if (doc?.name !== stem) {
787
+ diagnostics.push(
788
+ diagnostic('invalid_doc', {
789
+ ...at,
790
+ field: 'name',
791
+ message: `${path.basename(file)} declares name "${doc?.name}"; a docs tree file is named after its doc (${doc?.name}.doc.mjs).`,
792
+ }),
793
+ );
794
+ continue;
795
+ }
796
+ if (doc.type === 'namespace') {
797
+ namespaces.push({
798
+ provider: CLI_PROVIDER,
799
+ providerId: CLI_PROVIDER_ID,
800
+ source,
801
+ doc,
802
+ });
803
+ } else if (doc.type === 'generic') {
804
+ if (doc.placement == null) {
805
+ diagnostics.push(
806
+ diagnostic('invalid_placement', {
807
+ ...at,
808
+ field: 'placement',
809
+ message: `${path.basename(file)} has no placement. A guide in the docs tree names its parent namespace with placement.parent.`,
810
+ }),
811
+ );
812
+ continue;
813
+ }
814
+ docs.push({
815
+ provider: CLI_PROVIDER,
816
+ providerId: CLI_PROVIDER_ID,
817
+ source,
818
+ kind: 'generic',
819
+ name: doc.name,
820
+ title: doc.title,
821
+ summary: doc.description,
822
+ group: null,
823
+ placement: doc.placement,
824
+ ref: {topicFile: file},
825
+ });
826
+ } else {
827
+ diagnostics.push(
828
+ diagnostic('wrong_kind', {
829
+ ...at,
830
+ message: `${path.basename(file)} is stamped type ${JSON.stringify(doc?.type)}; the docs tree reads namespace and generic docs.`,
831
+ }),
832
+ );
833
+ }
834
+ }
835
+ if (selfDocs) {
836
+ const {loaded} = await loadCliSelfDocs();
837
+ for (const {source, doc} of loaded) {
838
+ docs.push({
839
+ provider: CLI_PROVIDER,
840
+ providerId: CLI_PROVIDER_ID,
841
+ source: `${CLI_PROVIDER}/${source}`,
842
+ kind: doc.type,
843
+ name: doc.name,
844
+ title: doc.displayName ?? doc.name,
845
+ summary: doc.summary ?? doc.description ?? '',
846
+ group: typeof doc.namespace === 'string' ? doc.namespace : null,
847
+ placement: doc.placement,
848
+ ref: {selfDoc: doc},
849
+ });
850
+ }
851
+ }
852
+ return {namespaces, docs, diagnostics};
853
+ }
854
+
855
+ /** @type {Map<string, Promise<DocsTree>>} */
856
+ const built = new Map();
857
+
858
+ /**
859
+ * The CLI's own docs tree, built once per process. With `selfDocs: false` it
860
+ * holds only the namespaces and guides, which is all a topic list needs.
861
+ * @param {{selfDocs?: boolean, fresh?: boolean}} [options]
862
+ * @returns {Promise<DocsTree>}
863
+ */
864
+ export function loadDocsTree({selfDocs = true, fresh = false} = {}) {
865
+ const key = selfDocs ? 'full' : 'namespaces';
866
+ let tree = fresh ? undefined : built.get(key);
867
+ if (!tree) {
868
+ tree = loadTreeInputs({selfDocs}).then(inputs => {
869
+ const result = buildDocsTree(inputs);
870
+ return {
871
+ ...result,
872
+ diagnostics: sortDiagnostics([
873
+ ...inputs.diagnostics,
874
+ ...result.diagnostics,
875
+ ]),
876
+ };
877
+ });
878
+ built.set(key, tree);
879
+ }
880
+ return tree;
881
+ }