Comparing version 0.9.4 to 0.9.5
@@ -16,2 +16,13 @@ # Changelog | ||
# 0.9.5 | ||
* **New Feature** | ||
* add `mixed` type (@gcanti) | ||
* replace `any` with `mixed` in all input type parameters (@gcanti) | ||
```diff | ||
-export class StringType extends Type<any, string> { | ||
+export class StringType extends Type<mixed, string> { | ||
} | ||
``` | ||
# 0.9.4 | ||
@@ -18,0 +29,0 @@ |
@@ -8,2 +8,3 @@ import { Either } from 'fp-ts/lib/Either'; | ||
} | ||
export declare type mixed = object | number | string | boolean | symbol | undefined | null; | ||
export interface ContextEntry { | ||
@@ -15,3 +16,3 @@ readonly key: string; | ||
export interface ValidationError { | ||
readonly value: any; | ||
readonly value: mixed; | ||
readonly context: Context; | ||
@@ -21,8 +22,8 @@ } | ||
export declare type Validation<A> = Either<Errors, A>; | ||
export declare type Is<A> = (v: any) => v is A; | ||
export declare type Is<A> = (v: mixed) => v is A; | ||
export declare type Validate<S, A> = (s: S, context: Context) => Validation<A>; | ||
export declare type Serialize<S, A> = (a: A) => S; | ||
export declare type Any = Type<any, any>; | ||
export declare type TypeOf<RT extends Any> = RT['_A']; | ||
export declare type InputOf<RT extends Any> = RT['_S']; | ||
export declare type Any = Type<mixed, any>; | ||
export declare type TypeOf<RT extends Type<any, any>> = RT['_A']; | ||
export declare type InputOf<RT extends Type<any, any>> = RT['_S']; | ||
export interface Decoder<S, A> { | ||
@@ -41,9 +42,21 @@ readonly name: string; | ||
export declare class Type<S, A> implements Decoder<S, A>, Encoder<S, A> { | ||
/** a unique name for this runtime type */ | ||
readonly name: string; | ||
/** a custom type guard */ | ||
readonly is: Is<A>; | ||
/** succeeds if a value of type S can be decoded to a value of type A */ | ||
readonly validate: Validate<S, A>; | ||
/** converts a value of type A to a value of type S */ | ||
readonly serialize: Serialize<S, A>; | ||
readonly '_A': A; | ||
readonly '_S': S; | ||
constructor(name: string, is: Is<A>, validate: Validate<S, A>, serialize: Serialize<S, A>); | ||
constructor( | ||
/** a unique name for this runtime type */ | ||
name: string, | ||
/** a custom type guard */ | ||
is: Is<A>, | ||
/** succeeds if a value of type S can be decoded to a value of type A */ | ||
validate: Validate<S, A>, | ||
/** converts a value of type A to a value of type S */ | ||
serialize: Serialize<S, A>); | ||
pipe<B>(ab: Type<A, B>, name?: string): Type<S, B>; | ||
@@ -54,12 +67,12 @@ asDecoder(): Decoder<S, A>; | ||
export declare const identity: <A>(a: A) => A; | ||
export declare const getFunctionName: (f: any) => string; | ||
export declare const getFunctionName: (f: Function) => string; | ||
export declare const getContextEntry: (key: string, type: Decoder<any, any>) => ContextEntry; | ||
export declare const getValidationError: (value: any, context: ContextEntry[]) => ValidationError; | ||
export declare const getValidationError: (value: mixed, context: ContextEntry[]) => ValidationError; | ||
export declare const getDefaultContext: (type: Decoder<any, any>) => ContextEntry[]; | ||
export declare const appendContext: (c: ContextEntry[], key: string, type: Decoder<any, any>) => ContextEntry[]; | ||
export declare const failures: <T>(errors: ValidationError[]) => Either<ValidationError[], T>; | ||
export declare const failure: <T>(value: any, context: ContextEntry[]) => Either<ValidationError[], T>; | ||
export declare const failure: <T>(value: mixed, context: ContextEntry[]) => Either<ValidationError[], T>; | ||
export declare const success: <T>(value: T) => Either<ValidationError[], T>; | ||
export declare const validate: <S, A>(value: S, type: Decoder<S, A>) => Either<ValidationError[], A>; | ||
export declare class NullType extends Type<any, null> { | ||
export declare class NullType extends Type<mixed, null> { | ||
readonly _tag: 'NullType'; | ||
@@ -70,3 +83,3 @@ constructor(); | ||
export declare const nullType: NullType; | ||
export declare class UndefinedType extends Type<any, undefined> { | ||
export declare class UndefinedType extends Type<mixed, undefined> { | ||
readonly _tag: 'UndefinedType'; | ||
@@ -76,3 +89,3 @@ constructor(); | ||
declare const undefinedType: UndefinedType; | ||
export declare class AnyType extends Type<any, any> { | ||
export declare class AnyType extends Type<mixed, any> { | ||
readonly _tag: 'AnyType'; | ||
@@ -82,3 +95,3 @@ constructor(); | ||
export declare const any: AnyType; | ||
export declare class NeverType extends Type<any, never> { | ||
export declare class NeverType extends Type<mixed, never> { | ||
readonly _tag: 'NeverType'; | ||
@@ -88,3 +101,3 @@ constructor(); | ||
export declare const never: NeverType; | ||
export declare class StringType extends Type<any, string> { | ||
export declare class StringType extends Type<mixed, string> { | ||
readonly _tag: 'StringType'; | ||
@@ -94,3 +107,3 @@ constructor(); | ||
export declare const string: StringType; | ||
export declare class NumberType extends Type<any, number> { | ||
export declare class NumberType extends Type<mixed, number> { | ||
readonly _tag: 'NumberType'; | ||
@@ -100,3 +113,3 @@ constructor(); | ||
export declare const number: NumberType; | ||
export declare class BooleanType extends Type<any, boolean> { | ||
export declare class BooleanType extends Type<mixed, boolean> { | ||
readonly _tag: 'BooleanType'; | ||
@@ -106,3 +119,3 @@ constructor(); | ||
export declare const boolean: BooleanType; | ||
export declare class AnyArrayType extends Type<any, Array<any>> { | ||
export declare class AnyArrayType extends Type<mixed, Array<mixed>> { | ||
readonly _tag: 'AnyArrayType'; | ||
@@ -112,4 +125,4 @@ constructor(); | ||
declare const arrayType: AnyArrayType; | ||
export declare class AnyDictionaryType extends Type<any, { | ||
[key: string]: any; | ||
export declare class AnyDictionaryType extends Type<mixed, { | ||
[key: string]: mixed; | ||
}> { | ||
@@ -120,3 +133,3 @@ readonly _tag: 'AnyDictionaryType'; | ||
export declare const Dictionary: AnyDictionaryType; | ||
export declare class ObjectType extends Type<any, object> { | ||
export declare class ObjectType extends Type<mixed, object> { | ||
readonly _tag: 'ObjectType'; | ||
@@ -126,3 +139,3 @@ constructor(); | ||
export declare const object: ObjectType; | ||
export declare class FunctionType extends Type<any, Function> { | ||
export declare class FunctionType extends Type<mixed, Function> { | ||
readonly _tag: 'FunctionType'; | ||
@@ -132,3 +145,3 @@ constructor(); | ||
export declare const Function: FunctionType; | ||
export declare class RefinementType<RT extends Any, S, A> extends Type<S, A> { | ||
export declare class RefinementType<RT extends Type<any, any>, S, A> extends Type<S, A> { | ||
readonly type: RT; | ||
@@ -140,4 +153,4 @@ readonly predicate: Predicate<A>; | ||
export declare const refinement: <RT extends Type<any, any>>(type: RT, predicate: Predicate<RT["_A"]>, name?: string) => RefinementType<RT, RT["_S"], RT["_A"]>; | ||
export declare const Integer: RefinementType<NumberType, any, number>; | ||
export declare class LiteralType<V extends string | number | boolean> extends Type<any, V> { | ||
export declare const Integer: RefinementType<NumberType, mixed, number>; | ||
export declare class LiteralType<V extends string | number | boolean> extends Type<mixed, V> { | ||
readonly value: V; | ||
@@ -150,3 +163,3 @@ readonly _tag: 'LiteralType'; | ||
[key: string]: any; | ||
}> extends Type<any, keyof D> { | ||
}> extends Type<mixed, keyof D> { | ||
readonly keys: D; | ||
@@ -159,3 +172,3 @@ readonly _tag: 'KeyofType'; | ||
}>(keys: D, name?: string) => KeyofType<D>; | ||
export declare class RecursiveType<RT extends Any, A> extends Type<any, A> { | ||
export declare class RecursiveType<RT extends Any, A> extends Type<mixed, A> { | ||
readonly _tag: 'RecursiveType'; | ||
@@ -165,4 +178,4 @@ readonly 'type': RT; | ||
} | ||
export declare const recursion: <A, RT extends Type<any, any> = Type<any, any>>(name: string, definition: (self: RT) => RT) => RecursiveType<RT, A>; | ||
export declare class ArrayType<RT extends Any, A> extends Type<any, A> { | ||
export declare const recursion: <A, RT extends Type<mixed, any> = Type<mixed, any>>(name: string, definition: (self: RT) => RT) => RecursiveType<RT, A>; | ||
export declare class ArrayType<RT extends Any, A> extends Type<mixed, A> { | ||
readonly type: RT; | ||
@@ -172,3 +185,3 @@ readonly _tag: 'ArrayType'; | ||
} | ||
export declare const array: <RT extends Type<any, any>>(type: RT, name?: string) => ArrayType<RT, RT["_A"][]>; | ||
export declare const array: <RT extends Type<mixed, any>>(type: RT, name?: string) => ArrayType<RT, RT["_A"][]>; | ||
export declare type Props = { | ||
@@ -180,3 +193,3 @@ [key: string]: Any; | ||
}; | ||
export declare class InterfaceType<P extends Props, A> extends Type<any, A> { | ||
export declare class InterfaceType<P extends Props, A> extends Type<mixed, A> { | ||
readonly props: P; | ||
@@ -191,3 +204,3 @@ readonly _tag: 'InterfaceType'; | ||
}; | ||
export declare class PartialType<P extends Props, A> extends Type<any, A> { | ||
export declare class PartialType<P extends Props, A> extends Type<mixed, A> { | ||
readonly props: P; | ||
@@ -198,3 +211,3 @@ readonly _tag: 'PartialType'; | ||
export declare const partial: <P extends Props>(props: P, name?: string) => PartialType<P, PartialOf<P>>; | ||
export declare class DictionaryType<D extends Any, C extends Any, A> extends Type<any, A> { | ||
export declare class DictionaryType<D extends Any, C extends Any, A> extends Type<mixed, A> { | ||
readonly domain: D; | ||
@@ -205,6 +218,6 @@ readonly codomain: C; | ||
} | ||
export declare const dictionary: <D extends Type<any, any>, C extends Type<any, any>>(domain: D, codomain: C, name?: string) => DictionaryType<D, C, { | ||
export declare const dictionary: <D extends Type<mixed, any>, C extends Type<mixed, any>>(domain: D, codomain: C, name?: string) => DictionaryType<D, C, { | ||
[K in D["_A"]]: C["_A"]; | ||
}>; | ||
export declare class UnionType<RTS extends Array<Any>, A> extends Type<any, A> { | ||
export declare class UnionType<RTS extends Array<Any>, A> extends Type<mixed, A> { | ||
readonly types: RTS; | ||
@@ -214,7 +227,7 @@ readonly _tag: 'UnionType'; | ||
} | ||
export declare const union: <RTS extends Type<any, any>[]>(types: RTS, name?: string) => UnionType<RTS, RTS["_A"]["_A"]>; | ||
export declare class IntersectionType<RTS extends Array<Any>, A> extends Type<any, A> { | ||
export declare const union: <RTS extends Type<mixed, any>[]>(types: RTS, name?: string) => UnionType<RTS, RTS["_A"]["_A"]>; | ||
export declare class IntersectionType<RTS extends Array<Any>, A> extends Type<mixed, A> { | ||
readonly types: RTS; | ||
readonly _tag: 'IntersectionType'; | ||
constructor(name: string, is: Is<A>, validate: Validate<any, A>, serialize: Serialize<any, A>, types: RTS); | ||
constructor(name: string, is: Is<A>, validate: Validate<mixed, A>, serialize: Serialize<mixed, A>, types: RTS); | ||
} | ||
@@ -226,6 +239,6 @@ export declare function intersection<A extends Any, B extends Any, C extends Any, D extends Any, E extends Any>(types: [A, B, C, D, E], name?: string): IntersectionType<[A, B, C, D, E], TypeOf<A> & TypeOf<B> & TypeOf<C> & TypeOf<D> & TypeOf<E>>; | ||
export declare function intersection<A extends Any>(types: [A], name?: string): IntersectionType<[A], TypeOf<A>>; | ||
export declare class TupleType<RTS extends Array<Any>, A> extends Type<any, A> { | ||
export declare class TupleType<RTS extends Array<Any>, A> extends Type<mixed, A> { | ||
readonly types: RTS; | ||
readonly _tag: 'TupleType'; | ||
constructor(name: string, is: Is<A>, validate: Validate<any, A>, serialize: Serialize<any, A>, types: RTS); | ||
constructor(name: string, is: Is<A>, validate: Validate<mixed, A>, serialize: Serialize<mixed, A>, types: RTS); | ||
} | ||
@@ -237,3 +250,3 @@ export declare function tuple<A extends Any, B extends Any, C extends Any, D extends Any, E extends Any>(types: [A, B, C, D, E], name?: string): TupleType<[A, B, C, D, E], [TypeOf<A>, TypeOf<B>, TypeOf<C>, TypeOf<D>, TypeOf<E>]>; | ||
export declare function tuple<A extends Any>(types: [A], name?: string): TupleType<[A], [TypeOf<A>]>; | ||
export declare class ReadonlyType<RT extends Any, A> extends Type<any, A> { | ||
export declare class ReadonlyType<RT extends Any, A> extends Type<mixed, A> { | ||
readonly type: RT; | ||
@@ -243,4 +256,4 @@ readonly _tag: 'ReadonlyType'; | ||
} | ||
export declare const readonly: <RT extends Type<any, any>>(type: RT, name?: string) => ReadonlyType<RT, Readonly<RT["_A"]>>; | ||
export declare class ReadonlyArrayType<RT extends Any, A> extends Type<any, A> { | ||
export declare const readonly: <RT extends Type<mixed, any>>(type: RT, name?: string) => ReadonlyType<RT, Readonly<RT["_A"]>>; | ||
export declare class ReadonlyArrayType<RT extends Any, A> extends Type<mixed, A> { | ||
readonly type: RT; | ||
@@ -250,4 +263,4 @@ readonly _tag: 'ReadonlyArrayType'; | ||
} | ||
export declare const readonlyArray: <RT extends Type<any, any>>(type: RT, name?: string) => ReadonlyArrayType<RT, ReadonlyArray<RT["_A"]>>; | ||
export declare class StrictType<P extends Props, A> extends Type<any, A> { | ||
export declare const readonlyArray: <RT extends Type<mixed, any>>(type: RT, name?: string) => ReadonlyArrayType<RT, ReadonlyArray<RT["_A"]>>; | ||
export declare class StrictType<P extends Props, A> extends Type<mixed, A> { | ||
readonly props: P; | ||
@@ -254,0 +267,0 @@ readonly _tag: 'StrictType'; |
@@ -28,3 +28,11 @@ "use strict"; | ||
var Type = /** @class */ (function () { | ||
function Type(name, is, validate, serialize) { | ||
function Type( | ||
/** a unique name for this runtime type */ | ||
name, | ||
/** a custom type guard */ | ||
is, | ||
/** succeeds if a value of type S can be decoded to a value of type A */ | ||
validate, | ||
/** converts a value of type A to a value of type S */ | ||
serialize) { | ||
this.name = name; | ||
@@ -51,3 +59,5 @@ this.is = is; | ||
exports.identity = function (a) { return a; }; | ||
exports.getFunctionName = function (f) { return f.displayName || f.name || "<function" + f.length + ">"; }; | ||
exports.getFunctionName = function (f) { | ||
return f.displayName || f.name || "<function" + f.length + ">"; | ||
}; | ||
exports.getContextEntry = function (key, type) { return ({ key: key, type: type }); }; | ||
@@ -470,3 +480,3 @@ exports.getValidationError = function (value, context) { return ({ value: value, context: context }); }; | ||
for (var k in a) { | ||
s[domain.serialize(k)] = codomain.serialize(a[k]); | ||
s[String(domain.serialize(k))] = codomain.serialize(a[k]); | ||
} | ||
@@ -599,5 +609,3 @@ return s; | ||
}); | ||
}, types.every(function (type) { return type.serialize === exports.identity; }) | ||
? exports.identity | ||
: function (a) { return types.map(function (type, i) { return type.serialize(a[i]); }); }, types); | ||
}, types.every(function (type) { return type.serialize === exports.identity; }) ? exports.identity : function (a) { return types.map(function (type, i) { return type.serialize(a[i]); }); }, types); | ||
} | ||
@@ -604,0 +612,0 @@ exports.tuple = tuple; |
{ | ||
"name": "io-ts", | ||
"version": "0.9.4", | ||
"version": "0.9.5", | ||
"description": "TypeScript compatible runtime type system for IO validation", | ||
@@ -5,0 +5,0 @@ "files": ["lib"], |
# The idea | ||
A value of type `Type<S, A>` (called "runtime type") is the runtime representation of the static type `A`: | ||
A value of type `Type<S, A>` (called "runtime type") is the runtime representation of the static type `A`. | ||
```js | ||
Also a runtime type can | ||
* decode inputs (through `validate`) | ||
* encode outputs (through `serialize`) | ||
* be used as a custom type guard (through `is`) | ||
```ts | ||
export type mixed = object | number | string | boolean | symbol | undefined | null | ||
class Type<S, A> { | ||
@@ -10,6 +18,10 @@ readonly _A: A | ||
constructor( | ||
/** a unique name for this runtime type */ | ||
readonly name: string, | ||
readonly is: Is<A>, | ||
readonly validate: Validate<S, A>, | ||
readonly serialize: Serialize<S, A> | ||
/** a custom type guard */ | ||
readonly is: (v: mixed) => v is A, | ||
/** succeeds if a value of type S can be decoded to a value of type A */ | ||
readonly validate: (input: S, context: Context) => Either<Errors, A>, | ||
/** converts a value of type A to a value of type S */ | ||
readonly serialize: (output: A) => S | ||
) {} | ||
@@ -19,21 +31,2 @@ } | ||
where `Validate<A>` is a specific validation function for the type `A` | ||
```js | ||
export interface ContextEntry { | ||
readonly key: string | ||
readonly type: Any | NeverType | ||
} | ||
export type Context = Array<ContextEntry> | ||
export interface ValidationError { | ||
readonly value: any | ||
readonly context: Context | ||
} | ||
export type Errors = Array<ValidationError> | ||
export type Validation<A> = Either<Errors, A> | ||
export type Is<A> = (v: any) => v is A | ||
export type Validate<S, A> = (s: S, context: Context) => Validation<A> | ||
export type Serialize<S, A> = (a: A) => S | ||
``` | ||
Note. The `Either` type is defined in [fp-ts](https://github.com/gcanti/fp-ts), a library containing implementations of | ||
@@ -49,3 +42,3 @@ common algebraic types in TypeScript. | ||
export class StringType extends Type<any, string> { | ||
export class StringType extends Type<mixed, string> { | ||
constructor() { | ||
@@ -179,5 +172,5 @@ super( | ||
| integer | ✘ | ✘ | `t.Integer` | | ||
| array of any | `Array<any>` | `Array<any>` | `t.Array` | | ||
| array of any | `Array<mixed>` | `Array<mixed>` | `t.Array` | | ||
| array of type | `Array<A>` | `Array<A>` | `t.array(A)` | | ||
| dictionary of any | `{ [key: string]: any }` | `{ [key: string]: any }` | `t.Dictionary` | | ||
| dictionary of any | `{ [key: string]: mixed }` | `{ [key: string]: mixed }` | `t.Dictionary` | | ||
| dictionary of type | `{ [K in A]: B }` | `{ [key: A]: B }` | `t.dictionary(A, B)` | | ||
@@ -274,3 +267,3 @@ | function | `Function` | `Function` | `t.Function` | | ||
// represents a Date from an ISO string | ||
const DateFromString = new t.Type<any, Date>( | ||
const DateFromString = new t.Type<t.mixed, Date>( | ||
'DateFromString', | ||
@@ -319,3 +312,3 @@ (v): v is Date => v instanceof Date, | ||
field: F | ||
): t.Type<any, t.TypeOf<U>[F]> => { | ||
): t.Type<t.mixed, t.TypeOf<U>[F]> => { | ||
return t.union(union.types.map(type => type.props[field])) | ||
@@ -339,3 +332,3 @@ } | ||
// ActionType: t.Type<any, "Action1" | "Action2"> | ||
// ActionType: t.Type<t.mixed, "Action1" | "Action2"> | ||
const ActionType = pluck(Action, 'type') | ||
@@ -348,3 +341,4 @@ ``` | ||
No, however you can define your own logic for that (if you _really_ trust the input) | ||
No, however you can define your own logic for that (if you _really_ trust the input and the involved types don't perform | ||
deserializations) | ||
@@ -351,0 +345,0 @@ ```ts |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
104658
986
385