0
# TypeScript AST Utilities
1
2
Comprehensive utilities for creating, manipulating, and converting TypeScript AST nodes. These building blocks enable custom transform functions and provide low-level control over TypeScript code generation.
3
4
## Capabilities
5
6
### AST Conversion Functions
7
8
Core functions for converting between TypeScript AST nodes and source code strings.
9
10
```typescript { .api }
11
/**
12
* Convert TypeScript AST nodes to formatted source code string
13
* @param ast - Array of TypeScript AST nodes to convert
14
* @param options - Formatting and output options
15
* @returns Formatted TypeScript source code string
16
*/
17
function astToString(
18
ast: ts.Node[],
19
options?: AstToStringOptions
20
): string;
21
22
interface AstToStringOptions {
23
/** TypeScript formatting options */
24
formatOptions?: FormatCodeSettings;
25
/** Custom banner text to prepend */
26
banner?: string;
27
/** Custom footer text to append */
28
footer?: string;
29
}
30
31
/**
32
* Parse TypeScript source code string to AST nodes
33
* @param source - TypeScript source code string
34
* @returns Array of parsed AST nodes
35
*/
36
function stringToAST(source: string): unknown[];
37
```
38
39
**Usage Examples:**
40
41
```typescript
42
import { astToString, stringToAST } from "openapi-typescript";
43
44
// Convert AST to string with custom formatting
45
const sourceCode = astToString(astNodes, {
46
formatOptions: {
47
indentSize: 2,
48
insertSpaceAfterCommaDelimiter: true,
49
},
50
banner: "/* Custom header */",
51
footer: "/* Custom footer */"
52
});
53
54
// Parse TypeScript code to AST
55
const parsedNodes = stringToAST(`
56
interface User {
57
id: string;
58
name: string;
59
}
60
`);
61
```
62
63
### TypeScript Type Constants
64
65
Pre-built TypeScript AST nodes for common primitive types.
66
67
```typescript { .api }
68
/** Boolean keyword type node */
69
const BOOLEAN: ts.TypeNode;
70
71
/** False literal type node */
72
const FALSE: ts.TypeNode;
73
74
/** Never keyword type node */
75
const NEVER: ts.TypeNode;
76
77
/** Null literal type node */
78
const NULL: ts.TypeNode;
79
80
/** Number keyword type node */
81
const NUMBER: ts.TypeNode;
82
83
/** String keyword type node */
84
const STRING: ts.TypeNode;
85
86
/** True literal type node */
87
const TRUE: ts.TypeNode;
88
89
/** Undefined keyword type node */
90
const UNDEFINED: ts.TypeNode;
91
92
/** Unknown keyword type node */
93
const UNKNOWN: ts.TypeNode;
94
95
/** Question token for optional properties */
96
const QUESTION_TOKEN: ts.QuestionToken;
97
```
98
99
**Usage Example:**
100
101
```typescript
102
import { STRING, NUMBER, BOOLEAN, QUESTION_TOKEN } from "openapi-typescript";
103
104
// Use pre-built type nodes
105
const stringType = STRING;
106
const numberType = NUMBER;
107
const booleanType = BOOLEAN;
108
```
109
110
### Type Creation Utilities
111
112
Functions for creating complex TypeScript type nodes from values and other types.
113
114
```typescript { .api }
115
/**
116
* Convert JavaScript value to TypeScript literal type node
117
* @param value - JavaScript value to convert
118
* @returns TypeScript literal type node
119
*/
120
function tsLiteral(value: unknown): ts.TypeNode;
121
122
/**
123
* Create union type from array of type nodes
124
* @param types - Array of TypeScript type nodes
125
* @returns Union type node or single type if array has one element
126
*/
127
function tsUnion(types: ts.TypeNode[]): ts.TypeNode;
128
129
/**
130
* Create intersection type from array of type nodes
131
* @param types - Array of TypeScript type nodes
132
* @returns Intersection type node or single type if array has one element
133
*/
134
function tsIntersection(types: ts.TypeNode[]): ts.TypeNode;
135
136
/**
137
* Create nullable type (union with undefined)
138
* @param types - Base type nodes to make nullable
139
* @returns Union type with undefined added
140
*/
141
function tsNullable(types: ts.TypeNode[]): ts.TypeNode;
142
```
143
144
**Usage Examples:**
145
146
```typescript
147
import { tsLiteral, tsUnion, tsIntersection, tsNullable } from "openapi-typescript";
148
149
// Create literal types
150
const stringLiteral = tsLiteral("hello");
151
const numberLiteral = tsLiteral(42);
152
const booleanLiteral = tsLiteral(true);
153
154
// Create union type: string | number | boolean
155
const unionType = tsUnion([STRING, NUMBER, BOOLEAN]);
156
157
// Create intersection type: BaseUser & AdminUser
158
const intersectionType = tsIntersection([baseUserType, adminUserType]);
159
160
// Create nullable type: string | undefined
161
const nullableString = tsNullable([STRING]);
162
```
163
164
### Utility Type Generators
165
166
Functions for creating TypeScript utility types like Record, Omit, and Required.
167
168
```typescript { .api }
169
/**
170
* Create Record utility type
171
* @param key - Key type node
172
* @param value - Value type node
173
* @returns Record<K, V> type reference
174
*/
175
function tsRecord(key: ts.TypeNode, value: ts.TypeNode): ts.TypeNode;
176
177
/**
178
* Create Omit utility type
179
* @param type - Base type node
180
* @param keys - Array of key names to omit
181
* @returns Omit<T, K> type reference
182
*/
183
function tsOmit(type: ts.TypeNode, keys: string[]): ts.TypeNode;
184
185
/**
186
* Create Required utility type
187
* @param type - Base type node
188
* @param keys - Array of key names to make required
189
* @param injectFooter - Nodes to inject after type (needed for type helper)
190
* @returns Required<T> or Pick<Required<T>, K> type reference
191
*/
192
function tsWithRequired(
193
type: ts.TypeNode,
194
keys: string[],
195
injectFooter: ts.Node[]
196
): ts.TypeNode;
197
198
/**
199
* Create readonly array type
200
* @param type - Element type node
201
* @param injectFooter - Optional nodes to inject after type
202
* @returns readonly T[] type node
203
*/
204
function tsReadonlyArray(type: ts.TypeNode, injectFooter?: ts.Node[]): ts.TypeNode;
205
```
206
207
**Usage Examples:**
208
209
```typescript
210
import { tsRecord, tsOmit, tsWithRequired, tsReadonlyArray } from "openapi-typescript";
211
212
// Create Record<string, any>
213
const recordType = tsRecord(STRING, UNKNOWN);
214
215
// Create Omit<User, 'password'>
216
const omitType = tsOmit(userType, ["password"]);
217
218
// Create Required<User> or Pick<Required<User>, 'name' | 'email'>
219
const requiredType = tsWithRequired(userType, ["name", "email"], injectFooter);
220
221
// Create readonly string[]
222
const readonlyArrayType = tsReadonlyArray(STRING);
223
```
224
225
### Declaration and Modifier Utilities
226
227
Functions for creating TypeScript declarations and modifiers.
228
229
```typescript { .api }
230
/**
231
* Create TypeScript modifier arrays
232
* @param modifiers - Modifier configuration object
233
* @returns Array of TypeScript modifier nodes
234
*/
235
function tsModifiers(modifiers: {
236
export?: boolean;
237
readonly?: boolean;
238
}): ts.Modifier[];
239
240
/**
241
* Create property name/index node for object properties
242
* @param index - Property name as string or number
243
* @returns TypeScript property name node
244
*/
245
function tsPropertyIndex(index: string | number): ts.PropertyName;
246
```
247
248
**Usage Examples:**
249
250
```typescript
251
import { tsModifiers, tsPropertyIndex } from "openapi-typescript";
252
253
// Create export modifier
254
const exportModifier = tsModifiers({ export: true });
255
256
// Create readonly export modifiers
257
const readonlyExportModifiers = tsModifiers({
258
export: true,
259
readonly: true
260
});
261
262
// Create property names
263
const stringProp = tsPropertyIndex("userName");
264
const numberProp = tsPropertyIndex(42);
265
```
266
267
### Enum and Array Utilities
268
269
Functions for creating TypeScript enums and array literal expressions.
270
271
```typescript { .api }
272
/**
273
* Create TypeScript enum declaration
274
* @param name - Enum name
275
* @param keys - Array of enum key names
276
* @param values - Optional array of enum values
277
* @param options - Enum creation options
278
* @returns TypeScript enum declaration
279
*/
280
function tsEnum(
281
name: string,
282
keys: (string | number)[],
283
values?: (string | number)[],
284
options?: { export?: boolean; shouldCache?: boolean }
285
): ts.EnumDeclaration;
286
287
/**
288
* Create enum member declarations
289
* @param value - Member value (string or number)
290
* @param metadata - Member metadata (name, description)
291
* @returns Array of TypeScript enum member nodes
292
*/
293
function tsEnumMember(
294
value: string | number,
295
metadata?: { name?: string; description?: string | null }
296
): ts.EnumMember[];
297
298
/**
299
* Create array literal expression as variable declaration
300
* @param name - Variable name
301
* @param elementType - Type of array elements
302
* @param values - Array of values (string or number)
303
* @param options - Array creation options
304
* @returns TypeScript variable statement with array literal
305
*/
306
function tsArrayLiteralExpression(
307
name: string,
308
elementType: ts.TypeNode,
309
values: (string | number)[],
310
options?: { export?: boolean; readonly?: boolean; injectFooter?: ts.Node[] }
311
): ts.VariableStatement;
312
313
/** Global enum declaration cache to prevent duplicates */
314
const enumCache: Map<string, ts.EnumDeclaration>;
315
```
316
317
**Usage Examples:**
318
319
```typescript
320
import { tsEnum, tsEnumMember, tsArrayLiteralExpression } from "openapi-typescript";
321
322
// Create enum with string values
323
const statusEnum = tsEnum(
324
"Status",
325
["ACTIVE", "INACTIVE", "PENDING"],
326
["active", "inactive", "pending"],
327
{ export: true }
328
);
329
330
// Create enum members
331
const enumMembers = tsEnumMember("active", {
332
name: "ACTIVE",
333
description: "User is active"
334
});
335
336
// Create array literal
337
const colorsArray = tsArrayLiteralExpression(
338
"COLORS",
339
STRING, // element type
340
["red", "green", "blue"],
341
{ export: true, readonly: true }
342
);
343
```
344
345
### Regular Expressions and Validation
346
347
Constants and utilities for JavaScript/TypeScript identifier validation.
348
349
```typescript { .api }
350
/** Regular expression for valid JavaScript property names */
351
const JS_PROPERTY_INDEX_RE: RegExp;
352
353
/** Regular expression for invalid characters in enum names */
354
const JS_ENUM_INVALID_CHARS_RE: RegExp;
355
356
/** Regular expression for invalid characters in property names */
357
const JS_PROPERTY_INDEX_INVALID_CHARS_RE: RegExp;
358
359
/** Map of special characters to their replacements */
360
const SPECIAL_CHARACTER_MAP: Record<string, string>;
361
```
362
363
**Usage Examples:**
364
365
```typescript
366
import {
367
JS_PROPERTY_INDEX_RE,
368
JS_ENUM_INVALID_CHARS_RE,
369
SPECIAL_CHARACTER_MAP
370
} from "openapi-typescript";
371
372
// Check if string is valid property name
373
const isValidProperty = JS_PROPERTY_INDEX_RE.test("userName"); // true
374
const isInvalidProperty = JS_PROPERTY_INDEX_RE.test("user-name"); // false
375
376
// Clean enum names
377
const cleanEnumName = "some+enum".replace(JS_ENUM_INVALID_CHARS_RE, "_");
378
379
// Replace special characters
380
const cleaned = "some+thing".replace("+", SPECIAL_CHARACTER_MAP["+"]);
381
```
382
383
### Type Checking and Manipulation
384
385
Utilities for analyzing and manipulating TypeScript type nodes.
386
387
```typescript { .api }
388
/**
389
* Check if TypeScript type node represents a primitive type
390
* @param type - TypeScript type node to check
391
* @returns True if type is primitive (string, number, boolean, etc.)
392
*/
393
function tsIsPrimitive(type: ts.TypeNode): boolean;
394
395
/**
396
* Remove duplicate types from array of type nodes
397
* @param types - Array of TypeScript type nodes
398
* @returns Array with duplicate types removed
399
*/
400
function tsDedupe(types: ts.TypeNode[]): ts.TypeNode[];
401
```
402
403
**Usage Examples:**
404
405
```typescript
406
import { tsIsPrimitive, tsDedupe } from "openapi-typescript";
407
408
// Check if type is primitive
409
const isPrimitive = tsIsPrimitive(STRING); // true
410
const isObject = tsIsPrimitive(objectType); // false
411
412
// Remove duplicates from type array
413
const uniqueTypes = tsDedupe([STRING, NUMBER, STRING, BOOLEAN]);
414
// Result: [STRING, NUMBER, BOOLEAN]
415
```
416
417
### JSDoc Comment Utilities
418
419
Functions for adding JSDoc comments to TypeScript nodes.
420
421
```typescript { .api }
422
/**
423
* Schema object interface for JSDoc comment generation
424
*/
425
interface AnnotatedSchemaObject {
426
const?: unknown;
427
default?: unknown;
428
deprecated?: boolean;
429
description?: string;
430
enum?: unknown[];
431
example?: string;
432
examples?: unknown;
433
format?: string;
434
nullable?: boolean;
435
summary?: string;
436
title?: string;
437
type?: string | string[];
438
}
439
440
/**
441
* Add JSDoc comment to TypeScript property signature
442
* @param schemaObject - Schema object with metadata
443
* @param node - TypeScript property signature to annotate
444
* @returns void (modifies node in place)
445
*/
446
function addJSDocComment(
447
schemaObject: AnnotatedSchemaObject,
448
node: ts.PropertySignature
449
): void;
450
```
451
452
**Usage Example:**
453
454
```typescript
455
import { addJSDocComment } from "openapi-typescript";
456
457
const schemaMetadata = {
458
description: "User's email address",
459
format: "email",
460
example: "user@example.com"
461
};
462
463
// Add JSDoc comment to property
464
addJSDocComment(schemaMetadata, propertyNode);
465
```
466
467
### OpenAPI Reference Utilities
468
469
Utilities for creating TypeScript reference types from OpenAPI $ref pointers.
470
471
```typescript { .api }
472
/**
473
* Create TypeScript reference type from OpenAPI $ref path
474
* @param path - OpenAPI $ref path (e.g., "#/components/schemas/User")
475
* @param resolved - Optional resolved reference metadata
476
* @returns TypeScript type reference node
477
*/
478
function oapiRef(path: string, resolved?: OapiRefResolved): ts.TypeNode;
479
480
interface OapiRefResolved {
481
schemaObject: SchemaObject;
482
isComponent: boolean;
483
}
484
```
485
486
**Usage Example:**
487
488
```typescript
489
import { oapiRef } from "openapi-typescript";
490
491
// Create reference to component schema
492
const userRef = oapiRef("#/components/schemas/User");
493
494
// Create reference with resolved metadata
495
const resolvedRef = oapiRef("#/components/schemas/Product", {
496
schemaObject: productSchema,
497
isComponent: true
498
});
499
```
500
501
### General Utilities
502
503
Additional utilities for schema processing, debugging, and OpenAPI reference handling.
504
505
```typescript { .api }
506
/**
507
* Debug logging with color groups and timing
508
* @param msg - Debug message to log
509
* @param group - Optional group for color coding (redoc, lint, bundle, ts)
510
* @param time - Optional timing information in milliseconds
511
* @returns void
512
*/
513
function debug(msg: string, group?: string, time?: number): void;
514
515
/**
516
* Format error messages with color
517
* @param msg - Error message to format
518
* @returns Formatted error message string
519
*/
520
function error(msg: string): string;
521
522
/**
523
* Format warning messages with color
524
* @param msg - Warning message to format
525
* @param silent - Whether to suppress output
526
* @returns void
527
*/
528
function warn(msg: string, silent?: boolean): void;
529
530
/**
531
* Format performance timing in readable format
532
* @param t - Time in milliseconds
533
* @returns Formatted time string (e.g., "1.23s", "456ms")
534
*/
535
function formatTime(t: number): string;
536
537
/**
538
* Create OpenAPI reference pointer from path parts
539
* @param parts - Array of path components (strings, numbers, etc.)
540
* @returns OpenAPI $ref pointer string
541
*/
542
function createRef(parts: (number | string | undefined | null)[]): string;
543
544
/**
545
* Resolve OpenAPI $ref pointers within a schema
546
* @param schema - OpenAPI document to resolve within
547
* @param $ref - Reference pointer to resolve
548
* @param options - Resolution options
549
* @returns Resolved object of type T
550
*/
551
function resolveRef<T>(
552
schema: OpenAPI3,
553
$ref: string,
554
options?: { silent?: boolean }
555
): T;
556
557
/**
558
* Type-safe Object.entries with filtering capabilities
559
* @param obj - Object or array-like object to get entries from
560
* @param options - Filtering and sorting options
561
* @returns Array of [key, value] tuples
562
*/
563
function getEntries<T>(
564
obj: ArrayLike<T> | Record<string, T>,
565
options?: {
566
alphabetize?: boolean;
567
excludeDeprecated?: boolean;
568
}
569
): [string, T][];
570
571
/**
572
* Scan OpenAPI schema for discriminator objects
573
* @param schema - OpenAPI document to scan
574
* @param options - Scanning options
575
* @returns Map of discriminator objects by schema path
576
*/
577
function scanDiscriminators(
578
schema: OpenAPI3,
579
options: OpenAPITSOptions
580
): Map<string, DiscriminatorObject>;
581
582
/**
583
* Walk JSON-serializable object recursively with visitor function
584
* @param obj - Object to walk recursively
585
* @param cb - Callback function called for each object
586
* @param path - Current path (internal parameter)
587
* @returns void
588
*/
589
function walk(
590
obj: unknown,
591
cb: (value: Record<string, unknown>, path: (string | number)[]) => void,
592
path?: (string | number)[]
593
): void;
594
595
/**
596
* Create discriminator property for polymorphic schemas
597
* @param discriminator - Discriminator object from OpenAPI
598
* @param options - Property creation options
599
* @returns TypeScript property signature for discriminator
600
*/
601
function createDiscriminatorProperty(
602
discriminator: DiscriminatorObject,
603
options: { path: string; readonly?: boolean }
604
): ts.TypeElement;
605
606
/** Color formatting utilities (re-export from ansi-colors) */
607
const c: typeof import("ansi-colors");
608
```
609
610
**Usage Examples:**
611
612
```typescript
613
import {
614
debug,
615
error,
616
warn,
617
formatTime,
618
createRef,
619
resolveRef,
620
getEntries,
621
c
622
} from "openapi-typescript";
623
624
// Debug logging with groups
625
debug("Processing schema", "ts", 123.45);
626
627
// Error formatting
628
const errorMsg = error("Schema validation failed");
629
630
// Warning with silent option
631
warn("Deprecated property found", false);
632
633
// Format timing
634
const timeStr = formatTime(1234.56); // "1.23s"
635
636
// Create reference pointer
637
const ref = createRef(["components", "schemas", "User"]); // "#/components/schemas/User"
638
639
// Resolve reference
640
const resolvedSchema = resolveRef(openApiDoc, "#/components/schemas/User");
641
642
// Get filtered entries
643
const entries = getEntries(componentsObject, {
644
alphabetize: true,
645
excludeDeprecated: true
646
});
647
648
// Use color formatting
649
console.log(c.green("Success:"), c.blue("Types generated"));
650
```