@amritk/generate-validators 0.1.0

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.
package/README.md ADDED
@@ -0,0 +1,105 @@
1
+ <div align="center">
2
+
3
+ # @amritk/generate-validators
4
+
5
+ **Programmatic API for generating predicate-style TypeScript validators from JSON Schemas.**
6
+
7
+ ![status](https://img.shields.io/badge/status-pre--alpha-ef4444?style=flat-square)&nbsp;
8
+ ![version](https://img.shields.io/badge/version-v0.1.0-6366f1?style=flat-square&logo=npm&logoColor=white)&nbsp;
9
+ ![license](https://img.shields.io/badge/license-MIT-22c55e?style=flat-square)&nbsp;
10
+ ![JSON Schema](https://img.shields.io/badge/JSON%20Schema-2020--12-f97316?style=flat-square)&nbsp;
11
+ ![node](https://img.shields.io/badge/node-%E2%89%A520-339933?style=flat-square&logo=node.js&logoColor=white)&nbsp;
12
+ ![vibe coded](https://img.shields.io/badge/vibe%20coded-100%25-a855f7?style=flat-square)
13
+
14
+ </div>
15
+
16
+ ---
17
+
18
+ ## Overview
19
+
20
+ `@amritk/generate-validators` produces lightweight runtime **validators** from a JSON Schema. Where [`@amritk/generate-parsers`](../generate-parsers) coerces and parses unknown input into a typed value, this package emits cheaper predicate-style functions that simply tell you whether a value matches a schema (and where it doesn't).
21
+
22
+ Each generated file exports:
23
+
24
+ - A TypeScript `type` definition for the schema
25
+ - A `validateFoo(input: unknown, _path?: string): ValidationResult` function
26
+
27
+ A shared `validation-result.ts` template and an `index.ts` barrel are emitted alongside the generated files.
28
+
29
+ ---
30
+
31
+ ## Installation
32
+
33
+ ```bash
34
+ npm install @amritk/generate-validators
35
+ # or
36
+ pnpm add @amritk/generate-validators
37
+ # or
38
+ yarn add @amritk/generate-validators
39
+ # or
40
+ bun add @amritk/generate-validators
41
+ ```
42
+
43
+ ---
44
+
45
+ ## Usage
46
+
47
+ ```ts
48
+ import { buildValidatorSchema } from '@amritk/generate-validators'
49
+ import type { JSONSchema } from 'json-schema-typed/draft-2020-12'
50
+
51
+ const schema: JSONSchema = {
52
+ type: 'object',
53
+ properties: {
54
+ info: { $ref: '#/$defs/info' },
55
+ },
56
+ $defs: {
57
+ info: {
58
+ type: 'object',
59
+ properties: { title: { type: 'string' } },
60
+ required: ['title'],
61
+ },
62
+ },
63
+ }
64
+
65
+ const files = await buildValidatorSchema(schema, 'Document')
66
+ // → [{ filename: 'document.ts', content: '...' }, { filename: 'info.ts', ... }, { filename: 'validation-result.ts', ... }, { filename: 'index.ts', ... }]
67
+ ```
68
+
69
+ Write the resulting files to disk and import the validators where you need them:
70
+
71
+ ```ts
72
+ import { validateDocument } from './generated'
73
+
74
+ const result = validateDocument(input)
75
+ if (!result.valid) {
76
+ console.error(result.errors)
77
+ }
78
+ ```
79
+
80
+ ---
81
+
82
+ ## API
83
+
84
+ ### `buildValidatorSchema(rootSchema, rootTypeName)`
85
+
86
+ | Parameter | Type | Description |
87
+ |:---|:---|:---|
88
+ | `rootSchema` | `JSONSchema` | The root schema to traverse. `$ref` and `$dynamicRef` are resolved recursively. Draft-07 schemas are upgraded to 2020-12 automatically. |
89
+ | `rootTypeName` | `string` | Name used for the root type (e.g. `"Document"`). |
90
+
91
+ Returns: `Promise<GeneratedFile[]>` where `GeneratedFile = { filename: string; content: string }`.
92
+
93
+ ---
94
+
95
+ ## Related packages
96
+
97
+ - [`@amritk/generate-parsers`](../generate-parsers) — type definitions plus parsers that coerce input
98
+ - [`@amritk/mjst`](../cli) — CLI wrapper around the generators
99
+ - [`@amritk/helpers`](../helpers) — shared schema-traversal utilities
100
+
101
+ ---
102
+
103
+ ## License
104
+
105
+ [MIT](../../LICENSE)
@@ -0,0 +1,30 @@
1
+ import type { JSONSchema } from 'json-schema-typed/draft-2020-12';
2
+ /**
3
+ * Represents a generated TypeScript file with its filename and content.
4
+ */
5
+ export type GeneratedFile = {
6
+ filename: string;
7
+ content: string;
8
+ };
9
+ /**
10
+ * Builds all TypeScript validator files from a JSON Schema by traversing
11
+ * all $ref references recursively, mirroring the generate-parsers pipeline.
12
+ *
13
+ * Each generated file exports:
14
+ * - A TypeScript type definition
15
+ * - A `validateFoo(input: unknown, _path?: string): ValidationResult` function
16
+ *
17
+ * A `validation-result.ts` file containing the `ValidationResult` and `ValidationError`
18
+ * runtime contract is always emitted. An `index.ts` re-exports everything.
19
+ *
20
+ * @param rootSchema - The root JSON Schema to build from
21
+ * @param rootTypeName - The name for the root type (e.g. "Document")
22
+ * @returns An array of generated TypeScript files
23
+ *
24
+ * @example
25
+ * ```typescript
26
+ * const files = await buildValidatorSchema(schema, 'Document')
27
+ * // files → [{ filename: 'document.ts', content: '...' }, { filename: 'info.ts', ... }, ...]
28
+ * ```
29
+ */
30
+ export declare const buildValidatorSchema: (rootSchema: JSONSchema, rootTypeName: string) => Promise<GeneratedFile[]>;
@@ -0,0 +1,29 @@
1
+ import type { JSONSchema } from 'json-schema-typed/draft-2020-12';
2
+ /**
3
+ * Options for controlling how validator imports are collected.
4
+ */
5
+ type CollectValidatorImportsOptions = {
6
+ /**
7
+ * The $ref path of the schema being generated (e.g. `#/$defs/encoding`).
8
+ * Prevents a file from importing itself.
9
+ */
10
+ readonly selfRef?: string | undefined;
11
+ /**
12
+ * The root schema document. URI refs that cannot be resolved within it
13
+ * are excluded from the import list (they were never generated as files).
14
+ */
15
+ readonly rootSchema?: Record<string, unknown> | undefined;
16
+ };
17
+ /**
18
+ * Collects import statements for all $ref dependencies of a schema.
19
+ * Each import brings in both the generated TypeScript type and validator function.
20
+ *
21
+ * @example
22
+ * ```typescript
23
+ * const schema = { properties: { contact: { $ref: '#/$defs/contact' } } }
24
+ * collectValidatorImports(schema)
25
+ * // ["import { type ContactObject, validateContactObject } from './contact-object'"]
26
+ * ```
27
+ */
28
+ export declare const collectValidatorImports: (schema: JSONSchema, options?: CollectValidatorImportsOptions) => string[];
29
+ export {};
@@ -0,0 +1,39 @@
1
+ import type { JSONSchema } from 'json-schema-typed/draft-2020-12';
2
+ /**
3
+ * Options for controlling what gets generated in a validator file.
4
+ */
5
+ type GenerateValidatorFileOptions = {
6
+ /**
7
+ * The $ref path of the schema being generated (e.g. `#/$defs/info`).
8
+ * Prevents the file from importing itself.
9
+ */
10
+ readonly selfRef?: string;
11
+ /**
12
+ * The root schema document. Used to filter out unresolvable refs.
13
+ */
14
+ readonly rootSchema?: Record<string, unknown>;
15
+ };
16
+ /**
17
+ * Generates a complete TypeScript validator file from a JSON Schema.
18
+ *
19
+ * The file contains:
20
+ * - Imports for the ValidationResult/ValidationError types
21
+ * - Imports for any $ref types and their validator functions
22
+ * - The exported TypeScript type definition
23
+ * - The exported validator function
24
+ *
25
+ * @example
26
+ * ```typescript
27
+ * const schema = {
28
+ * type: 'object',
29
+ * properties: { title: { type: 'string' } },
30
+ * required: ['title'],
31
+ * }
32
+ * generateValidatorFile(schema, 'Info')
33
+ * // import type { ValidationResult, ValidationError } from './validation-result'
34
+ * // export type Info = { title: string }
35
+ * // export const validateInfo = (input: unknown, _path = ''): ValidationResult => { ... }
36
+ * ```
37
+ */
38
+ export declare const generateValidatorFile: (schema: JSONSchema, typeName: string, options?: GenerateValidatorFileOptions) => string;
39
+ export {};
@@ -0,0 +1,24 @@
1
+ import type { JSONSchema } from 'json-schema-typed/draft-2020-12';
2
+ /**
3
+ * Generates a TypeScript validator function from a JSON Schema.
4
+ *
5
+ * The generated function accepts `unknown` input and returns `true` if valid,
6
+ * or `{ valid: false, errors }` with a list of errors if not.
7
+ *
8
+ * Object schemas check that required properties are present and that all
9
+ * provided properties match their declared types. Non-object schemas (strings,
10
+ * numbers, enums, $refs) emit an inline type check.
11
+ *
12
+ * @example
13
+ * ```typescript
14
+ * generateValidatorFunction({ type: 'object', properties: { name: { type: 'string' } }, required: ['name'] }, 'Info')
15
+ * // export const validateInfo = (input: unknown, _path = ''): ValidationResult => {
16
+ * // if (typeof input !== 'object' || ...) return { valid: false, ... }
17
+ * // const errors: ValidationError[] = []
18
+ * // const obj = input as Record<string, unknown>
19
+ * // if (!('name' in obj)) { errors.push(...) } else if (typeof obj['name'] !== 'string') { errors.push(...) }
20
+ * // return errors.length > 0 ? { valid: false, errors } : true
21
+ * // }
22
+ * ```
23
+ */
24
+ export declare const generateValidatorFunction: (schema: JSONSchema, typeName: string) => string;
@@ -0,0 +1,2 @@
1
+ export type { GeneratedFile } from './generators/build-schema';
2
+ export { buildValidatorSchema } from './generators/build-schema';