decoders 2.2.0 → 2.3.0-beta.2

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/dist/index.d.cts CHANGED
@@ -1,8 +1,6 @@
1
1
  interface ObjectAnnotation {
2
2
  readonly type: 'object';
3
- readonly fields: {
4
- readonly [key: string]: Annotation;
5
- };
3
+ readonly fields: ReadonlyMap<string, Annotation>;
6
4
  readonly text?: string;
7
5
  }
8
6
  interface ArrayAnnotation {
@@ -55,8 +53,12 @@ declare function ok<T>(value: T): Ok<T>;
55
53
  */
56
54
  declare function err<E>(error: E): Err<E>;
57
55
 
58
- type Scalar = string | number | boolean | symbol | undefined | null;
59
56
  type DecodeResult<T> = Result<T, Annotation>;
57
+ /**
58
+ * A function taking a untrusted input, and returning a DecodeResult<T>. The
59
+ * `ok()` and `err()` constructor functions are provided as the 2nd and 3rd
60
+ * param. One of these should be called and its value returned.
61
+ */
60
62
  type AcceptanceFn<T, InputT = unknown> = (blob: InputT, ok: (value: T) => DecodeResult<T>, err: (msg: string | Annotation) => DecodeResult<T>) => DecodeResult<T>;
61
63
  interface Decoder<T> {
62
64
  /**
@@ -94,24 +96,37 @@ interface Decoder<T> {
94
96
  */
95
97
  describe(message: string): Decoder<T>;
96
98
  /**
97
- * Chain together the current decoder with another acceptance function.
99
+ * Send the output of the current decoder into another acceptance function.
100
+ * The given acceptance function will receive the output of the current
101
+ * decoder as its input, making it partially trusted.
102
+ *
103
+ * This works similar to how you would `define()` a new decoder, except
104
+ * that the ``blob`` param will now be ``T`` (a known type), rather than
105
+ * ``unknown``. This will allow the function to make a stronger assumption
106
+ * about its input and avoid re-refining inputs.
107
+ *
108
+ * > _**NOTE:** This is an advanced, low-level, API. It's not recommended
109
+ * > to reach for this construct unless there is no other way. Most cases can
110
+ * > be covered more elegantly by `.transform()` or `.refine()` instead._
111
+ *
112
+ * If it helps, you can think of `define(...)` as equivalent to
113
+ * `unknown.then(...)`.
98
114
  */
99
115
  then<V>(next: AcceptanceFn<V, T>): Decoder<V>;
100
- peek_UNSTABLE<V>(next: AcceptanceFn<V, [unknown, T]>): Decoder<V>;
101
116
  }
102
117
  /**
103
- * Helper type to return the "type" of a Decoder.
118
+ * Helper type to return the output type of a Decoder.
119
+ * It’s the inverse of Decoder<T>.
104
120
  *
105
- * You can use it on types:
121
+ * You can use it at the type level:
106
122
  *
107
123
  * DecoderType<Decoder<string>> // string
108
124
  * DecoderType<Decoder<number[]>> // number[]
109
125
  *
110
- * Or on "values", by using the `typeof` keyword:
126
+ * Or on decoder instances, by using the `typeof` keyword:
111
127
  *
112
128
  * DecoderType<typeof string> // string
113
129
  * DecoderType<typeof truthy> // boolean
114
- *
115
130
  */
116
131
  type DecoderType<D extends Decoder<any>> = D extends Decoder<infer T> ? T : never;
117
132
  /**
@@ -129,36 +144,39 @@ type DecoderType<D extends Decoder<any>> = D extends Decoder<infer T> ? T : neve
129
144
  */
130
145
  declare function define<T>(fn: AcceptanceFn<T>): Decoder<T>;
131
146
 
132
- type JSONValue = null | string | number | boolean | JSONObject | JSONArray;
133
- type JSONObject = {
134
- [key: string]: JSONValue | undefined;
135
- };
136
- type JSONArray = JSONValue[];
147
+ type Formatter = (err: Annotation) => string | Error;
148
+ declare function formatInline(ann: Annotation): string;
149
+ declare function formatShort(ann: Annotation): string;
150
+
137
151
  /**
138
- * Accepts objects that contain only valid JSON values.
152
+ * Accepts any array, but doesn't validate its items further.
153
+ *
154
+ * "poja" means "plain old JavaScript array", a play on `pojo()`.
139
155
  */
140
- declare const jsonObject: Decoder<JSONObject>;
156
+ declare const poja: Decoder<unknown[]>;
141
157
  /**
142
- * Accepts arrays that contain only valid JSON values.
158
+ * Accepts arrays of whatever the given decoder accepts.
143
159
  */
144
- declare const jsonArray: Decoder<JSONArray>;
160
+ declare function array<T>(decoder: Decoder<T>): Decoder<T[]>;
145
161
  /**
146
- * Accepts any value that's a valid JSON value.
147
- *
148
- * In other words: any value returned by `JSON.parse()` should decode without
149
- * failure.
150
- *
151
- * ```typescript
152
- * type JSONValue =
153
- * | null
154
- * | string
155
- * | number
156
- * | boolean
157
- * | { [string]: JSONValue }
158
- * | JSONValue[]
159
- * ```
162
+ * Like `array()`, but will reject arrays with 0 elements.
160
163
  */
161
- declare const json: Decoder<JSONValue>;
164
+ declare function nonEmptyArray<T>(decoder: Decoder<T>): Decoder<[T, ...T[]]>;
165
+ /**
166
+ * Similar to `array()`, but returns the result as an [ES6
167
+ * Set](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Set).
168
+ */
169
+ declare function set<T>(decoder: Decoder<T>): Decoder<Set<T>>;
170
+ type TupleDecoderType<Ds extends readonly Decoder<unknown>[]> = {
171
+ [K in keyof Ds]: DecoderType<Ds[K]>;
172
+ };
173
+ /**
174
+ * Accepts a tuple (an array with exactly _n_ items) of values accepted by the
175
+ * _n_ given decoders.
176
+ */
177
+ declare function tuple<Ds extends readonly [first: Decoder<unknown>, ...rest: readonly Decoder<unknown>[]]>(...decoders: Ds): Decoder<TupleDecoderType<Ds>>;
178
+
179
+ type Scalar = string | number | boolean | symbol | undefined | null;
162
180
 
163
181
  /**
164
182
  * Accepts and returns only the literal `null` value.
@@ -186,15 +204,20 @@ declare function optional<T, V>(decoder: Decoder<T>, defaultValue: (() => V) | V
186
204
  declare function nullable<T>(decoder: Decoder<T>): Decoder<T | null>;
187
205
  declare function nullable<T, C extends Scalar>(decoder: Decoder<T>, defaultValue: (() => C) | C): Decoder<NonNullable<T> | C>;
188
206
  declare function nullable<T, V>(decoder: Decoder<T>, defaultValue: (() => V) | V): Decoder<NonNullable<T> | V>;
207
+ /**
208
+ * @deprecated
209
+ * Alias of `nullish()`.
210
+ */
211
+ declare const maybe: typeof nullish;
189
212
  /**
190
213
  * Accepts whatever the given decoder accepts, or `null`, or `undefined`.
191
214
  *
192
215
  * If a default value is explicitly provided, return that instead in the
193
216
  * `null`/`undefined` case.
194
217
  */
195
- declare function maybe<T>(decoder: Decoder<T>): Decoder<T | null | undefined>;
196
- declare function maybe<T, C extends Scalar>(decoder: Decoder<T>, defaultValue: (() => C) | C): Decoder<NonNullable<T> | C>;
197
- declare function maybe<T, V>(decoder: Decoder<T>, defaultValue: (() => V) | V): Decoder<NonNullable<T> | V>;
218
+ declare function nullish<T>(decoder: Decoder<T>): Decoder<T | null | undefined>;
219
+ declare function nullish<T, C extends Scalar>(decoder: Decoder<T>, defaultValue: (() => C) | C): Decoder<NonNullable<T> | C>;
220
+ declare function nullish<T, V>(decoder: Decoder<T>, defaultValue: (() => V) | V): Decoder<NonNullable<T> | V>;
198
221
  /**
199
222
  * Accepts only the given constant value.
200
223
  */
@@ -208,7 +231,17 @@ declare function constant<C extends Scalar>(value: C): Decoder<C>;
208
231
  declare function always<C extends Scalar>(value: C): Decoder<C>;
209
232
  declare function always<T>(value: (() => T) | T): Decoder<T>;
210
233
  /**
211
- * Alias of always.
234
+ * Rejects all inputs, and always fails with the given error message. May be
235
+ * useful for explicitly disallowing keys, or for testing purposes.
236
+ */
237
+ declare function never(msg: string): Decoder<never>;
238
+ /**
239
+ * Alias of `never()`.
240
+ */
241
+ declare const fail: typeof never;
242
+ /**
243
+ * @deprecated
244
+ * Alias of `always()`.
212
245
  */
213
246
  declare const hardcoded: typeof always;
214
247
  /**
@@ -220,40 +253,11 @@ declare const hardcoded: typeof always;
220
253
  */
221
254
  declare const unknown: Decoder<unknown>;
222
255
  /**
223
- * Alias of unknown.
256
+ * @deprecated
257
+ * Alias of `unknown`.
224
258
  */
225
259
  declare const mixed: Decoder<unknown>;
226
260
 
227
- /**
228
- * Accepts any array, but doesn't validate its items further.
229
- *
230
- * "poja" means "plain old JavaScript array", a play on `pojo()`.
231
- */
232
- declare const poja: Decoder<unknown[]>;
233
- /**
234
- * Accepts arrays of whatever the given decoder accepts.
235
- */
236
- declare function array<T>(decoder: Decoder<T>): Decoder<T[]>;
237
- /**
238
- * Like `array()`, but will reject arrays with 0 elements.
239
- */
240
- declare function nonEmptyArray<T>(decoder: Decoder<T>): Decoder<[T, ...T[]]>;
241
- /**
242
- * Similar to `array()`, but returns the result as an [ES6
243
- * Set](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Set).
244
- */
245
- declare function set<T>(decoder: Decoder<T>): Decoder<Set<T>>;
246
- /**
247
- * Accepts a tuple (an array with exactly _n_ items) of values accepted by the
248
- * _n_ given decoders.
249
- */
250
- declare function tuple<A>(a: Decoder<A>): Decoder<[A]>;
251
- declare function tuple<A, B>(a: Decoder<A>, b: Decoder<B>): Decoder<[A, B]>;
252
- declare function tuple<A, B, C>(a: Decoder<A>, b: Decoder<B>, c: Decoder<C>): Decoder<[A, B, C]>;
253
- declare function tuple<A, B, C, D>(a: Decoder<A>, b: Decoder<B>, c: Decoder<C>, d: Decoder<D>): Decoder<[A, B, C, D]>;
254
- declare function tuple<A, B, C, D, E>(a: Decoder<A>, b: Decoder<B>, c: Decoder<C>, d: Decoder<D>, e: Decoder<E>): Decoder<[A, B, C, D, E]>;
255
- declare function tuple<A, B, C, D, E, F>(a: Decoder<A>, b: Decoder<B>, c: Decoder<C>, d: Decoder<D>, e: Decoder<E>, f: Decoder<F>): Decoder<[A, B, C, D, E, F]>;
256
-
257
261
  /**
258
262
  * Accepts and returns booleans.
259
263
  */
@@ -264,6 +268,9 @@ declare const boolean: Decoder<boolean>;
264
268
  declare const truthy: Decoder<boolean>;
265
269
  /**
266
270
  * Accepts numbers, but return their boolean representation.
271
+ *
272
+ * @deprecated This decoder will be removed in a future version. You can use
273
+ * `truthy` to get almost the same effect.
267
274
  */
268
275
  declare const numericBoolean: Decoder<boolean>;
269
276
 
@@ -280,9 +287,94 @@ declare const date: Decoder<Date>;
280
287
  */
281
288
  declare const iso8601: Decoder<Date>;
282
289
 
290
+ type JSONValue = null | string | number | boolean | JSONObject | JSONArray;
291
+ type JSONObject = {
292
+ [key: string]: JSONValue | undefined;
293
+ };
294
+ type JSONArray = JSONValue[];
295
+ /**
296
+ * Accepts objects that contain only valid JSON values.
297
+ */
298
+ declare const jsonObject: Decoder<JSONObject>;
299
+ /**
300
+ * Accepts arrays that contain only valid JSON values.
301
+ */
302
+ declare const jsonArray: Decoder<JSONArray>;
303
+ /**
304
+ * Accepts any value that's a valid JSON value.
305
+ *
306
+ * In other words: any value returned by `JSON.parse()` should decode without
307
+ * failure.
308
+ *
309
+ * ```typescript
310
+ * type JSONValue =
311
+ * | null
312
+ * | string
313
+ * | number
314
+ * | boolean
315
+ * | { [string]: JSONValue }
316
+ * | JSONValue[]
317
+ * ```
318
+ */
319
+ declare const json: Decoder<JSONValue>;
320
+
321
+ interface Klass<T> extends Function {
322
+ new (...args: readonly any[]): T;
323
+ }
324
+ type Instance<K> = K extends Klass<infer T> ? T : never;
325
+ /**
326
+ * Accepts any value that is an ``instanceof`` the given class.
327
+ */
328
+ declare function instanceOf<K extends Klass<any>>(klass: K): Decoder<Instance<K>>;
329
+ /**
330
+ * Lazily evaluate the given decoder. This is useful to build self-referential
331
+ * types for recursive data structures.
332
+ */
333
+ declare function lazy<T>(decoderFn: () => Decoder<T>): Decoder<T>;
334
+ /**
335
+ * Pre-process the data input before passing it into the decoder. This gives
336
+ * you the ability to arbitrarily customize the input on the fly before passing
337
+ * it to the decoder. Of course, the input value at that point is still of
338
+ * ``unknown`` type, so you will have to deal with that accordingly.
339
+ */
340
+ declare function prep<T>(mapperFn: (blob: unknown) => unknown, decoder: Decoder<T>): Decoder<T>;
341
+
342
+ /**
343
+ * Accepts any valid ``number`` value.
344
+ *
345
+ * This also accepts special values like `NaN` and `Infinity`. Unless you
346
+ * want to deliberately accept those, you'll likely want to use the
347
+ * `number` decoder instead.
348
+ */
349
+ declare const anyNumber: Decoder<number>;
350
+ /**
351
+ * Accepts finite numbers (can be integer or float values). Values `NaN`,
352
+ * or positive and negative `Infinity` will get rejected.
353
+ */
354
+ declare const number: Decoder<number>;
355
+ /**
356
+ * Accepts only finite whole numbers.
357
+ */
358
+ declare const integer: Decoder<number>;
359
+ /**
360
+ * Accepts only non-negative (zero or positive) finite numbers.
361
+ */
362
+ declare const positiveNumber: Decoder<number>;
363
+ /**
364
+ * Accepts only non-negative (zero or positive) finite whole numbers.
365
+ */
366
+ declare const positiveInteger: Decoder<number>;
367
+ /**
368
+ * Accepts any valid ``bigint`` value.
369
+ */
370
+ declare const bigint: Decoder<bigint>;
371
+
283
372
  type RequiredKeys<T extends object> = {
284
373
  [K in keyof T]: undefined extends T[K] ? never : K;
285
374
  }[keyof T];
375
+ type Resolve<T> = T extends (...args: readonly unknown[]) => unknown ? T : {
376
+ [K in keyof T]: T[K];
377
+ };
286
378
  /**
287
379
  * Transforms an object type, by marking all fields that contain "undefined"
288
380
  * with a question mark, i.e. allowing implicit-undefineds when
@@ -305,12 +397,8 @@ type RequiredKeys<T extends object> = {
305
397
  * }
306
398
  */
307
399
  type UndefinedToOptional<T extends object> = Resolve<Pick<Required<T>, RequiredKeys<T>> & Partial<T>>;
308
- type Resolve<T> = T extends (...args: readonly unknown[]) => unknown ? T : {
309
- [K in keyof T]: T[K];
310
- };
311
-
312
- type ObjectDecoderType<T> = UndefinedToOptional<{
313
- [K in keyof T]: T[K] extends Decoder<infer V> ? V : never;
400
+ type ObjectDecoderType<Ds extends Record<string, Decoder<unknown>>> = UndefinedToOptional<{
401
+ [K in keyof Ds]: DecoderType<Ds[K]>;
314
402
  }>;
315
403
  /**
316
404
  * Accepts any "plain old JavaScript object", but doesn't validate its keys or
@@ -321,88 +409,42 @@ declare const pojo: Decoder<Record<string, unknown>>;
321
409
  * Accepts objects with fields matching the given decoders. Extra fields that
322
410
  * exist on the input object are ignored and will not be returned.
323
411
  */
324
- declare function object(decodersByKey: Record<any, never>): Decoder<Record<string, never>>;
325
- declare function object<DS extends Record<string, Decoder<any>>>(decodersByKey: DS): Decoder<ObjectDecoderType<DS>>;
412
+ declare function object(decoders: Record<any, never>): Decoder<Record<string, never>>;
413
+ declare function object<Ds extends Record<string, Decoder<unknown>>>(decoders: Ds): Decoder<ObjectDecoderType<Ds>>;
326
414
  /**
327
415
  * Like `object()`, but will reject inputs that contain extra fields that are
328
416
  * not specified explicitly.
329
417
  */
330
- declare function exact(decodersByKey: Record<any, never>): Decoder<Record<string, never>>;
331
- declare function exact<O extends Record<string, Decoder<any>>>(decodersByKey: O): Decoder<{
332
- [K in keyof ObjectDecoderType<O>]: ObjectDecoderType<O>[K];
333
- }>;
418
+ declare function exact(decoders: Record<any, never>): Decoder<Record<string, never>>;
419
+ declare function exact<Ds extends Record<string, Decoder<unknown>>>(decoders: Ds): Decoder<ObjectDecoderType<Ds>>;
334
420
  /**
335
421
  * Like `object()`, but will pass through any extra fields on the input object
336
422
  * unvalidated that will thus be of `unknown` type statically.
337
423
  */
338
- declare function inexact(decodersByKey: Record<any, never>): Decoder<Record<string, unknown>>;
339
- declare function inexact<O extends Record<string, Decoder<any>>>(decodersByKey: O): Decoder<{
340
- [K in keyof ObjectDecoderType<O>]: ObjectDecoderType<O>[K];
341
- } & Record<string, unknown>>;
424
+ declare function inexact(decoders: Record<any, never>): Decoder<Record<string, unknown>>;
425
+ declare function inexact<Ds extends Record<string, Decoder<unknown>>>(decoders: Ds): Decoder<ObjectDecoderType<Ds> & Record<string, unknown>>;
342
426
  /**
343
427
  * Accepts objects where all values match the given decoder, and returns the
344
- * result as a `Record<string, T>`.
345
- *
346
- * The main difference between `object()` and `dict()` is that you'd typically
347
- * use `object()` if this is a record-like object, where all field names are
348
- * known and the values are heterogeneous. Whereas with `dict()` the keys are
349
- * typically dynamic and the values homogeneous, like in a dictionary,
350
- * a lookup table, or a cache.
428
+ * result as a `Record<string, V>`.
351
429
  */
352
- declare function dict<T>(decoder: Decoder<T>): Decoder<Record<string, T>>;
430
+ declare function record<V>(valueDecoder: Decoder<V>): Decoder<Record<string, V>>;
353
431
  /**
354
- * Similar to `dict()`, but returns the result as a `Map<string, T>` (an [ES6
355
- * Map](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Map))
356
- * instead.
357
- */
358
- declare function mapping<T>(decoder: Decoder<T>): Decoder<Map<string, T>>;
359
-
360
- type Values<T extends object> = T[keyof T];
361
- type DecoderTypes<T> = T extends readonly Decoder<infer U>[] ? U : never;
362
- /**
363
- * Accepts values accepted by any of the given decoders.
364
- *
365
- * The decoders are tried on the input one by one, in the given order. The
366
- * first one that accepts the input "wins". If all decoders reject the input,
367
- * the input gets rejected.
432
+ * Accepts objects where all keys and values match the given decoders, and
433
+ * returns the result as a `Record<K, V>`. The given key decoder must return
434
+ * strings.
368
435
  */
369
- declare function either<T extends readonly Decoder<any>[]>(...decoders: T): Decoder<DecoderTypes<T>>;
436
+ declare function record<K extends string, V>(keyDecoder: Decoder<K>, valueDecoder: Decoder<V>): Decoder<Record<K, V>>;
370
437
  /**
371
- * Accepts any value that is strictly-equal (using `===`) to one of the
372
- * specified values.
438
+ * @deprecated
439
+ * Alias of `record()`.
373
440
  */
374
- declare function oneOf<C extends Scalar>(constants: readonly C[]): Decoder<C>;
441
+ declare const dict: typeof record;
375
442
  /**
376
- * If you are decoding tagged unions you may want to use the `taggedUnion()`
377
- * decoder instead of the general purpose `either()` decoder to get better
378
- * error messages and better performance.
379
- *
380
- * This decoder is optimized for [tagged
381
- * unions](https://en.wikipedia.org/wiki/Tagged_union), i.e. a union of
382
- * objects where one field is used as the discriminator.
383
- *
384
- * ```ts
385
- * const A = object({ tag: constant('A'), foo: string });
386
- * const B = object({ tag: constant('B'), bar: number });
387
- *
388
- * const AorB = taggedUnion('tag', { A, B });
389
- * // ^^^
390
- * ```
391
- *
392
- * Decoding now works in two steps:
393
- *
394
- * 1. Look at the `'tag'` field in the incoming object (this is the field
395
- * that decides which decoder will be used)
396
- * 2. If the value is `'A'`, then decoder `A` will be used. If it's `'B'`, then
397
- * decoder `B` will be used. Otherwise, this will fail.
398
- *
399
- * This is effectively equivalent to `either(A, B)`, but will provide better
400
- * error messages and is more performant at runtime because it doesn't have to
401
- * try all decoders one by one.
443
+ * Similar to `record()`, but returns the result as a `Map<string, T>` (an [ES6
444
+ * Map](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Map))
445
+ * instead.
402
446
  */
403
- declare function taggedUnion<O extends Record<string, Decoder<any>>>(field: string, mapping: O): Decoder<Values<{
404
- [key in keyof O]: DecoderType<O[key]>;
405
- }>>;
447
+ declare function mapping<T>(decoder: Decoder<T>): Decoder<Map<string, T>>;
406
448
 
407
449
  /**
408
450
  * Accepts and returns strings.
@@ -448,65 +490,77 @@ declare const uuidv1: Decoder<string>;
448
490
  * strings.
449
491
  */
450
492
  declare const uuidv4: Decoder<string>;
451
-
452
- interface Klass<T> extends Function {
453
- new (...args: readonly any[]): T;
454
- }
455
- type Instance<K> = K extends Klass<infer T> ? T : never;
456
493
  /**
457
- * Accepts any value that is an ``instanceof`` the given class.
494
+ * Accepts and returns strings with decimal digits only (base-10).
495
+ * To convert these to numbers, use the `numeric` decoder.
458
496
  */
459
- declare function instanceOf<K extends Klass<any>>(klass: K): Decoder<Instance<K>>;
497
+ declare const decimal: Decoder<string>;
460
498
  /**
461
- * Lazily evaluate the given decoder. This is useful to build self-referential
462
- * types for recursive data structures.
499
+ * Accepts and returns strings with hexadecimal digits only (base-16).
463
500
  */
464
- declare function lazy<T>(decoderFn: () => Decoder<T>): Decoder<T>;
501
+ declare const hexadecimal: Decoder<string>;
465
502
  /**
466
- * Pre-process the data input before passing it into the decoder. This gives
467
- * you the ability to arbitrarily customize the input on the fly before passing
468
- * it to the decoder. Of course, the input value at that point is still of
469
- * ``unknown`` type, so you will have to deal with that accordingly.
503
+ * Accepts valid numerical strings (in base-10) and returns them as a number.
504
+ * To only accept numerical strings and keep them as string values, use the
505
+ * `decimal` decoder.
470
506
  */
471
- declare function prep<T>(mapperFn: (blob: unknown) => unknown, decoder: Decoder<T>): Decoder<T>;
472
- /**
473
- * Rejects all inputs, and always fails with the given error message. May be
474
- * useful for explicitly disallowing keys, or for testing purposes.
475
- */
476
- declare function never(msg: string): Decoder<never>;
477
- /**
478
- * Alias of never().
479
- */
480
- declare const fail: typeof never;
507
+ declare const numeric: Decoder<number>;
481
508
 
482
509
  /**
483
- * Accepts any valid ``number`` value.
510
+ * Accepts values accepted by any of the given decoders.
484
511
  *
485
- * This also accepts special values like `NaN` and `Infinity`. Unless you
486
- * want to deliberately accept those, you'll likely want to use the
487
- * `number` decoder instead.
512
+ * The decoders are tried on the input one by one, in the given order. The
513
+ * first one that accepts the input "wins". If all decoders reject the input,
514
+ * the input gets rejected.
488
515
  */
489
- declare const anyNumber: Decoder<number>;
516
+ declare function either<TDecoders extends readonly Decoder<unknown>[], T = DecoderType<TDecoders[number]>>(...decoders: TDecoders): Decoder<T>;
490
517
  /**
491
- * Accepts finite numbers (can be integer or float values). Values `NaN`,
492
- * or positive and negative `Infinity` will get rejected.
518
+ * Accepts any value that is strictly-equal (using `===`) to one of the
519
+ * specified values.
493
520
  */
494
- declare const number: Decoder<number>;
521
+ declare function oneOf<C extends Scalar>(constants: readonly C[]): Decoder<C>;
495
522
  /**
496
- * Accepts only finite whole numbers.
523
+ * Accepts and return an enum value.
497
524
  */
498
- declare const integer: Decoder<number>;
525
+ declare function enum_<TEnum extends Record<string, string | number>>(enumObj: TEnum): Decoder<TEnum[keyof TEnum]>;
499
526
  /**
500
- * Accepts only non-negative (zero or positive) finite numbers.
527
+ * If you are decoding tagged unions you may want to use the `taggedUnion()`
528
+ * decoder instead of the general purpose `either()` decoder to get better
529
+ * error messages and better performance.
530
+ *
531
+ * This decoder is optimized for [tagged
532
+ * unions](https://en.wikipedia.org/wiki/Tagged_union), i.e. a union of
533
+ * objects where one field is used as the discriminator.
534
+ *
535
+ * ```ts
536
+ * const A = object({ tag: constant('A'), foo: string });
537
+ * const B = object({ tag: constant('B'), bar: number });
538
+ *
539
+ * const AorB = taggedUnion('tag', { A, B });
540
+ * // ^^^
541
+ * ```
542
+ *
543
+ * Decoding now works in two steps:
544
+ *
545
+ * 1. Look at the `'tag'` field in the incoming object (this is the field
546
+ * that decides which decoder will be used)
547
+ * 2. If the value is `'A'`, then decoder `A` will be used. If it's `'B'`, then
548
+ * decoder `B` will be used. Otherwise, this will fail.
549
+ *
550
+ * This is effectively equivalent to `either(A, B)`, but will provide better
551
+ * error messages and is more performant at runtime because it doesn't have to
552
+ * try all decoders one by one.
501
553
  */
502
- declare const positiveNumber: Decoder<number>;
554
+ declare function taggedUnion<O extends Record<string, Decoder<unknown>>, T = DecoderType<O[keyof O]>>(field: string, mapping: O): Decoder<T>;
503
555
  /**
504
- * Accepts only non-negative (zero or positive) finite whole numbers.
556
+ * Briefly peek at a runtime input using a "scout" decoder first, then decide
557
+ * which decoder to run on the (original) input, based on the information that
558
+ * the "scout" extracted.
559
+ *
560
+ * It serves a similar purpose as `taggedUnion()`, but is a generalization that
561
+ * works even if there isn't a single discriminator, or the discriminator isn't
562
+ * a string.
505
563
  */
506
- declare const positiveInteger: Decoder<number>;
507
-
508
- type Formatter = (err: Annotation) => string | Error;
509
- declare function formatInline(ann: Annotation): string;
510
- declare function formatShort(ann: Annotation): string;
564
+ declare function select<T, D extends Decoder<unknown>>(scout: Decoder<T>, selectFn: (result: T) => D): Decoder<DecoderType<D>>;
511
565
 
512
- export { type DecodeResult, type Decoder, type DecoderType, type Err, type Formatter, type JSONArray, type JSONObject, type JSONValue, type Ok, type Result, type Scalar, always, anyNumber, array, boolean, constant, date, define, dict, either, email, err, exact, fail, formatInline, formatShort, hardcoded, httpsUrl, inexact, instanceOf, integer, iso8601, json, jsonArray, jsonObject, lazy, mapping, maybe, mixed, never, nonEmptyArray, nonEmptyString, null_, nullable, number, numericBoolean, object, ok, oneOf, optional, poja, pojo, positiveInteger, positiveNumber, prep, regex, set, string, taggedUnion, truthy, tuple, undefined_, unknown, url, uuid, uuidv1, uuidv4 };
566
+ export { type DecodeResult, type Decoder, type DecoderType, type Err, type Formatter, type JSONArray, type JSONObject, type JSONValue, type Ok, type Result, type Scalar, always, anyNumber, array, bigint, boolean, constant, date, decimal, define, dict, either, email, enum_, err, exact, fail, formatInline, formatShort, hardcoded, hexadecimal, httpsUrl, inexact, instanceOf, integer, iso8601, json, jsonArray, jsonObject, lazy, mapping, maybe, mixed, never, nonEmptyArray, nonEmptyString, null_, nullable, nullish, number, numeric, numericBoolean, object, ok, oneOf, optional, poja, pojo, positiveInteger, positiveNumber, prep, record, regex, select, set, string, taggedUnion, truthy, tuple, undefined_, unknown, url, uuid, uuidv1, uuidv4 };