@kubb/ast 5.0.0-beta.63 → 5.0.0-beta.64

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 (69) hide show
  1. package/dist/{defineMacro-Shz8f6SG.js → defineMacro-B76LsJwO.js} +4 -4
  2. package/dist/{defineMacro-Shz8f6SG.js.map → defineMacro-B76LsJwO.js.map} +1 -1
  3. package/dist/{defineMacro-BATi7xoC.d.ts → defineMacro-B7qm3zTd.d.ts} +3 -3
  4. package/dist/factory-wJLzHeXT.d.ts +27 -0
  5. package/dist/factory.d.ts +3 -27
  6. package/dist/factory.js +2 -2
  7. package/dist/{index-B9cc8MBS.d.ts → index-BKD4drsX.d.ts} +2 -2
  8. package/dist/index.cjs +54 -2
  9. package/dist/index.cjs.map +1 -1
  10. package/dist/index.d.ts +24 -21
  11. package/dist/index.js +54 -8
  12. package/dist/index.js.map +1 -1
  13. package/dist/macros.d.ts +2 -2
  14. package/dist/macros.js +4 -4
  15. package/dist/{operationParams-k5CKwSWZ.d.ts → operationParams-ByVfpYr7.d.ts} +3 -3
  16. package/dist/{refs-BjNDuCBD.js → refs-Dx6U5LoE.js} +3 -3
  17. package/dist/{refs-BjNDuCBD.js.map → refs-Dx6U5LoE.js.map} +1 -1
  18. package/dist/{schema-Cbnxmz4b.js → schema-YNbOtTCM.js} +2 -2
  19. package/dist/{schema-Cbnxmz4b.js.map → schema-YNbOtTCM.js.map} +1 -1
  20. package/dist/{types-BB_xgRJ3.d.ts → types-BP9BZoq-.d.ts} +8 -8
  21. package/dist/types.d.ts +5 -5
  22. package/dist/{utils-DaXkewb1.js → utils-BJi0y-xg.js} +4 -4
  23. package/dist/{utils-DaXkewb1.js.map → utils-BJi0y-xg.js.map} +1 -1
  24. package/dist/utils.d.ts +3 -3
  25. package/dist/utils.js +3 -3
  26. package/package.json +1 -2
  27. package/src/constants.ts +0 -150
  28. package/src/defineMacro.ts +0 -139
  29. package/src/defineNode.ts +0 -102
  30. package/src/definePrinter.ts +0 -258
  31. package/src/dialect.ts +0 -86
  32. package/src/factory.ts +0 -44
  33. package/src/guards.ts +0 -28
  34. package/src/index.ts +0 -13
  35. package/src/infer.ts +0 -132
  36. package/src/macros/index.ts +0 -3
  37. package/src/macros/macroDiscriminatorEnum.ts +0 -50
  38. package/src/macros/macroEnumName.ts +0 -33
  39. package/src/macros/macroSimplifyUnion.ts +0 -60
  40. package/src/nodes/base.ts +0 -49
  41. package/src/nodes/code.ts +0 -355
  42. package/src/nodes/content.ts +0 -51
  43. package/src/nodes/file.ts +0 -380
  44. package/src/nodes/function.ts +0 -283
  45. package/src/nodes/index.ts +0 -93
  46. package/src/nodes/input.ts +0 -144
  47. package/src/nodes/operation.ts +0 -168
  48. package/src/nodes/output.ts +0 -49
  49. package/src/nodes/parameter.ts +0 -71
  50. package/src/nodes/property.ts +0 -67
  51. package/src/nodes/requestBody.ts +0 -54
  52. package/src/nodes/response.ts +0 -173
  53. package/src/nodes/schema.ts +0 -732
  54. package/src/optionality.ts +0 -15
  55. package/src/registry.ts +0 -75
  56. package/src/signature.ts +0 -207
  57. package/src/types.ts +0 -8
  58. package/src/utils/codegen.ts +0 -103
  59. package/src/utils/extractStringsFromNodes.ts +0 -35
  60. package/src/utils/fileMerge.ts +0 -183
  61. package/src/utils/index.ts +0 -11
  62. package/src/utils/operationParams.ts +0 -353
  63. package/src/utils/refs.ts +0 -134
  64. package/src/utils/schemaGraph.ts +0 -177
  65. package/src/utils/schemaMerge.ts +0 -34
  66. package/src/utils/schemaTraversal.ts +0 -86
  67. package/src/utils/strings.ts +0 -139
  68. package/src/visitor.ts +0 -519
  69. /package/dist/{chunk-CNktS9qV.js → rolldown-runtime-CNktS9qV.js} +0 -0
package/src/nodes/file.ts DELETED
@@ -1,380 +0,0 @@
1
- import { hash } from 'node:crypto'
2
- import path from 'node:path'
3
- import { trimExtName } from '@internals/utils'
4
- import { defineNode } from '../defineNode.ts'
5
- import { extractStringsFromNodes } from '../utils/extractStringsFromNodes.ts'
6
- import { combineExports, combineImports, combineSources } from '../utils/fileMerge.ts'
7
- import type { BaseNode } from './base.ts'
8
- import type { CodeNode } from './code.ts'
9
-
10
- /**
11
- * Supported file extensions.
12
- */
13
- type Extname = '.ts' | '.js' | '.tsx' | '.json' | `.${string}`
14
-
15
- type ImportName = string | Array<string | { propertyName: string; name?: string }>
16
-
17
- /**
18
- * Represents a language-agnostic import/dependency declaration.
19
- *
20
- * @example Named import (TypeScript: `import { useState } from 'react'`)
21
- * ```ts
22
- * createImport({ name: ['useState'], path: 'react' })
23
- * ```
24
- *
25
- * @example Default import (TypeScript: `import React from 'react'`)
26
- * ```ts
27
- * createImport({ name: 'React', path: 'react' })
28
- * ```
29
- *
30
- * @example Type-only import (TypeScript: `import type { FC } from 'react'`)
31
- * ```ts
32
- * createImport({ name: ['FC'], path: 'react', isTypeOnly: true })
33
- * ```
34
- *
35
- * @example Namespace import (TypeScript: `import * as React from 'react'`)
36
- * ```ts
37
- * createImport({ name: 'React', path: 'react', isNameSpace: true })
38
- * ```
39
- */
40
- export type ImportNode = BaseNode & {
41
- kind: 'Import'
42
- /**
43
- * Import name(s) to be used.
44
- *
45
- * @example Named imports
46
- * `['useState']`
47
- *
48
- * @example Default import
49
- * `'React'`
50
- */
51
- name: ImportName
52
- /**
53
- * Path for the import.
54
- *
55
- * @example
56
- * `'@kubb/core'`
57
- */
58
- path: string
59
- /**
60
- * Add a type-only import prefix.
61
- * - `true` generates `import type { Type } from './path'`
62
- * - `false` generates `import { Type } from './path'`
63
- */
64
- isTypeOnly?: boolean | null
65
- /**
66
- * Import the entire module as a namespace.
67
- * - `true` generates `import * as Name from './path'`
68
- * - `false` generates a standard import
69
- */
70
- isNameSpace?: boolean | null
71
- /**
72
- * When set, the import path is resolved relative to this root.
73
- */
74
- root?: string | null
75
- }
76
-
77
- /**
78
- * Represents a language-agnostic export/public API declaration.
79
- *
80
- * @example Named export (TypeScript: `export { Pets } from './Pets'`)
81
- * ```ts
82
- * createExport({ name: ['Pets'], path: './Pets' })
83
- * ```
84
- *
85
- * @example Type-only export (TypeScript: `export type { Pet } from './Pet'`)
86
- * ```ts
87
- * createExport({ name: ['Pet'], path: './Pet', isTypeOnly: true })
88
- * ```
89
- *
90
- * @example Wildcard export (TypeScript: `export * from './utils'`)
91
- * ```ts
92
- * createExport({ path: './utils' })
93
- * ```
94
- *
95
- * @example Namespace alias (TypeScript: `export * as utils from './utils'`)
96
- * ```ts
97
- * createExport({ name: 'utils', path: './utils', asAlias: true })
98
- * ```
99
- */
100
- export type ExportNode = BaseNode & {
101
- kind: 'Export'
102
- /**
103
- * Export name(s) to be used. When omitted, generates a wildcard export.
104
- *
105
- * @example Named exports
106
- * `['useState']`
107
- *
108
- * @example Single export
109
- * `'React'`
110
- */
111
- name?: string | Array<string> | null
112
- /**
113
- * Path for the export.
114
- *
115
- * @example
116
- * `'@kubb/core'`
117
- */
118
- path: string
119
- /**
120
- * Add a type-only export prefix.
121
- * - `true` generates `export type { Type } from './path'`
122
- * - `false` generates `export { Type } from './path'`
123
- */
124
- isTypeOnly?: boolean | null
125
- /**
126
- * Export as an aliased namespace.
127
- * - `true` generates `export * as aliasName from './path'`
128
- * - `false` generates a standard export
129
- */
130
- asAlias?: boolean | null
131
- }
132
-
133
- /**
134
- * Represents a fragment of source code within a file.
135
- *
136
- * @example Named exportable source
137
- * ```ts
138
- * createSource({ name: 'Pet', nodes: [createText('export type Pet = { id: number }')], isExportable: true, isIndexable: true })
139
- * ```
140
- *
141
- * @example Inline unnamed code block
142
- * ```ts
143
- * createSource({ nodes: [createText('const x = 1')] })
144
- * ```
145
- */
146
- export type SourceNode = BaseNode & {
147
- kind: 'Source'
148
- /**
149
- * Optional name identifying this source (used for deduplication and barrel generation).
150
- */
151
- name?: string | null
152
- /**
153
- * Mark this source as a type-only export.
154
- */
155
- isTypeOnly?: boolean | null
156
- /**
157
- * Include the `export` keyword in the generated source.
158
- */
159
- isExportable?: boolean | null
160
- /**
161
- * Include this source in barrel/index file generation.
162
- */
163
- isIndexable?: boolean | null
164
- /**
165
- * Child nodes that make up this source fragment, in DOM order.
166
- * Use a {@link TextNode} for raw string content.
167
- */
168
- nodes?: Array<CodeNode>
169
- }
170
-
171
- /**
172
- * Represents a fully resolved file in the AST.
173
- *
174
- * Created via `createFile()`, which computes the `id`, `name`, and `extname` from the input
175
- * and deduplicates `imports`, `exports`, and `sources`.
176
- *
177
- * @example
178
- * ```ts
179
- * const file = createFile({
180
- * baseName: 'petStore.ts',
181
- * path: 'src/models/petStore.ts',
182
- * sources: [createSource({ name: 'Pet', nodes: [createText('export type Pet = { id: number }')], isExportable: true })],
183
- * imports: [createImport({ name: ['z'], path: 'zod' })],
184
- * exports: [createExport({ name: ['Pet'], path: './petStore' })],
185
- * })
186
- * // file.id = SHA256 hash of the path
187
- * // file.name = 'petStore'
188
- * // file.extname = '.ts'
189
- * ```
190
- */
191
- export type FileNode<TMeta extends object = object> = BaseNode & {
192
- kind: 'File'
193
- /**
194
- * Unique identifier derived from a SHA256 hash of the file path. `createFile`
195
- * computes it, so callers do not need to provide it.
196
- */
197
- id: string
198
- /**
199
- * File name without extension, derived from `baseName`.
200
- *
201
- * @see https://nodejs.org/api/path.html#pathformatpathobject
202
- */
203
- name: string
204
- /**
205
- * File base name, including extension, shaped like `${name}${extname}`.
206
- *
207
- * @see https://nodejs.org/api/path.html#pathbasenamepath-suffix
208
- */
209
- baseName: `${string}.${string}`
210
- /**
211
- * Full qualified path to the file.
212
- */
213
- path: string
214
- /**
215
- * File extension extracted from `baseName`.
216
- */
217
- extname: Extname
218
- /**
219
- * Deduplicated list of source code fragments.
220
- */
221
- sources: Array<SourceNode>
222
- /**
223
- * Deduplicated list of import declarations.
224
- */
225
- imports: Array<ImportNode>
226
- /**
227
- * Deduplicated list of export declarations.
228
- */
229
- exports: Array<ExportNode>
230
- /**
231
- * Optional metadata attached to this file, read by plugins during barrel generation.
232
- */
233
- meta?: TMeta
234
- /**
235
- * Optional banner prepended to the generated file content.
236
- * Accepts `null` so `resolver.resolveBanner()` results can be passed directly.
237
- */
238
- banner?: string | null
239
- /**
240
- * Optional footer appended to the generated file content.
241
- * Accepts `null` so `resolver.resolveFooter()` results can be passed directly.
242
- */
243
- footer?: string | null
244
- }
245
-
246
- /**
247
- * Definition for the {@link ImportNode}.
248
- */
249
- export const importDef = defineNode<ImportNode>({ kind: 'Import' })
250
-
251
- /**
252
- * Definition for the {@link ExportNode}.
253
- */
254
- export const exportDef = defineNode<ExportNode>({ kind: 'Export' })
255
-
256
- /**
257
- * Definition for the {@link SourceNode}.
258
- */
259
- export const sourceDef = defineNode<SourceNode>({ kind: 'Source' })
260
-
261
- /**
262
- * Definition for the {@link FileNode}. The fully resolved builder lives in
263
- * `createFile`, so this definition only supplies the guard.
264
- */
265
- export const fileDef = defineNode<FileNode>({ kind: 'File' })
266
-
267
- /**
268
- * Creates an `ImportNode` representing a language-agnostic import/dependency declaration.
269
- *
270
- * @example Named import
271
- * ```ts
272
- * createImport({ name: ['useState'], path: 'react' })
273
- * // import { useState } from 'react'
274
- * ```
275
- */
276
- export const createImport = importDef.create
277
-
278
- /**
279
- * Creates an `ExportNode` representing a language-agnostic export/public API declaration.
280
- *
281
- * @example Named export
282
- * ```ts
283
- * createExport({ name: ['Pet'], path: './Pet' })
284
- * // export { Pet } from './Pet'
285
- * ```
286
- */
287
- export const createExport = exportDef.create
288
-
289
- /**
290
- * Creates a `SourceNode` representing a fragment of source code within a file.
291
- *
292
- * @example
293
- * ```ts
294
- * createSource({ name: 'Pet', nodes: [createText('export type Pet = { id: number }')], isExportable: true })
295
- * ```
296
- */
297
- export const createSource = sourceDef.create
298
-
299
- /**
300
- * Input descriptor for {@link createFile}, before `id`, `name`, and `extname` are computed
301
- * and `imports`/`exports`/`sources` are deduplicated.
302
- */
303
- export type UserFileNode<TMeta extends object = object> = Omit<FileNode<TMeta>, 'kind' | 'id' | 'name' | 'extname' | 'imports' | 'exports' | 'sources'> &
304
- Pick<Partial<FileNode<TMeta>>, 'imports' | 'exports' | 'sources'>
305
-
306
- /**
307
- * Creates a fully resolved `FileNode` from a file input descriptor.
308
- *
309
- * Computes:
310
- * - `id` SHA256 hash of the file path
311
- * - `name` `baseName` without extension
312
- * - `extname` extension extracted from `baseName`
313
- *
314
- * Deduplicates:
315
- * - `sources` via `combineSources`
316
- * - `exports` via `combineExports`
317
- * - `imports` via `combineImports` (also filters unused imports)
318
- *
319
- * @throws {Error} when `baseName` has no extension.
320
- *
321
- * @example
322
- * ```ts
323
- * const file = createFile({
324
- * baseName: 'petStore.ts',
325
- * path: 'src/models/petStore.ts',
326
- * sources: [createSource({ name: 'Pet', nodes: [createText('export type Pet = { id: number }')] })],
327
- * imports: [createImport({ name: ['z'], path: 'zod' })],
328
- * exports: [createExport({ name: ['Pet'], path: './petStore' })],
329
- * })
330
- * // file.id = SHA256 hash of 'src/models/petStore.ts'
331
- * // file.name = 'petStore'
332
- * // file.extname = '.ts'
333
- * ```
334
- */
335
- export function createFile<TMeta extends object = object>(input: UserFileNode<TMeta>): FileNode<TMeta> {
336
- const rawExtname = path.extname(input.baseName)
337
- // Handle dotfile basename like '.ts' where path.extname returns ''
338
- const extname = (rawExtname || (input.baseName.startsWith('.') ? input.baseName : '')) as `.${string}`
339
- if (!extname) {
340
- throw new Error(`No extname found for ${input.baseName}`)
341
- }
342
-
343
- const source = (input.sources ?? [])
344
- .flatMap((item) => item.nodes ?? [])
345
- .map((node) => extractStringsFromNodes([node]))
346
- .filter(Boolean)
347
- .join('\n\n')
348
- const resolvedExports = input.exports?.length ? combineExports(input.exports) : []
349
- const combinedImports = input.imports?.length ? combineImports(input.imports, resolvedExports, source || undefined) : []
350
- const localNames = new Set((input.sources ?? []).map((item) => item.name).filter((name): name is string => Boolean(name)))
351
- const nameOf = (item: string | { propertyName: string; name?: string }): string => (typeof item === 'string' ? item : (item.name ?? item.propertyName))
352
- // Drop self-imports. Consolidating output (`mode: 'file'`) can place a symbol's
353
- // definition and a cross-file import of it in the same file. The first pass catches imports that
354
- // resolve to this file's own path. The second drops imports of names the file already defines,
355
- // the case consolidation produces when the import path no longer matches `input.path`. Sources
356
- // stay intact, so the local definition remains. Bare specifiers like `'zod'` never match a path.
357
- const resolvedImports = combinedImports
358
- .filter((imp) => imp.path !== input.path)
359
- .flatMap((imp) => {
360
- if (!Array.isArray(imp.name)) {
361
- return typeof imp.name === 'string' && localNames.has(imp.name) ? [] : [imp]
362
- }
363
- const kept = imp.name.filter((item) => !localNames.has(nameOf(item)))
364
- if (!kept.length) return []
365
- return [kept.length === imp.name.length ? imp : { ...imp, name: kept }]
366
- })
367
- const resolvedSources = input.sources?.length ? combineSources(input.sources) : []
368
-
369
- return {
370
- kind: 'File',
371
- ...input,
372
- id: hash('sha256', input.path, 'hex'),
373
- name: trimExtName(input.baseName),
374
- extname,
375
- imports: resolvedImports,
376
- exports: resolvedExports,
377
- sources: resolvedSources,
378
- meta: input.meta ?? ({} as TMeta),
379
- }
380
- }
@@ -1,283 +0,0 @@
1
- import { defineNode } from '../defineNode.ts'
2
- import type { BaseNode } from './base.ts'
3
-
4
- /**
5
- * A language-agnostic type expression used as a function parameter type annotation.
6
- *
7
- * - a plain `string` is a type reference rendered as-is, e.g. `'string'`, `'QueryParams'`, `'Partial<Config>'`
8
- * - a {@link TypeLiteralNode} is an inline anonymous type, e.g. `{ petId: string; name?: string }`
9
- * - an {@link IndexedAccessTypeNode} is a single field accessed from a named type, e.g. `PathParams['petId']`
10
- */
11
- export type TypeExpression = string | TypeLiteralNode | IndexedAccessTypeNode
12
-
13
- /**
14
- * AST node for an inline anonymous object type grouping named fields.
15
- * TypeScript renders as `{ key: Type; other?: OtherType }`.
16
- *
17
- * @example
18
- * ```ts
19
- * createTypeLiteral({ members: [{ name: 'petId', type: 'string', optional: false }] })
20
- * // { petId: string }
21
- * ```
22
- */
23
- export type TypeLiteralNode = BaseNode & {
24
- kind: 'TypeLiteral'
25
- /**
26
- * Members of the object type, rendered in order.
27
- */
28
- members: Array<{
29
- /**
30
- * Member key.
31
- */
32
- name: string
33
- /**
34
- * Member type expression.
35
- */
36
- type: TypeExpression
37
- /**
38
- * Whether the member is optional, rendered with `?`.
39
- */
40
- optional?: boolean
41
- }>
42
- }
43
-
44
- /**
45
- * AST node for a single field accessed from a named group type.
46
- * TypeScript renders as `target['key']`.
47
- *
48
- * @example
49
- * ```ts
50
- * createIndexedAccessType({ target: 'GetPetPathParams', key: 'petId' })
51
- * // GetPetPathParams['petId']
52
- * ```
53
- */
54
- export type IndexedAccessTypeNode = BaseNode & {
55
- kind: 'IndexedAccessType'
56
- /**
57
- * Name of the type being indexed, e.g. `'GetPetPathParams'`.
58
- */
59
- target: string
60
- /**
61
- * Field key to access, e.g. `'petId'`.
62
- */
63
- key: string
64
- }
65
-
66
- /**
67
- * AST node for an object destructuring binding, used as the name of a grouped function parameter.
68
- * TypeScript renders as `{ id, name }` or `{ id: renamed }` when `propertyName` differs.
69
- *
70
- * @example
71
- * ```ts
72
- * createObjectBindingPattern({ elements: [{ name: 'id' }, { name: 'name' }] })
73
- * // { id, name }
74
- * ```
75
- */
76
- export type ObjectBindingPatternNode = BaseNode & {
77
- kind: 'ObjectBindingPattern'
78
- /**
79
- * Bound elements, rendered in order.
80
- */
81
- elements: Array<{
82
- /**
83
- * Local binding name.
84
- */
85
- name: string
86
- /**
87
- * Source key when it differs from the binding name, rendered as `propertyName: name`.
88
- */
89
- propertyName?: string
90
- }>
91
- }
92
-
93
- /**
94
- * AST node for one function parameter.
95
- *
96
- * A simple parameter has a `string` name. A destructured group has an
97
- * {@link ObjectBindingPatternNode} name paired with a {@link TypeLiteralNode} type.
98
- *
99
- * @example Required parameter
100
- * `name: Type`
101
- *
102
- * @example Optional parameter
103
- * `name?: Type`
104
- *
105
- * @example Parameter with default value
106
- * `name: Type = defaultValue`
107
- *
108
- * @example Rest parameter
109
- * `...name: Type[]`
110
- *
111
- * @example Destructured group
112
- * `{ id, name? }: { id: string; name?: string } = {}`
113
- */
114
- export type FunctionParameterNode = BaseNode & {
115
- kind: 'FunctionParameter'
116
- /**
117
- * Parameter name, or an {@link ObjectBindingPatternNode} for a destructured group.
118
- */
119
- name: string | ObjectBindingPatternNode
120
- /**
121
- * Type annotation as a {@link TypeExpression}. Omit for untyped output.
122
- */
123
- type?: TypeExpression
124
- /**
125
- * Whether the parameter is optional, rendered with `?`.
126
- */
127
- optional?: boolean
128
- /**
129
- * Default value, written verbatim after `=`. Commonly `'{}'` for a destructured group.
130
- */
131
- default?: string
132
- /**
133
- * When `true` the parameter is emitted as a rest parameter, e.g. `...name: Type[]`.
134
- */
135
- rest?: boolean
136
- }
137
-
138
- /**
139
- * AST node for a complete function parameter list.
140
- *
141
- * Printers are responsible for sorting (`required` → `optional` → `defaulted`).
142
- * Nodes are plain immutable data.
143
- *
144
- * Renders differently depending on the output mode:
145
- * - `declaration` → `(id: string, config: Config = {})` function declaration parameters
146
- * - `call` → `(id, { method, url })` function call arguments
147
- */
148
- export type FunctionParametersNode = BaseNode & {
149
- kind: 'FunctionParameters'
150
- /**
151
- * Ordered parameter nodes.
152
- */
153
- params: ReadonlyArray<FunctionParameterNode>
154
- }
155
-
156
- /**
157
- * Union of all function-parameter AST node variants used by the function-parameter printer.
158
- */
159
- export type FunctionParamNode = FunctionParameterNode | FunctionParametersNode | TypeLiteralNode | IndexedAccessTypeNode | ObjectBindingPatternNode
160
-
161
- /**
162
- * Handler-map keys for the function-parameter printer, one per {@link FunctionParamNode} kind.
163
- */
164
- export type FunctionParamKind = FunctionParamNode['kind']
165
-
166
- /**
167
- * Definition for the {@link TypeLiteralNode}.
168
- */
169
- export const typeLiteralDef = defineNode<TypeLiteralNode, Pick<TypeLiteralNode, 'members'>>({ kind: 'TypeLiteral' })
170
-
171
- /**
172
- * Definition for the {@link IndexedAccessTypeNode}.
173
- */
174
- export const indexedAccessTypeDef = defineNode<IndexedAccessTypeNode, Omit<IndexedAccessTypeNode, 'kind'>>({ kind: 'IndexedAccessType' })
175
-
176
- /**
177
- * Definition for the {@link ObjectBindingPatternNode}.
178
- */
179
- export const objectBindingPatternDef = defineNode<ObjectBindingPatternNode, Pick<ObjectBindingPatternNode, 'elements'>>({ kind: 'ObjectBindingPattern' })
180
-
181
- /**
182
- * Plain property descriptor for a destructured group built by {@link createFunctionParameter}.
183
- */
184
- type FunctionParameterProperty = {
185
- name: string
186
- type: TypeExpression
187
- optional?: boolean
188
- }
189
-
190
- type FunctionParameterInput =
191
- | { name: string; type?: TypeExpression; optional?: boolean; default?: string; rest?: boolean }
192
- | { properties: Array<FunctionParameterProperty>; optional?: boolean; default?: string }
193
-
194
- /**
195
- * Definition for the {@link FunctionParameterNode}. `optional` defaults to `false`.
196
- * Passing `properties` builds a destructured group: an {@link ObjectBindingPatternNode} name
197
- * paired with a {@link TypeLiteralNode} type.
198
- */
199
- export const functionParameterDef = defineNode<FunctionParameterNode, FunctionParameterInput>({
200
- kind: 'FunctionParameter',
201
- build: (input) => {
202
- if ('properties' in input) {
203
- return {
204
- name: createObjectBindingPattern({ elements: input.properties.map((p) => ({ name: p.name })) }),
205
- type: createTypeLiteral({ members: input.properties.map((p) => ({ name: p.name, type: p.type, optional: p.optional ?? false })) }),
206
- optional: input.optional ?? false,
207
- ...(input.default !== undefined ? { default: input.default } : {}),
208
- }
209
- }
210
- return { optional: false, ...input }
211
- },
212
- })
213
-
214
- /**
215
- * Definition for the {@link FunctionParametersNode}.
216
- */
217
- export const functionParametersDef = defineNode<FunctionParametersNode, Partial<Omit<FunctionParametersNode, 'kind'>>>({
218
- kind: 'FunctionParameters',
219
- defaults: { params: [] },
220
- })
221
-
222
- /**
223
- * Creates a {@link TypeLiteralNode} representing an inline anonymous object type.
224
- *
225
- * @example
226
- * ```ts
227
- * createTypeLiteral({ members: [{ name: 'petId', type: 'string', optional: false }] })
228
- * // { petId: string }
229
- * ```
230
- */
231
- export const createTypeLiteral = typeLiteralDef.create
232
-
233
- /**
234
- * Creates an {@link IndexedAccessTypeNode} representing a single field accessed from a named type.
235
- *
236
- * @example
237
- * ```ts
238
- * createIndexedAccessType({ target: 'DeletePetPathParams', key: 'petId' })
239
- * // DeletePetPathParams['petId']
240
- * ```
241
- */
242
- export const createIndexedAccessType = indexedAccessTypeDef.create
243
-
244
- /**
245
- * Creates an {@link ObjectBindingPatternNode} for a destructured parameter binding.
246
- *
247
- * @example
248
- * ```ts
249
- * createObjectBindingPattern({ elements: [{ name: 'id' }, { name: 'name' }] })
250
- * // { id, name }
251
- * ```
252
- */
253
- export const createObjectBindingPattern = objectBindingPatternDef.create
254
-
255
- /**
256
- * Creates a `FunctionParameterNode`. `optional` defaults to `false`.
257
- *
258
- * @example Optional param
259
- * ```ts
260
- * createFunctionParameter({ name: 'params', type: 'QueryParams', optional: true })
261
- * // → params?: QueryParams
262
- * ```
263
- *
264
- * @example Destructured group
265
- * ```ts
266
- * createFunctionParameter({ properties: [{ name: 'id', type: 'string' }, { name: 'name', type: 'string', optional: true }], default: '{}' })
267
- * // → { id, name }: { id: string; name?: string } = {}
268
- * ```
269
- */
270
- export const createFunctionParameter = functionParameterDef.create
271
-
272
- /**
273
- * Creates a `FunctionParametersNode` from an ordered list of parameters.
274
- *
275
- * @example
276
- * ```ts
277
- * const empty = createFunctionParameters()
278
- * // { kind: 'FunctionParameters', params: [] }
279
- * ```
280
- */
281
- export function createFunctionParameters(props: Partial<Omit<FunctionParametersNode, 'kind'>> = {}): FunctionParametersNode {
282
- return functionParametersDef.create(props)
283
- }