Runtime validation for static types
npx @tessl/cli install tessl/npm-runtypes@7.0.00
# Runtypes
1
2
Runtypes is a comprehensive TypeScript library that provides runtime type validation for safely bringing untyped data into strongly-typed applications. It offers composable type validators for primitives, literals, arrays, tuples, objects, unions, intersections and more, enabling developers to validate data structures at runtime while maintaining full static type safety.
3
4
## Package Information
5
6
- **Package Name**: runtypes
7
- **Package Type**: npm
8
- **Language**: TypeScript
9
- **Installation**: `npm install runtypes`
10
11
## Core Imports
12
13
```typescript
14
import {
15
String, Number, Boolean, Array, Object, Union, Literal,
16
Never, Nullish, InstanceOf, ValidationError,
17
Contract, AsyncContract, Constraint, Brand, Parser,
18
type Static, type Parsed, type Failcode
19
} from "runtypes";
20
```
21
22
For CommonJS:
23
24
```javascript
25
const {
26
String, Number, Boolean, Array, Object, Union, Literal,
27
Never, Nullish, InstanceOf, ValidationError,
28
Contract, AsyncContract, Constraint, Brand, Parser
29
} = require("runtypes");
30
```
31
32
## Basic Usage
33
34
```typescript
35
import { String, Number, Object, Array, Union, Literal } from "runtypes";
36
37
// Define a user schema
38
const User = Object({
39
id: Number,
40
name: String,
41
email: String,
42
age: Number.optional(),
43
status: Union(Literal("active"), Literal("inactive"))
44
});
45
46
// Extract TypeScript types
47
type UserType = Static<typeof User>;
48
49
// Validate data at runtime
50
const userData = {
51
id: 1,
52
name: "Alice",
53
email: "alice@example.com",
54
status: "active"
55
};
56
57
try {
58
const validUser = User.check(userData);
59
console.log("Valid user:", validUser);
60
} catch (error) {
61
console.error("Validation failed:", error.message);
62
}
63
64
// Use guard for type narrowing
65
if (User.guard(userData)) {
66
// userData is now typed as UserType
67
console.log(userData.name); // TypeScript knows this is a string
68
}
69
```
70
71
## Architecture
72
73
Runtypes is built around several core concepts:
74
75
- **Runtype Class**: Base class providing validation methods (`check`, `guard`, `assert`, `parse`, `inspect`)
76
- **Type Constructors**: Functions that create specific validator types (String, Number, Object, etc.)
77
- **Composition**: Runtypes can be combined using unions, intersections, and other operations
78
- **Result System**: Structured success/failure results with detailed error information
79
- **Static Types**: TypeScript type extraction via `Static<T>` and `Parsed<T>` utilities
80
81
## Capabilities
82
83
### Primitive Validators
84
85
Core type validators for JavaScript primitive values and special types.
86
87
```typescript { .api }
88
const String: Runtype<string>;
89
const Number: Runtype<number>;
90
const Boolean: Runtype<boolean>;
91
const BigInt: Runtype<bigint>;
92
const Symbol: Runtype<symbol>;
93
const Null: Runtype<null>;
94
const Undefined: Runtype<undefined>;
95
const Unknown: Runtype<unknown>;
96
const Never: Runtype<never>;
97
const Nullish: Union<[typeof Null, typeof Undefined]>;
98
const Void: Runtype<unknown>; // deprecated alias for Unknown
99
```
100
101
[Primitive Types](./primitives.md)
102
103
### Literal Values
104
105
Validates exact literal values using SameValueZero equality.
106
107
```typescript { .api }
108
function Literal<T extends LiteralValue>(value: T): Runtype<T>;
109
110
type LiteralValue = undefined | null | boolean | number | bigint | string;
111
```
112
113
[Literal Types](./literals.md)
114
115
### Instance Validation
116
117
Validates that values are instances of specific classes.
118
119
```typescript { .api }
120
function InstanceOf<V>(ctor: Constructor<V>): Runtype<V>;
121
122
type Constructor<V> = { new (...args: never[]): V };
123
```
124
125
### Composite Types
126
127
Complex data structure validators for arrays, objects, and tuples.
128
129
```typescript { .api }
130
function Array<R extends Runtype.Core>(element: R): Array<R>;
131
function Object<O extends Object.Fields>(fields: O): Object<O>;
132
function Tuple<R extends readonly (Runtype.Core | Spread)[]>(...components: R): Tuple<R>;
133
function Record<K extends PropertyKey, V>(key: Runtype<K>, value: Runtype<V>): Record<K, V>;
134
```
135
136
[Composite Types](./composite.md)
137
138
### Union and Intersection Types
139
140
Combines multiple runtypes for flexible validation.
141
142
```typescript { .api }
143
function Union<R extends readonly Runtype.Core[]>(...alternatives: R): Union<R>;
144
function Intersect<R extends readonly Runtype.Core[]>(...intersectees: R): Intersect<R>;
145
```
146
147
[Union and Intersection](./union-intersect.md)
148
149
### Lazy Evaluation
150
151
Enables recursive type definitions by deferring runtype creation.
152
153
```typescript { .api }
154
function Lazy<R extends Runtype.Core>(fn: () => R): Lazy<R>;
155
```
156
157
### Template Literals
158
159
Validates template literal strings with typed interpolation.
160
161
```typescript { .api }
162
function Template<A extends readonly [string, ...string[]], B extends readonly Runtype.Core<LiteralValue>[]>(
163
strings: A,
164
...runtypes: B
165
): Template<A, B>;
166
167
type LiteralValue = undefined | null | boolean | number | bigint | string;
168
```
169
170
[Template Literals](./templates.md)
171
172
### Constraints and Transformations
173
174
Add custom validation logic and data transformation.
175
176
```typescript { .api }
177
function Constraint<T, U extends T>(
178
underlying: Runtype<T>,
179
constraint: (x: T) => asserts x is U
180
): Runtype<U>;
181
182
function Brand<B extends string, T>(brand: B, entity: Runtype<T>): Runtype<T & Brand<B>>;
183
184
function Parser<T, U>(underlying: Runtype<T>, parser: (value: T) => U): Runtype<U>;
185
```
186
187
[Constraints and Transformations](./constraints.md)
188
189
### Function Contracts
190
191
Runtime validation for function arguments and return values.
192
193
```typescript { .api }
194
function Contract<O extends ContractOptions>(options: O): ContractType<O>;
195
function AsyncContract<O extends AsyncContractOptions>(options: O): AsyncContractType<O>;
196
197
interface ContractOptions {
198
receives?: Runtype<readonly unknown[]>;
199
returns?: Runtype;
200
}
201
```
202
203
[Function Contracts](./contracts.md)
204
205
### Validation Results
206
207
Structured results for validation operations with detailed error information.
208
209
```typescript { .api }
210
type Result<T> = Success<T> | Failure;
211
212
interface Success<T> {
213
success: true;
214
value: T;
215
}
216
217
interface Failure {
218
success: false;
219
code: Failcode;
220
message: string;
221
expected: Runtype;
222
received: unknown;
223
details?: Record<PropertyKey, Failure>;
224
detail?: Failure;
225
thrown?: unknown;
226
}
227
```
228
229
[Results and Errors](./results.md)
230
231
### Core Validation Methods
232
233
Every runtype provides these essential validation methods.
234
235
```typescript { .api }
236
interface Runtype<T, X = T> {
237
check<U>(x: U): T & U;
238
guard<U>(x: U): x is T & U;
239
assert<U>(x: U): asserts x is T & U;
240
parse<U>(x: U): X;
241
inspect<U>(x: U, options?: { parse?: boolean }): Result<T | X>;
242
}
243
```
244
245
[Validation Methods](./validation.md)
246
247
### Runtype Composition and Modification Methods
248
249
Methods available on every runtype for composition, constraints, and transformations.
250
251
```typescript { .api }
252
interface Runtype<T, X = T> {
253
// Composition methods
254
or<R extends Runtype.Core>(other: R): Union<[this, R]>;
255
and<R extends Runtype.Core>(other: R): Intersect<[this, R]>;
256
257
// Optional and nullable shortcuts
258
optional(): Optional<this, never>;
259
default<V = never>(value: V): Optional<this, V>;
260
nullable(): Union<[this, Literal<null>]>;
261
undefinedable(): Union<[this, Literal<undefined>]>;
262
nullishable(): Union<[this, Literal<null>, Literal<undefined>]>;
263
264
// Constraint methods
265
withConstraint<Y extends T>(constraint: (x: T) => boolean | string): Constraint<this, Y>;
266
withGuard<Y extends T>(guard: (x: T) => x is Y): Constraint<this, Y>;
267
withAssertion<Y extends T>(assert: (x: T) => asserts x is Y): Constraint<this, Y>;
268
269
// Branding and parsing
270
withBrand<B extends string>(brand: B): Brand<B, this>;
271
withParser<Y>(parser: (value: X) => Y): Parser<this, Y>;
272
273
// Extension
274
with<P extends object>(extension: P | ((self: this) => P)): this & P;
275
276
// Utilities
277
clone(): this;
278
conform<V, Y = V>(this: Conform<V, Y>): Conform<V, Y> & this;
279
}
280
281
// Static methods
282
interface RuntypeStatic {
283
isRuntype(x: unknown): x is Runtype.Interfaces;
284
assertIsRuntype(x: unknown): asserts x is Runtype.Interfaces;
285
}
286
```
287
288
### Utility Functions
289
290
Pattern matching and other utility functions.
291
292
```typescript { .api }
293
function match<C extends readonly Case[]>(...cases: C): Matcher<C>;
294
function when<T, U>(runtype: Runtype<T>, transformer: (value: T) => U): Case<T, U>;
295
```
296
297
[Utilities](./utilities.md)
298
299
## Types
300
301
```typescript { .api }
302
type Static<R extends Runtype> = /* inferred static type */;
303
type Parsed<R extends Runtype> = /* inferred parsed type */;
304
305
class ValidationError extends Error {
306
name: "ValidationError";
307
message: string;
308
failure: Failure;
309
310
constructor(failure: Failure);
311
312
static isValidationError(value: unknown): value is ValidationError;
313
static [Symbol.hasInstance](value: unknown): value is ValidationError;
314
}
315
316
type Failcode =
317
| "TYPE_INCORRECT"
318
| "VALUE_INCORRECT"
319
| "KEY_INCORRECT"
320
| "CONTENT_INCORRECT"
321
| "ARGUMENTS_INCORRECT"
322
| "RETURN_INCORRECT"
323
| "RESOLVE_INCORRECT"
324
| "CONSTRAINT_FAILED"
325
| "PROPERTY_MISSING"
326
| "PROPERTY_PRESENT"
327
| "NOTHING_EXPECTED"
328
| "PARSING_FAILED"
329
| "INSTANCEOF_FAILED";
330
```