@astryxdesign/cli 0.6.3-canary.f22695a → 0.6.3

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 (197) hide show
  1. package/README.md +1 -2
  2. package/api/build/build.type.d.mts +2 -2
  3. package/api/build/build.type.mjs +2 -2
  4. package/api/component/component.type.d.mts +6 -6
  5. package/api/component/component.type.mjs +19 -19
  6. package/api/discover/discover.type.d.mts +4 -4
  7. package/api/discover/discover.type.mjs +10 -10
  8. package/api/docs/_adapter.d.mts +24 -37
  9. package/api/docs/_adapter.mjs +83 -169
  10. package/api/docs/detail/detail.mjs +63 -14
  11. package/api/docs/detail/section/section.d.mts +1 -1
  12. package/api/docs/detail/section/section.mjs +20 -44
  13. package/api/docs/detail/section/section.test.mjs +0 -41
  14. package/api/docs/docs.d.mts +2 -7
  15. package/api/docs/docs.doc.mjs +10 -27
  16. package/api/docs/docs.mjs +9 -16
  17. package/api/docs/docs.test.mjs +0 -6
  18. package/api/docs/docs.type.d.mts +3 -40
  19. package/api/docs/docs.type.mjs +8 -36
  20. package/api/docs/integrationDocs.test.mjs +0 -106
  21. package/api/doctor/doctor.d.mts +0 -48
  22. package/api/doctor/doctor.mjs +0 -232
  23. package/api/doctor/doctor.test.mjs +0 -196
  24. package/api/hook/hook.type.d.mts +3 -3
  25. package/api/hook/hook.type.mjs +11 -11
  26. package/api/hook/list/list.d.mts +1 -1
  27. package/api/integration/add-contribution.mjs +3 -5
  28. package/api/integration/add-contribution.test.mjs +4 -4
  29. package/api/integration/integration-authoring.type.d.mts +1 -1
  30. package/api/integration/pack-check.mjs +7 -49
  31. package/api/integration/pack-check.test.mjs +0 -249
  32. package/api/search/search.d.mts +1 -1
  33. package/api/search/search.mjs +5 -5
  34. package/api/search/search.type.d.mts +2 -2
  35. package/api/search/search.type.mjs +1 -1
  36. package/api/swizzle/swizzle.type.d.mts +2 -2
  37. package/api/swizzle/swizzle.type.mjs +2 -2
  38. package/api/template/template.d.mts +1 -1
  39. package/api/template/template.type.d.mts +6 -6
  40. package/api/template/template.type.mjs +12 -12
  41. package/api/theme/build/build.mjs +6 -20
  42. package/api/theme/build/build.test.mjs +0 -127
  43. package/api/theme/palette/generate/generate.mjs +1 -1
  44. package/api/theme/palette/generate/generator.d.mts +13 -10
  45. package/api/theme/palette/generate/generator.mjs +3 -7
  46. package/api/theme/theme.type.d.mts +11 -170
  47. package/api/theme/theme.type.mjs +27 -94
  48. package/api/upgrade/_adapter.mjs +5 -71
  49. package/api/upgrade/upgrade.doc.mjs +3 -4
  50. package/api/upgrade/upgrade.type.d.mts +5 -5
  51. package/api/upgrade/upgrade.type.mjs +11 -11
  52. package/assets/codemods/integration-discovery.mjs +2 -40
  53. package/assets/codemods/integration-discovery.test.mjs +0 -58
  54. package/assets/codemods/transforms/v0.3.0/__tests__/unwrap-authoring-factories.test.mjs +5 -27
  55. package/assets/codemods/transforms/v0.3.0/unwrap-authoring-factories.mjs +5 -20
  56. package/assets/docs/README.md +0 -9
  57. package/assets/docs/cli-integrations.doc.mjs +15 -86
  58. package/assets/docs/styling-libraries.doc.mjs +1 -1
  59. package/assets/docs/working-with-ai.doc.mjs +1 -1
  60. package/assets/templates/blocks/components/Toolbar/ToolbarTableFilter.doc.mjs +3 -19
  61. package/assets/templates/blocks/components/Toolbar/ToolbarTableFilter.tsx +65 -383
  62. package/authoring/_shared/contract.ts +0 -22
  63. package/authoring/codemod/codemod.doc.mjs +1 -6
  64. package/authoring/codemod/parse.d.mts +8 -8
  65. package/authoring/codemod/parse.mjs +6 -8
  66. package/authoring/config/parse.d.mts +13 -13
  67. package/authoring/config/parse.mjs +8 -8
  68. package/authoring/config/type.ts +3 -3
  69. package/authoring/debug/parse.d.mts +5 -5
  70. package/authoring/debug/parse.mjs +3 -3
  71. package/authoring/doctypes/_schema.d.mts +23 -788
  72. package/authoring/doctypes/_schema.mjs +39 -492
  73. package/authoring/doctypes/base/type.ts +0 -40
  74. package/authoring/doctypes/command/command.doc.mjs +2 -3
  75. package/authoring/doctypes/command/parse.d.mts +2 -2
  76. package/authoring/doctypes/command/parse.mjs +1 -1
  77. package/authoring/doctypes/command/type.ts +2 -3
  78. package/authoring/doctypes/component/component.doc.mjs +3 -6
  79. package/authoring/doctypes/component/parse.d.mts +2 -2
  80. package/authoring/doctypes/component/parse.mjs +1 -1
  81. package/authoring/doctypes/component/type.ts +3 -4
  82. package/authoring/doctypes/enum/parse.d.mts +2 -2
  83. package/authoring/doctypes/enum/parse.mjs +1 -1
  84. package/authoring/doctypes/enum/type.ts +1 -3
  85. package/authoring/doctypes/function/function.doc.mjs +0 -4
  86. package/authoring/doctypes/function/parse.d.mts +2 -2
  87. package/authoring/doctypes/function/parse.mjs +1 -1
  88. package/authoring/doctypes/function/type.ts +2 -6
  89. package/authoring/doctypes/hook/hook.doc.mjs +0 -4
  90. package/authoring/doctypes/hook/parse.d.mts +2 -2
  91. package/authoring/doctypes/hook/parse.mjs +1 -1
  92. package/authoring/doctypes/hook/type.ts +2 -3
  93. package/authoring/doctypes/legacy.d.mts +6 -8
  94. package/authoring/doctypes/legacy.mjs +4 -5
  95. package/authoring/doctypes/parse.d.mts +18 -20
  96. package/authoring/doctypes/parse.mjs +10 -16
  97. package/authoring/doctypes/parse.test.mjs +3 -77
  98. package/authoring/doctypes/reference/parse.d.mts +2 -2
  99. package/authoring/doctypes/reference/parse.mjs +5 -8
  100. package/authoring/doctypes/reference/reference.doc.mjs +4 -17
  101. package/authoring/doctypes/reference/type.ts +5 -51
  102. package/authoring/doctypes/schema/parse.d.mts +2 -2
  103. package/authoring/doctypes/schema/parse.mjs +1 -1
  104. package/authoring/doctypes/schema/type.ts +2 -3
  105. package/authoring/doctypes/template/parse.d.mts +1 -92
  106. package/authoring/doctypes/template/parse.mjs +2 -36
  107. package/authoring/doctypes/template/parse.test.mjs +2 -8
  108. package/authoring/doctypes/template/template.doc.mjs +0 -4
  109. package/authoring/doctypes/template/type.ts +2 -5
  110. package/authoring/doctypes/types.ts +9 -10
  111. package/authoring/gap-report/parse.d.mts +10 -10
  112. package/authoring/gap-report/parse.mjs +6 -6
  113. package/authoring/gap-report/type.ts +1 -1
  114. package/authoring/index.d.mts +0 -1
  115. package/authoring/index.d.ts +17 -49
  116. package/authoring/index.mjs +0 -1
  117. package/authoring/integration/integration.doc.mjs +6 -13
  118. package/authoring/integration/parse.d.mts +2 -2
  119. package/authoring/integration/parse.mjs +1 -1
  120. package/authoring/integration/parse.test.mjs +1 -10
  121. package/authoring/integration/schema.d.mts +4 -6
  122. package/authoring/integration/schema.mjs +3 -9
  123. package/authoring/integration/type.ts +6 -23
  124. package/authoring/shadcn/receipt.d.mts +6 -6
  125. package/clients/cli/commands/docs.doc.mjs +3 -13
  126. package/clients/cli/commands/docs.mjs +21 -121
  127. package/clients/cli/commands/docs.test.mjs +0 -88
  128. package/clients/cli/commands/integration-authoring.test.mjs +9 -13
  129. package/clients/cli/commands/theme-palette-generate.doc.mjs +4 -8
  130. package/clients/cli/commands/upgrade.doc.mjs +2 -2
  131. package/clients/cli/formatters/index.mjs +1 -162
  132. package/clients/cli/formatters/index.test.mjs +0 -91
  133. package/clients/cli/lib/manifest.mjs +2 -7
  134. package/foundation/config/project.mjs +6 -21
  135. package/foundation/discovery/component-discovery.d.mts +1 -1
  136. package/foundation/discovery/component-discovery.mjs +1 -2
  137. package/foundation/discovery/docs-discovery.d.mts +4 -11
  138. package/foundation/discovery/docs-discovery.mjs +88 -208
  139. package/foundation/discovery/docs-discovery.test.mjs +13 -279
  140. package/foundation/discovery/template-adapter.mjs +1 -2
  141. package/foundation/integrations/autolink.mjs +5 -12
  142. package/foundation/integrations/integration-warnings.mjs +0 -6
  143. package/foundation/integrations/integrations.d.mts +2 -46
  144. package/foundation/integrations/integrations.mjs +8 -167
  145. package/foundation/integrations/integrations.test.mjs +1 -384
  146. package/foundation/integrations/validate-contributions.d.mts +0 -2
  147. package/foundation/integrations/validate-contributions.mjs +0 -10
  148. package/foundation/response/json-contract.test.mjs +17 -46
  149. package/foundation/response/response-types.doc.mjs +1 -6
  150. package/package.json +11 -9
  151. package/api/docs/compiled-topics.test.mjs +0 -78
  152. package/api/docs/index/index.d.mts +0 -18
  153. package/api/docs/index/index.mjs +0 -32
  154. package/api/docs/index/index.test.mjs +0 -62
  155. package/api/upgrade/project-context.test.mjs +0 -272
  156. package/assets/docs/authoring.doc.mjs +0 -14
  157. package/assets/templates/blocks/components/Timer/TimerFormats.doc.mjs +0 -14
  158. package/assets/templates/blocks/components/Timer/TimerFormats.tsx +0 -34
  159. package/assets/templates/blocks/components/Timer/TimerInline.doc.mjs +0 -14
  160. package/assets/templates/blocks/components/Timer/TimerInline.tsx +0 -14
  161. package/assets/templates/blocks/components/Timer/TimerShowcase.doc.mjs +0 -13
  162. package/assets/templates/blocks/components/Timer/TimerShowcase.tsx +0 -47
  163. package/assets/templates/blocks/components/Timer/TimerTypography.doc.mjs +0 -14
  164. package/assets/templates/blocks/components/Timer/TimerTypography.tsx +0 -31
  165. package/authoring/doctypes/base/graph-fields.doc.d.mts +0 -9
  166. package/authoring/doctypes/base/graph-fields.doc.mjs +0 -62
  167. package/authoring/doctypes/load-contract.test.mjs +0 -207
  168. package/authoring/doctypes/namespace/namespace.doc.d.mts +0 -9
  169. package/authoring/doctypes/namespace/namespace.doc.mjs +0 -132
  170. package/authoring/doctypes/namespace/parse.d.mts +0 -12
  171. package/authoring/doctypes/namespace/parse.mjs +0 -25
  172. package/authoring/doctypes/namespace/parse.test.mjs +0 -165
  173. package/authoring/doctypes/namespace/type.ts +0 -71
  174. package/authoring/identity/identity.doc.d.mts +0 -9
  175. package/authoring/identity/identity.doc.mjs +0 -61
  176. package/authoring/identity/type.ts +0 -132
  177. package/foundation/discovery/authoring-self-docs.d.mts +0 -69
  178. package/foundation/discovery/authoring-self-docs.mjs +0 -214
  179. package/foundation/discovery/authoring-self-docs.test.mjs +0 -154
  180. package/foundation/discovery/docs-output-budget.d.mts +0 -28
  181. package/foundation/discovery/docs-output-budget.mjs +0 -50
  182. package/foundation/discovery/docs-section-key.d.mts +0 -98
  183. package/foundation/discovery/docs-section-key.mjs +0 -221
  184. package/foundation/discovery/docs-section-key.test.mjs +0 -224
  185. package/foundation/doc-compiler/compile.d.mts +0 -162
  186. package/foundation/doc-compiler/compile.mjs +0 -262
  187. package/foundation/doc-compiler/doc-compiler.test.mjs +0 -687
  188. package/foundation/doc-compiler/ir.d.mts +0 -9
  189. package/foundation/doc-compiler/ir.mjs +0 -287
  190. package/foundation/doc-compiler/lenses.d.mts +0 -33
  191. package/foundation/doc-compiler/lenses.mjs +0 -127
  192. package/foundation/identity/provider-identity.d.mts +0 -90
  193. package/foundation/identity/provider-identity.mjs +0 -320
  194. package/foundation/identity/provider-identity.test.mjs +0 -254
  195. package/foundation/identity/providers.d.mts +0 -7
  196. package/foundation/identity/providers.mjs +0 -16
  197. package/foundation/integrations/provider-conflicts.test.mjs +0 -125
@@ -3,208 +3,16 @@
3
3
  /**
4
4
  * @file Sealed doc load-boundary schemas (doctypes-internal).
5
5
  *
6
- * Existing doctypes keep their historical top-level passthrough policy so
7
- * already-published docs continue to load. NamespaceDoc and every semantic
8
- * content block are strict: a misspelled field cannot reach a renderer as
9
- * missing data.
6
+ * These zod schemas are the implementation detail behind the doctypes parsers.
7
+ * They are NOT part of the public authoring surface: nothing outside
8
+ * `authoring/doctypes/**` imports them, and they never appear in a public type.
9
+ * They accept BOTH the stamped formats (`type: 'component' | 'function' |
10
+ * 'generic'`) and the legacy loose `export const docs = {...}` shape, so the
11
+ * ~600+ existing docs keep validating unchanged.
10
12
  */
11
13
 
12
14
  import {z} from 'zod';
13
15
 
14
- /** @typedef {import('./base/type.js').AuthoredDocGraphFields} AuthoredDocGraphFieldsType */
15
- /** @typedef {import('./base/type.js').AuthoredDocKind} AuthoredDocKind */
16
- /** @typedef {import('./namespace/type.js').NamespaceDoc} NamespaceDoc */
17
- /** @typedef {import('./reference/type.js').ReferenceContentBlock} ReferenceContentBlock */
18
- /** @typedef {import('./reference/type.js').ReferenceDoc} ReferenceDoc */
19
- /** @typedef {import('./component/type.js').SingleComponentDoc} SingleComponentDoc */
20
- /** @typedef {import('./base/type.js').ComponentPropDoc} ComponentPropDoc */
21
- /** @typedef {import('./hook/type.js').HookDoc} HookDoc */
22
- /** @typedef {import('./function/type.js').FunctionDoc} FunctionDoc */
23
- /** @typedef {import('./schema/type.js').SchemaDoc} SchemaDoc */
24
- /** @typedef {import('./command/type.js').CommandDoc} CommandDoc */
25
- /** @typedef {import('./enum/type.js').EnumDoc} EnumDoc */
26
-
27
- const nonEmptyString = z.string().min(1);
28
-
29
- /** Every authored doc-kind discriminant accepted by parseDoc. */
30
- export const AuthoredDocKindSchema = z.enum([
31
- 'component',
32
- 'function',
33
- 'generic',
34
- 'page',
35
- 'block',
36
- 'schema',
37
- 'command',
38
- 'enum',
39
- 'namespace',
40
- ]);
41
-
42
- /**
43
- * @typedef {import('../_shared/contract.js').Expect<
44
- * import('../_shared/contract.js').Equal<z.infer<typeof AuthoredDocKindSchema>, AuthoredDocKind>
45
- * >} _AuthoredDocKindDriftLock
46
- */
47
-
48
- /** Shared optional graph fields for every authored doc kind. */
49
- export const AuthoredDocGraphFields = {
50
- placement: z
51
- .object({
52
- parent: nonEmptyString,
53
- slot: nonEmptyString.optional(),
54
- order: z.number().int().safe().optional(),
55
- })
56
- .strict()
57
- .optional(),
58
- aliases: z.array(nonEmptyString).optional(),
59
- audience: z.enum(['public', 'internal']).optional(),
60
- };
61
-
62
- const _AuthoredDocGraphSchema = z.object(AuthoredDocGraphFields).strict();
63
-
64
- /**
65
- * @typedef {import('../_shared/contract.js').Expect<
66
- * import('../_shared/contract.js').MutuallyAssignable<
67
- * z.infer<typeof _AuthoredDocGraphSchema>,
68
- * AuthoredDocGraphFieldsType
69
- * >
70
- * >} _AuthoredDocGraphDriftLock
71
- */
72
-
73
- const ProseBlockSchema = z
74
- .object({type: z.literal('prose'), text: nonEmptyString})
75
- .strict();
76
- const HeadingBlockSchema = z
77
- .object({
78
- type: z.literal('heading'),
79
- level: z.union([z.literal(3), z.literal(4), z.literal(5), z.literal(6)]),
80
- text: nonEmptyString,
81
- })
82
- .strict();
83
- const CodeBlockSchema = z
84
- .object({
85
- type: z.literal('code'),
86
- lang: nonEmptyString,
87
- code: z.string(),
88
- label: nonEmptyString.optional(),
89
- })
90
- .strict();
91
- const TableBlockSchema = z
92
- .object({
93
- type: z.literal('table'),
94
- headers: z.array(z.string()).min(1),
95
- rows: z.array(z.array(z.string())),
96
- })
97
- .strict()
98
- .superRefine((table, context) => {
99
- table.rows.forEach((row, index) => {
100
- if (row.length !== table.headers.length) {
101
- context.addIssue({
102
- code: 'custom',
103
- path: ['rows', index],
104
- message: `expected ${table.headers.length} cells`,
105
- });
106
- }
107
- });
108
- });
109
- const ListBlockSchema = z
110
- .object({
111
- type: z.literal('list'),
112
- style: z.enum(['ordered', 'unordered', 'do', 'dont']),
113
- items: z.array(nonEmptyString).min(1),
114
- })
115
- .strict();
116
- const TokenReferenceBlockSchema = z
117
- .object({
118
- type: z.literal('token-ref'),
119
- topic: nonEmptyString,
120
- section: nonEmptyString,
121
- })
122
- .strict();
123
- const WorkflowBlockSchema = z
124
- .object({
125
- type: z.literal('workflow'),
126
- title: nonEmptyString.optional(),
127
- steps: z
128
- .array(
129
- z
130
- .object({
131
- title: nonEmptyString,
132
- description: nonEmptyString.optional(),
133
- references: z.array(nonEmptyString).min(1).optional(),
134
- })
135
- .strict(),
136
- )
137
- .min(1),
138
- })
139
- .strict();
140
- const CollectionBlockSchema = z
141
- .object({
142
- type: z.literal('collection'),
143
- title: nonEmptyString.optional(),
144
- source: z.object({slot: nonEmptyString}).strict(),
145
- presentation: z.enum(['list', 'cards', 'compact']).optional(),
146
- whenEmpty: z.enum(['show', 'omit']).optional(),
147
- })
148
- .strict();
149
- const ReferenceBlockSchema = z
150
- .object({
151
- type: z.literal('reference'),
152
- target: nonEmptyString,
153
- projection: z
154
- .object({
155
- fields: z.array(nonEmptyString).min(1).optional(),
156
- sections: z.array(nonEmptyString).min(1).optional(),
157
- })
158
- .strict()
159
- .optional(),
160
- presentation: z.enum(['summary', 'compact', 'full']).optional(),
161
- })
162
- .strict();
163
-
164
- /** Runtime schema for every existing and V1 semantic content block. */
165
- export const ReferenceContentBlockSchema = z.discriminatedUnion('type', [
166
- ProseBlockSchema,
167
- HeadingBlockSchema,
168
- CodeBlockSchema,
169
- TableBlockSchema,
170
- ListBlockSchema,
171
- TokenReferenceBlockSchema,
172
- WorkflowBlockSchema,
173
- CollectionBlockSchema,
174
- ReferenceBlockSchema,
175
- ]);
176
-
177
- /**
178
- * @typedef {import('../_shared/contract.js').Expect<
179
- * import('../_shared/contract.js').Equal<
180
- * z.infer<typeof ReferenceContentBlockSchema>,
181
- * ReferenceContentBlock
182
- * >
183
- * >} _ReferenceContentBlockDriftLock
184
- */
185
-
186
- const ReferenceSectionSchema = z
187
- .object({
188
- id: nonEmptyString.optional(),
189
- title: nonEmptyString,
190
- category: z.string().optional(),
191
- content: z.array(ReferenceContentBlockSchema),
192
- previewType: z
193
- .enum([
194
- 'swatch',
195
- 'shadow-box',
196
- 'radius-box',
197
- 'spacing-bar',
198
- 'size-bar',
199
- 'border-line',
200
- 'duration-bar',
201
- 'easing-curve',
202
- 'font-sample',
203
- ])
204
- .optional(),
205
- })
206
- .strict();
207
-
208
16
  const PropSchema = z
209
17
  .object({
210
18
  name: z.string().min(1, 'prop name is required'),
@@ -234,7 +42,6 @@ const ReturnSchema = z
234
42
  .passthrough();
235
43
 
236
44
  const BaseDocFields = {
237
- ...AuthoredDocGraphFields,
238
45
  name: z.string().min(1, 'name is required'),
239
46
  displayName: z.string().optional(),
240
47
  description: z.string().optional(),
@@ -249,69 +56,21 @@ const BaseDocFields = {
249
56
  isHiddenFromOverview: z.boolean().optional(),
250
57
  };
251
58
 
252
- const ComponentBaseSchema = z
59
+ /** New-format stamped component doc (`type: 'component'`). */
60
+ export const ComponentDocKindSchema = z
253
61
  .object({
254
62
  ...BaseDocFields,
255
63
  type: z.literal('component'),
64
+ props: z.array(PropSchema),
256
65
  theming: z.unknown().optional(),
257
66
  playground: z.unknown().optional(),
258
67
  examples: z.array(z.unknown()).optional(),
259
68
  })
260
69
  .passthrough();
261
70
 
262
- /**
263
- * One entry in a group doc's `components`: a full ComponentEntry or a
264
- * name-only ComponentRef. Readers look every entry up by `name`, so that much
265
- * is checked here; the rest passes through, as on an unstamped doc.
266
- */
267
- const ComponentGroupEntrySchema = z
268
- .object({name: z.string().min(1, 'component name is required')})
269
- .passthrough();
270
-
271
- /**
272
- * New-format stamped component doc (`type: 'component'`): one component's
273
- * `props`, or the `components` a group doc documents together. These are the
274
- * shapes the published ComponentDoc type allows, and the ones an unstamped doc
275
- * may already take.
276
- */
277
- export const ComponentDocKindSchema = ComponentBaseSchema.extend({
278
- props: z.array(PropSchema).optional(),
279
- components: z.array(ComponentGroupEntrySchema).optional(),
280
- }).superRefine((doc, context) => {
281
- if (doc.props == null && doc.components == null) {
282
- context.addIssue({
283
- code: 'custom',
284
- path: ['props'],
285
- message:
286
- 'expected the props array, or `components` for a doc that groups several components',
287
- });
288
- }
289
- });
290
-
291
- /**
292
- * A stamped component doc as it loads. The loader accepts what the unstamped
293
- * format always accepted, so stamping an existing doc never breaks it:
294
- * `displayName` may be missing, `category` is any string, `usage`, `theming`,
295
- * `playground` and `examples` pass through unchecked, and a doc has `props`,
296
- * `components`, or both; each `components` entry needs only a `name`. Every
297
- * other field matches the published type.
298
- *
299
- * @typedef {Omit<SingleComponentDoc,
300
- * 'type' | 'displayName' | 'category' | 'usage' | 'theming' | 'examples' | 'playground' | 'props'>
301
- * & {type: 'component', displayName?: string, category?: string, usage?: unknown,
302
- * theming?: unknown, examples?: unknown[], playground?: unknown,
303
- * props?: ComponentPropDoc[], components?: Array<{name: string}>}} LoadedComponentDoc
304
- */
305
- /**
306
- * @typedef {import('../_shared/contract.js').Expect<
307
- * import('../_shared/contract.js').MutuallyAssignable<
308
- * import('../_shared/contract.js').NamedFields<z.infer<typeof ComponentDocKindSchema>>,
309
- * import('../_shared/contract.js').NamedFields<LoadedComponentDoc>
310
- * >
311
- * >} _ComponentDocDriftLock
312
- */
313
-
314
- /** Return entry for generalized function docs. */
71
+ /** Return entry for the generalized function doc: `name` is optional so CLI/API
72
+ * functions can document their `{type, data}` envelope entries (which have no
73
+ * field name), while hooks keep listing named return fields. */
315
74
  const FunctionReturnSchema = z
316
75
  .object({
317
76
  name: z.string().min(1).optional(),
@@ -320,7 +79,8 @@ const FunctionReturnSchema = z
320
79
  })
321
80
  .passthrough();
322
81
 
323
- /** New-format stamped function doc (`type: 'function'`). */
82
+ /** New-format stamped function doc (`type: 'function'`) — hooks and CLI/API
83
+ * functions alike (the discriminant and schema are shared). */
324
84
  export const FunctionDocKindSchema = z
325
85
  .object({
326
86
  ...BaseDocFields,
@@ -330,95 +90,30 @@ export const FunctionDocKindSchema = z
330
90
  })
331
91
  .passthrough();
332
92
 
333
- /**
334
- * A stamped function doc as it loads: as with components, `displayName` may be
335
- * missing and `usage` passes through unchecked.
336
- *
337
- * @typedef {Omit<FunctionDoc, 'type' | 'displayName' | 'usage'>
338
- * & {type: 'function', displayName?: string, usage?: unknown}} LoadedFunctionDoc
339
- */
340
- /**
341
- * @typedef {import('../_shared/contract.js').Expect<
342
- * import('../_shared/contract.js').MutuallyAssignable<
343
- * import('../_shared/contract.js').NamedFields<z.infer<typeof FunctionDocKindSchema>>,
344
- * import('../_shared/contract.js').NamedFields<LoadedFunctionDoc>
345
- * >
346
- * >} _FunctionDocDriftLock
347
- */
348
-
349
- /**
350
- * Every HookDoc is a FunctionDoc, so the one function schema covers both.
351
- *
352
- * @typedef {import('../_shared/contract.js').Expect<[HookDoc] extends [FunctionDoc] ? true : false>} _HookDocIsFunctionDocLock
353
- */
354
-
355
- /**
356
- * Stamped generic reference/topic doc (`type: 'generic'`). `title` and
357
- * `sections` stay optional at this parser boundary for docs produced by the
358
- * shipped v0.3.0 factory-removal codemod. When present, all rich fields and
359
- * semantic blocks are validated.
360
- */
93
+ /** New-format stamped generic reference/topic doc (`type: 'generic'`). */
361
94
  export const GenericDocKindSchema = z
362
95
  .object({
363
96
  ...BaseDocFields,
364
97
  type: z.literal('generic'),
365
- title: nonEmptyString.optional(),
366
- sections: z.array(ReferenceSectionSchema).min(1).optional(),
367
- replaces: nonEmptyString.optional(),
368
- extends: nonEmptyString.optional(),
369
- tokenCategory: z.string().optional(),
98
+ // Declared rather than left to the passthrough: these two are read by
99
+ // docs discovery to resolve one topic against another, so a non-string
100
+ // should fail at the load boundary, not halfway through resolution.
101
+ replaces: z.string().optional(),
102
+ extends: z.string().optional(),
370
103
  })
371
- .passthrough()
372
- .superRefine((doc, context) => {
373
- if (doc.replaces != null && doc.extends != null) {
374
- context.addIssue({
375
- code: 'custom',
376
- path: ['extends'],
377
- message: 'declares both `replaces` and `extends`; choose one',
378
- });
379
- }
380
- const sectionIds = new Set();
381
- doc.sections?.forEach((section, index) => {
382
- if (section.id == null) return;
383
- if (sectionIds.has(section.id)) {
384
- context.addIssue({
385
- code: 'custom',
386
- path: ['sections', index, 'id'],
387
- message: `duplicate section id "${section.id}"`,
388
- });
389
- }
390
- sectionIds.add(section.id);
391
- });
392
- });
393
-
394
- /**
395
- * A stamped generic doc as the load check accepts it. `title`, `description`
396
- * and `sections` may be missing, as in docs the v0.3.0 factory-removal codemod
397
- * produced; `parseReference` then fills them (title from `displayName` or
398
- * `name`, an empty description, no sections), so its result is a full
399
- * ReferenceDoc. Only a doc with a description and sections is a usable topic
400
- * (see `problemsInTopic`).
401
- *
402
- * @typedef {Omit<ReferenceDoc, 'type' | 'title' | 'description' | 'sections'>
403
- * & {type: 'generic'}
404
- * & Partial<Pick<ReferenceDoc, 'title' | 'description' | 'sections'>>} LoadedReferenceDoc
405
- */
406
- /**
407
- * @typedef {import('../_shared/contract.js').Expect<
408
- * import('../_shared/contract.js').MutuallyAssignable<
409
- * import('../_shared/contract.js').NamedFields<z.infer<typeof GenericDocKindSchema>>,
410
- * import('../_shared/contract.js').NamedFields<LoadedReferenceDoc>
411
- * >
412
- * >} _ReferenceDocDriftLock
413
- */
104
+ .passthrough();
414
105
 
415
- /** Recursive field descriptor for a SchemaDoc. */
106
+ /** Recursive field descriptor for a SchemaDoc (objects nest via `fields`). The
107
+ * explicit cast breaks the self-referential type inference (TS7022) that the
108
+ * authoring-contract `checkJs` pass would otherwise flag. */
416
109
  const SchemaFieldSchema =
417
- /** @type {import('zod').ZodType<import('./schema/type.js').SchemaFieldDoc>} */ (
110
+ /** @type {import('zod').ZodType<import('./schema/type').SchemaFieldDoc>} */ (
418
111
  z.lazy(() =>
419
112
  z
420
113
  .object({
421
114
  name: z.string().min(1, 'field name is required'),
115
+ // `{error}` covers a missing (undefined) type; `.min(1)` covers an
116
+ // empty string — both give the same author-friendly message.
422
117
  type: z
423
118
  .string({error: 'field type is required'})
424
119
  .min(1, 'field type is required'),
@@ -433,15 +128,15 @@ const SchemaFieldSchema =
433
128
  )
434
129
  );
435
130
 
436
- /** New stamped schema doc (`type: 'schema'`). */
131
+ /** New stamped schema doc (`type: 'schema'`) — documents an authored object. */
437
132
  export const SchemaDocKindSchema = z
438
133
  .object({
439
- ...AuthoredDocGraphFields,
440
134
  type: z.literal('schema'),
441
135
  name: z.string().min(1, 'name is required'),
442
136
  displayName: z.string().min(1, 'displayName is required'),
443
137
  description: z.string(),
444
138
  namespace: z.string().optional(),
139
+ aliases: z.array(z.string()).optional(),
445
140
  appliesTo: z.string().optional(),
446
141
  fields: z.array(SchemaFieldSchema),
447
142
  examples: z
@@ -451,29 +146,21 @@ export const SchemaDocKindSchema = z
451
146
  .passthrough(),
452
147
  )
453
148
  .optional(),
454
- notes: z.array(ReferenceContentBlockSchema).optional(),
149
+ notes: z.array(z.unknown()).optional(),
455
150
  })
456
151
  .passthrough();
457
152
 
458
- /**
459
- * @typedef {import('../_shared/contract.js').Expect<
460
- * import('../_shared/contract.js').MutuallyAssignable<
461
- * import('../_shared/contract.js').NamedFields<z.infer<typeof SchemaDocKindSchema>>,
462
- * import('../_shared/contract.js').NamedFields<SchemaDoc & {type: 'schema'}>
463
- * >
464
- * >} _SchemaDocDriftLock
465
- */
466
-
467
- /** New stamped command doc (`type: 'command'`). */
153
+ /** New stamped command doc (`type: 'command'`) — a function's terminal binding;
154
+ * references a FunctionDoc via `fn`. */
468
155
  export const CommandDocKindSchema = z
469
156
  .object({
470
- ...AuthoredDocGraphFields,
471
157
  type: z.literal('command'),
472
158
  name: z.string().min(1, 'name is required'),
473
159
  displayName: z.string().min(1, 'displayName is required'),
474
160
  summary: z.string(),
475
161
  description: z.string().optional(),
476
162
  namespace: z.string().optional(),
163
+ aliases: z.array(z.string()).optional(),
477
164
  fn: z.string().optional(),
478
165
  args: z
479
166
  .array(
@@ -520,28 +207,20 @@ export const CommandDocKindSchema = z
520
207
  .array(z.object({code: z.number(), when: z.string()}).passthrough())
521
208
  .optional(),
522
209
  related: z.array(z.string()).optional(),
523
- notes: z.array(ReferenceContentBlockSchema).optional(),
210
+ notes: z.array(z.unknown()).optional(),
524
211
  })
525
212
  .passthrough();
526
213
 
527
- /**
528
- * @typedef {import('../_shared/contract.js').Expect<
529
- * import('../_shared/contract.js').MutuallyAssignable<
530
- * import('../_shared/contract.js').NamedFields<z.infer<typeof CommandDocKindSchema>>,
531
- * import('../_shared/contract.js').NamedFields<CommandDoc & {type: 'command'}>
532
- * >
533
- * >} _CommandDocDriftLock
534
- */
535
-
536
- /** New stamped enum doc (`type: 'enum'`). */
214
+ /** New stamped enum doc (`type: 'enum'`) — a closed vocabulary (error codes,
215
+ * response-type discriminants). */
537
216
  export const EnumDocKindSchema = z
538
217
  .object({
539
- ...AuthoredDocGraphFields,
540
218
  type: z.literal('enum'),
541
219
  name: z.string().min(1, 'name is required'),
542
220
  displayName: z.string().min(1, 'displayName is required'),
543
221
  description: z.string(),
544
222
  namespace: z.string().optional(),
223
+ aliases: z.array(z.string()).optional(),
545
224
  members: z.array(
546
225
  z
547
226
  .object({
@@ -554,108 +233,8 @@ export const EnumDocKindSchema = z
554
233
  })
555
234
  .passthrough();
556
235
 
557
- /**
558
- * @typedef {import('../_shared/contract.js').Expect<
559
- * import('../_shared/contract.js').MutuallyAssignable<
560
- * import('../_shared/contract.js').NamedFields<z.infer<typeof EnumDocKindSchema>>,
561
- * import('../_shared/contract.js').NamedFields<EnumDoc & {type: 'enum'}>
562
- * >
563
- * >} _EnumDocDriftLock
564
- */
565
-
566
- const NamespaceSlotSchema = z
567
- .object({
568
- title: nonEmptyString,
569
- accepts: z
570
- .object({
571
- kinds: z.array(AuthoredDocKindSchema).min(1),
572
- providers: z.enum(['same', 'configured']).optional(),
573
- })
574
- .strict(),
575
- })
576
- .strict();
577
-
578
- /** The one new authored doctype: a hierarchy and layout owner. */
579
- export const NamespaceDocKindSchema = z
580
- .object({
581
- ...AuthoredDocGraphFields,
582
- type: z.literal('namespace'),
583
- name: nonEmptyString,
584
- title: nonEmptyString,
585
- summary: nonEmptyString,
586
- keywords: z.array(nonEmptyString).optional(),
587
- slots: z
588
- .record(nonEmptyString, NamespaceSlotSchema)
589
- .refine(slots => Object.keys(slots).length > 0, {
590
- message: 'at least one slot is required',
591
- }),
592
- adopts: z
593
- .array(
594
- z
595
- .object({
596
- source: z
597
- .object({
598
- group: nonEmptyString,
599
- kinds: z.array(AuthoredDocKindSchema).min(1).optional(),
600
- })
601
- .strict(),
602
- into: nonEmptyString,
603
- groupBy: z.literal('kind').optional(),
604
- })
605
- .strict(),
606
- )
607
- .optional(),
608
- blocks: z.array(ReferenceContentBlockSchema).optional(),
609
- })
610
- .strict()
611
- .superRefine((doc, context) => {
612
- const slots = new Set(Object.keys(doc.slots));
613
- doc.adopts?.forEach((rule, index) => {
614
- const slot = doc.slots[rule.into];
615
- if (slot == null) {
616
- context.addIssue({
617
- code: 'custom',
618
- path: ['adopts', index, 'into'],
619
- message: `must name a declared slot; received "${rule.into}"`,
620
- });
621
- return;
622
- }
623
- /** @type {AuthoredDocKind[]} */
624
- const adoptedKinds =
625
- rule.groupBy === 'kind' ? ['namespace'] : (rule.source.kinds ?? []);
626
- adoptedKinds.forEach(kind => {
627
- if (!slot.accepts.kinds.includes(kind)) {
628
- context.addIssue({
629
- code: 'custom',
630
- path: ['adopts', index, 'into'],
631
- message: `slot "${rule.into}" does not accept adopted kind "${kind}"`,
632
- });
633
- }
634
- });
635
- });
636
- doc.blocks?.forEach((block, index) => {
637
- if (block.type === 'collection' && !slots.has(block.source.slot)) {
638
- context.addIssue({
639
- code: 'custom',
640
- path: ['blocks', index, 'source', 'slot'],
641
- message: `must name a declared slot; received "${block.source.slot}"`,
642
- });
643
- }
644
- });
645
- });
646
-
647
- /**
648
- * @typedef {import('../_shared/contract.js').Expect<
649
- * import('../_shared/contract.js').Equal<
650
- * z.infer<typeof NamespaceDocKindSchema>,
651
- * NamespaceDoc
652
- * >
653
- * >} _NamespaceDocDriftLock
654
- */
655
-
656
- // Legacy loose format stays permissive for backward compatibility.
236
+ // ── Legacy loose format (unchanged, kept for back-compat) ─────────────
657
237
  const LegacyBaseDocSchema = z.object({
658
- ...AuthoredDocGraphFields,
659
238
  name: z.string().min(1, 'name is required'),
660
239
  displayName: z.string().optional(),
661
240
  description: z.string().optional(),
@@ -676,37 +255,6 @@ const LegacyBaseDocSchema = z.object({
676
255
  relatedHooks: z.array(z.string()).optional(),
677
256
  });
678
257
 
679
- const LegacyReferenceDocSchema = LegacyBaseDocSchema.extend({
680
- title: nonEmptyString,
681
- description: z.string(),
682
- sections: z.array(ReferenceSectionSchema).min(1),
683
- replaces: nonEmptyString.optional(),
684
- extends: nonEmptyString.optional(),
685
- tokenCategory: z.string().optional(),
686
- })
687
- .passthrough()
688
- .superRefine((doc, context) => {
689
- if (doc.replaces != null && doc.extends != null) {
690
- context.addIssue({
691
- code: 'custom',
692
- path: ['extends'],
693
- message: 'declares both `replaces` and `extends`; choose one',
694
- });
695
- }
696
- const sectionIds = new Set();
697
- doc.sections.forEach((section, index) => {
698
- if (section.id == null) return;
699
- if (sectionIds.has(section.id)) {
700
- context.addIssue({
701
- code: 'custom',
702
- path: ['sections', index, 'id'],
703
- message: `duplicate section id "${section.id}"`,
704
- });
705
- }
706
- sectionIds.add(section.id);
707
- });
708
- });
709
-
710
258
  const LegacySingleComponentDocSchema = LegacyBaseDocSchema.extend({
711
259
  props: z.array(PropSchema),
712
260
  }).passthrough();
@@ -726,11 +274,10 @@ const LegacySubComponentDocSchema = LegacyBaseDocSchema.extend({
726
274
  props: z.array(PropSchema),
727
275
  }).passthrough();
728
276
 
729
- /** The permissive legacy union (sub-component, hook, multi, single, then reference). */
277
+ /** The permissive legacy union (sub-component first, then hook, multi, single). */
730
278
  export const LegacyDocSchema = z.union([
731
279
  LegacySubComponentDocSchema,
732
280
  LegacyHookDocSchema,
733
281
  LegacyMultiComponentDocSchema,
734
282
  LegacySingleComponentDocSchema,
735
- LegacyReferenceDocSchema,
736
283
  ]);