diff options
| author | Philipp Tanlak <philipp.tanlak@gmail.com> | 2025-11-24 20:54:57 +0100 |
|---|---|---|
| committer | Philipp Tanlak <philipp.tanlak@gmail.com> | 2025-11-24 20:57:48 +0100 |
| commit | b1e2c8fd5cb5dfa46bc440a12eafaf56cd844b1c (patch) | |
| tree | 49d360fd6cbc6a2754efe93524ac47ff0fbe0f7d /node_modules/ts-interface-checker/dist | |
Docs
Diffstat (limited to 'node_modules/ts-interface-checker/dist')
| -rw-r--r-- | node_modules/ts-interface-checker/dist/index.d.ts | 124 | ||||
| -rw-r--r-- | node_modules/ts-interface-checker/dist/index.js | 224 | ||||
| -rw-r--r-- | node_modules/ts-interface-checker/dist/types.d.ts | 181 | ||||
| -rw-r--r-- | node_modules/ts-interface-checker/dist/types.js | 566 | ||||
| -rw-r--r-- | node_modules/ts-interface-checker/dist/util.d.ts | 55 | ||||
| -rw-r--r-- | node_modules/ts-interface-checker/dist/util.js | 130 |
6 files changed, 1280 insertions, 0 deletions
diff --git a/node_modules/ts-interface-checker/dist/index.d.ts b/node_modules/ts-interface-checker/dist/index.d.ts new file mode 100644 index 0000000..578e0c6 --- /dev/null +++ b/node_modules/ts-interface-checker/dist/index.d.ts @@ -0,0 +1,124 @@ +import { ITypeSuite, TType } from "./types"; +import { IErrorDetail } from "./util"; +/** + * Export functions used to define interfaces. + */ +export { TArray, TEnumType, TEnumLiteral, TFunc, TIface, TLiteral, TName, TOptional, TParam, TParamList, TProp, TTuple, TType, TUnion, TIntersection, array, enumlit, enumtype, func, iface, lit, name, opt, param, tuple, union, intersection, BasicType, ITypeSuite, } from "./types"; +export { VError, IErrorDetail } from './util'; +export interface ICheckerSuite { + [name: string]: Checker; +} +/** + * Takes one of more type suites (e.g. a module generated by `ts-interface-builder`), and combines + * them into a suite of interface checkers. If a type is used by name, that name should be present + * among the passed-in type suites. + * + * The returned object maps type names to Checker objects. + */ +export declare function createCheckers(...typeSuite: ITypeSuite[]): ICheckerSuite; +/** + * Checker implements validation of objects, and also includes accessors to validate method calls. + * Checkers should be created using `createCheckers()`. + */ +export declare class Checker { + private suite; + private ttype; + private _path; + private props; + private checkerPlain; + private checkerStrict; + constructor(suite: ITypeSuite, ttype: TType, _path?: string); + /** + * Set the path to report in errors, instead of the default "value". (E.g. if the Checker is for + * a "person" interface, set path to "person" to report e.g. "person.name is not a string".) + */ + setReportedPath(path: string): void; + /** + * Check that the given value satisfies this checker's type, or throw Error. + */ + check(value: any): void; + /** + * A fast check for whether or not the given value satisfies this Checker's type. This returns + * true or false, does not produce an error message, and is fast both on success and on failure. + */ + test(value: any): boolean; + /** + * Returns an error object describing the errors if the given value does not satisfy this + * Checker's type, or null if it does. + */ + validate(value: any): IErrorDetail | null; + /** + * Check that the given value satisfies this checker's type strictly. This checks that objects + * and tuples have no extra members. Note that this prevents backward compatibility, so usually + * a plain check() is more appropriate. + */ + strictCheck(value: any): void; + /** + * A fast strict check for whether or not the given value satisfies this Checker's type. Returns + * true or false, does not produce an error message, and is fast both on success and on failure. + */ + strictTest(value: any): boolean; + /** + * Returns an error object describing the errors if the given value does not satisfy this + * Checker's type strictly, or null if it does. + */ + strictValidate(value: any): IErrorDetail | null; + /** + * If this checker is for an interface, returns a Checker for the type required for the given + * property of this interface. + */ + getProp(prop: string): Checker; + /** + * If this checker is for an interface, returns a Checker for the argument-list required to call + * the given method of this interface. E.g. if this Checker is for the interface: + * interface Foo { + * find(s: string, pos?: number): number; + * } + * Then methodArgs("find").check(...) will succeed for ["foo"] and ["foo", 3], but not for [17]. + */ + methodArgs(methodName: string): Checker; + /** + * If this checker is for an interface, returns a Checker for the return value of the given + * method of this interface. + */ + methodResult(methodName: string): Checker; + /** + * If this checker is for a function, returns a Checker for its argument-list. + */ + getArgs(): Checker; + /** + * If this checker is for a function, returns a Checker for its result. + */ + getResult(): Checker; + /** + * Return the type for which this is a checker. + */ + getType(): TType; + /** + * Actual implementation of check() and strictCheck(). + */ + private _doCheck; + private _doValidate; + private _getMethod; +} +/** + * Typed checker interface. Adds type guard functionality to a normal `Checker`. + * + * To use, cast a `Checker` to a `CheckerT<>` using the appropriate type. + * + * eg. + * import { MyInterface } from './my-interface'; + * import MyInterfaceTi from './my-interface-ti'; + * + * const checkers = createCheckers(MyInterfaceTi) as { + * MyInterface: CheckerT<MyInterface> + * }; + * + * TODO: + * - Enable `check()` and `strictCheck()` type assertion definitions once the functionality + * is correctly working in TypeScript. (https://github.com/microsoft/TypeScript/issues/36931) + */ +export interface CheckerT<T> extends Checker { + test(value: any): value is T; + strictTest(value: any): value is T; +} diff --git a/node_modules/ts-interface-checker/dist/index.js b/node_modules/ts-interface-checker/dist/index.js new file mode 100644 index 0000000..d321bd8 --- /dev/null +++ b/node_modules/ts-interface-checker/dist/index.js @@ -0,0 +1,224 @@ +"use strict"; +var __spreadArrays = (this && this.__spreadArrays) || function () { + for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length; + for (var r = Array(s), k = 0, i = 0; i < il; i++) + for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++) + r[k] = a[j]; + return r; +}; +Object.defineProperty(exports, "__esModule", { value: true }); +exports.Checker = exports.createCheckers = void 0; +var types_1 = require("./types"); +var util_1 = require("./util"); +/** + * Export functions used to define interfaces. + */ +var types_2 = require("./types"); +Object.defineProperty(exports, "TArray", { enumerable: true, get: function () { return types_2.TArray; } }); +Object.defineProperty(exports, "TEnumType", { enumerable: true, get: function () { return types_2.TEnumType; } }); +Object.defineProperty(exports, "TEnumLiteral", { enumerable: true, get: function () { return types_2.TEnumLiteral; } }); +Object.defineProperty(exports, "TFunc", { enumerable: true, get: function () { return types_2.TFunc; } }); +Object.defineProperty(exports, "TIface", { enumerable: true, get: function () { return types_2.TIface; } }); +Object.defineProperty(exports, "TLiteral", { enumerable: true, get: function () { return types_2.TLiteral; } }); +Object.defineProperty(exports, "TName", { enumerable: true, get: function () { return types_2.TName; } }); +Object.defineProperty(exports, "TOptional", { enumerable: true, get: function () { return types_2.TOptional; } }); +Object.defineProperty(exports, "TParam", { enumerable: true, get: function () { return types_2.TParam; } }); +Object.defineProperty(exports, "TParamList", { enumerable: true, get: function () { return types_2.TParamList; } }); +Object.defineProperty(exports, "TProp", { enumerable: true, get: function () { return types_2.TProp; } }); +Object.defineProperty(exports, "TTuple", { enumerable: true, get: function () { return types_2.TTuple; } }); +Object.defineProperty(exports, "TType", { enumerable: true, get: function () { return types_2.TType; } }); +Object.defineProperty(exports, "TUnion", { enumerable: true, get: function () { return types_2.TUnion; } }); +Object.defineProperty(exports, "TIntersection", { enumerable: true, get: function () { return types_2.TIntersection; } }); +Object.defineProperty(exports, "array", { enumerable: true, get: function () { return types_2.array; } }); +Object.defineProperty(exports, "enumlit", { enumerable: true, get: function () { return types_2.enumlit; } }); +Object.defineProperty(exports, "enumtype", { enumerable: true, get: function () { return types_2.enumtype; } }); +Object.defineProperty(exports, "func", { enumerable: true, get: function () { return types_2.func; } }); +Object.defineProperty(exports, "iface", { enumerable: true, get: function () { return types_2.iface; } }); +Object.defineProperty(exports, "lit", { enumerable: true, get: function () { return types_2.lit; } }); +Object.defineProperty(exports, "name", { enumerable: true, get: function () { return types_2.name; } }); +Object.defineProperty(exports, "opt", { enumerable: true, get: function () { return types_2.opt; } }); +Object.defineProperty(exports, "param", { enumerable: true, get: function () { return types_2.param; } }); +Object.defineProperty(exports, "tuple", { enumerable: true, get: function () { return types_2.tuple; } }); +Object.defineProperty(exports, "union", { enumerable: true, get: function () { return types_2.union; } }); +Object.defineProperty(exports, "intersection", { enumerable: true, get: function () { return types_2.intersection; } }); +Object.defineProperty(exports, "BasicType", { enumerable: true, get: function () { return types_2.BasicType; } }); +var util_2 = require("./util"); +Object.defineProperty(exports, "VError", { enumerable: true, get: function () { return util_2.VError; } }); +/** + * Takes one of more type suites (e.g. a module generated by `ts-interface-builder`), and combines + * them into a suite of interface checkers. If a type is used by name, that name should be present + * among the passed-in type suites. + * + * The returned object maps type names to Checker objects. + */ +function createCheckers() { + var typeSuite = []; + for (var _i = 0; _i < arguments.length; _i++) { + typeSuite[_i] = arguments[_i]; + } + var fullSuite = Object.assign.apply(Object, __spreadArrays([{}, types_1.basicTypes], typeSuite)); + var checkers = {}; + for (var _a = 0, typeSuite_1 = typeSuite; _a < typeSuite_1.length; _a++) { + var suite_1 = typeSuite_1[_a]; + for (var _b = 0, _c = Object.keys(suite_1); _b < _c.length; _b++) { + var name = _c[_b]; + checkers[name] = new Checker(fullSuite, suite_1[name]); + } + } + return checkers; +} +exports.createCheckers = createCheckers; +/** + * Checker implements validation of objects, and also includes accessors to validate method calls. + * Checkers should be created using `createCheckers()`. + */ +var Checker = /** @class */ (function () { + // Create checkers by using `createCheckers()` function. + function Checker(suite, ttype, _path) { + if (_path === void 0) { _path = 'value'; } + this.suite = suite; + this.ttype = ttype; + this._path = _path; + this.props = new Map(); + if (ttype instanceof types_1.TIface) { + for (var _i = 0, _a = ttype.props; _i < _a.length; _i++) { + var p = _a[_i]; + this.props.set(p.name, p.ttype); + } + } + this.checkerPlain = this.ttype.getChecker(suite, false); + this.checkerStrict = this.ttype.getChecker(suite, true); + } + /** + * Set the path to report in errors, instead of the default "value". (E.g. if the Checker is for + * a "person" interface, set path to "person" to report e.g. "person.name is not a string".) + */ + Checker.prototype.setReportedPath = function (path) { + this._path = path; + }; + /** + * Check that the given value satisfies this checker's type, or throw Error. + */ + Checker.prototype.check = function (value) { return this._doCheck(this.checkerPlain, value); }; + /** + * A fast check for whether or not the given value satisfies this Checker's type. This returns + * true or false, does not produce an error message, and is fast both on success and on failure. + */ + Checker.prototype.test = function (value) { + return this.checkerPlain(value, new util_1.NoopContext()); + }; + /** + * Returns an error object describing the errors if the given value does not satisfy this + * Checker's type, or null if it does. + */ + Checker.prototype.validate = function (value) { + return this._doValidate(this.checkerPlain, value); + }; + /** + * Check that the given value satisfies this checker's type strictly. This checks that objects + * and tuples have no extra members. Note that this prevents backward compatibility, so usually + * a plain check() is more appropriate. + */ + Checker.prototype.strictCheck = function (value) { return this._doCheck(this.checkerStrict, value); }; + /** + * A fast strict check for whether or not the given value satisfies this Checker's type. Returns + * true or false, does not produce an error message, and is fast both on success and on failure. + */ + Checker.prototype.strictTest = function (value) { + return this.checkerStrict(value, new util_1.NoopContext()); + }; + /** + * Returns an error object describing the errors if the given value does not satisfy this + * Checker's type strictly, or null if it does. + */ + Checker.prototype.strictValidate = function (value) { + return this._doValidate(this.checkerStrict, value); + }; + /** + * If this checker is for an interface, returns a Checker for the type required for the given + * property of this interface. + */ + Checker.prototype.getProp = function (prop) { + var ttype = this.props.get(prop); + if (!ttype) { + throw new Error("Type has no property " + prop); + } + return new Checker(this.suite, ttype, this._path + "." + prop); + }; + /** + * If this checker is for an interface, returns a Checker for the argument-list required to call + * the given method of this interface. E.g. if this Checker is for the interface: + * interface Foo { + * find(s: string, pos?: number): number; + * } + * Then methodArgs("find").check(...) will succeed for ["foo"] and ["foo", 3], but not for [17]. + */ + Checker.prototype.methodArgs = function (methodName) { + var tfunc = this._getMethod(methodName); + return new Checker(this.suite, tfunc.paramList); + }; + /** + * If this checker is for an interface, returns a Checker for the return value of the given + * method of this interface. + */ + Checker.prototype.methodResult = function (methodName) { + var tfunc = this._getMethod(methodName); + return new Checker(this.suite, tfunc.result); + }; + /** + * If this checker is for a function, returns a Checker for its argument-list. + */ + Checker.prototype.getArgs = function () { + if (!(this.ttype instanceof types_1.TFunc)) { + throw new Error("getArgs() applied to non-function"); + } + return new Checker(this.suite, this.ttype.paramList); + }; + /** + * If this checker is for a function, returns a Checker for its result. + */ + Checker.prototype.getResult = function () { + if (!(this.ttype instanceof types_1.TFunc)) { + throw new Error("getResult() applied to non-function"); + } + return new Checker(this.suite, this.ttype.result); + }; + /** + * Return the type for which this is a checker. + */ + Checker.prototype.getType = function () { + return this.ttype; + }; + /** + * Actual implementation of check() and strictCheck(). + */ + Checker.prototype._doCheck = function (checkerFunc, value) { + var noopCtx = new util_1.NoopContext(); + if (!checkerFunc(value, noopCtx)) { + var detailCtx = new util_1.DetailContext(); + checkerFunc(value, detailCtx); + throw detailCtx.getError(this._path); + } + }; + Checker.prototype._doValidate = function (checkerFunc, value) { + var noopCtx = new util_1.NoopContext(); + if (checkerFunc(value, noopCtx)) { + return null; + } + var detailCtx = new util_1.DetailContext(); + checkerFunc(value, detailCtx); + return detailCtx.getErrorDetail(this._path); + }; + Checker.prototype._getMethod = function (methodName) { + var ttype = this.props.get(methodName); + if (!ttype) { + throw new Error("Type has no property " + methodName); + } + if (!(ttype instanceof types_1.TFunc)) { + throw new Error("Property " + methodName + " is not a method"); + } + return ttype; + }; + return Checker; +}()); +exports.Checker = Checker; diff --git a/node_modules/ts-interface-checker/dist/types.d.ts b/node_modules/ts-interface-checker/dist/types.d.ts new file mode 100644 index 0000000..8c0cc6b --- /dev/null +++ b/node_modules/ts-interface-checker/dist/types.d.ts @@ -0,0 +1,181 @@ +/** + * This module defines nodes used to define types and validations for objects and interfaces. + */ +import { IContext } from "./util"; +export declare type CheckerFunc = (value: any, ctx: IContext) => boolean; +/** Node that represents a type. */ +export declare abstract class TType { + abstract getChecker(suite: ITypeSuite, strict: boolean, allowedProps?: Set<string>): CheckerFunc; +} +/** + * Descriptor from which TType may be build (by parseSpec()). A plain string is equivalent to + * name(string). + */ +export declare type TypeSpec = TType | string; +/** + * Represents a suite of named types. Suites are used to resolve type names. + */ +export interface ITypeSuite { + [name: string]: TType; +} +/** + * Defines a type name, either built-in, or defined in this suite. It can typically be included in + * the specs as just a plain string. + */ +export declare function name(value: string): TName; +export declare class TName extends TType { + name: string; + private _failMsg; + constructor(name: string); + getChecker(suite: ITypeSuite, strict: boolean, allowedProps?: Set<string>): CheckerFunc; +} +/** + * Defines a literal value, e.g. lit('hello') or lit(123). + */ +export declare function lit(value: any): TLiteral; +export declare class TLiteral extends TType { + value: any; + name: string; + private _failMsg; + constructor(value: any); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines an array type, e.g. array('number'). + */ +export declare function array(typeSpec: TypeSpec): TArray; +export declare class TArray extends TType { + ttype: TType; + constructor(ttype: TType); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines a tuple type, e.g. tuple('string', 'number'). + */ +export declare function tuple(...typeSpec: TypeSpec[]): TTuple; +export declare class TTuple extends TType { + ttypes: TType[]; + constructor(ttypes: TType[]); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines a union type, e.g. union('number', 'null'). + */ +export declare function union(...typeSpec: TypeSpec[]): TUnion; +export declare class TUnion extends TType { + ttypes: TType[]; + private _failMsg; + constructor(ttypes: TType[]); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines an intersection type, e.g. intersection('number', 'null'). + */ +export declare function intersection(...typeSpec: TypeSpec[]): TIntersection; +export declare class TIntersection extends TType { + ttypes: TType[]; + constructor(ttypes: TType[]); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines an enum type, e.g. enum({'A': 1, 'B': 2}). + */ +export declare function enumtype(values: { + [name: string]: string | number; +}): TEnumType; +export declare class TEnumType extends TType { + members: { + [name: string]: string | number; + }; + readonly validValues: Set<string | number>; + private _failMsg; + constructor(members: { + [name: string]: string | number; + }); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines a literal enum value, such as Direction.Up, specified as enumlit("Direction", "Up"). + */ +export declare function enumlit(name: string, prop: string): TEnumLiteral; +export declare class TEnumLiteral extends TType { + enumName: string; + prop: string; + private _failMsg; + constructor(enumName: string, prop: string); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines an interface. The first argument is an array of interfaces that it extends, and the + * second is an array of properties. + */ +export declare function iface(bases: string[], props: { + [name: string]: TOptional | TypeSpec; +}): TIface; +export declare class TIface extends TType { + bases: string[]; + props: TProp[]; + private propSet; + constructor(bases: string[], props: TProp[]); + getChecker(suite: ITypeSuite, strict: boolean, allowedProps?: Set<string>): CheckerFunc; +} +/** + * Defines an optional property on an interface. + */ +export declare function opt(typeSpec: TypeSpec): TOptional; +export declare class TOptional extends TType { + ttype: TType; + constructor(ttype: TType); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines a property in an interface. + */ +export declare class TProp { + name: string; + ttype: TType; + isOpt: boolean; + constructor(name: string, ttype: TType, isOpt: boolean); +} +/** + * Defines a function. The first argument declares the function's return type, the rest declare + * its parameters. + */ +export declare function func(resultSpec: TypeSpec, ...params: TParam[]): TFunc; +export declare class TFunc extends TType { + paramList: TParamList; + result: TType; + constructor(paramList: TParamList, result: TType); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines a function parameter. + */ +export declare function param(name: string, typeSpec: TypeSpec, isOpt?: boolean): TParam; +export declare class TParam { + name: string; + ttype: TType; + isOpt: boolean; + constructor(name: string, ttype: TType, isOpt: boolean); +} +/** + * Defines a function parameter list. + */ +export declare class TParamList extends TType { + params: TParam[]; + constructor(params: TParam[]); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Single TType implementation for all basic built-in types. + */ +export declare class BasicType extends TType { + validator: (value: any) => boolean; + private message; + constructor(validator: (value: any) => boolean, message: string); + getChecker(suite: ITypeSuite, strict: boolean): CheckerFunc; +} +/** + * Defines the suite of basic types. + */ +export declare const basicTypes: ITypeSuite; diff --git a/node_modules/ts-interface-checker/dist/types.js b/node_modules/ts-interface-checker/dist/types.js new file mode 100644 index 0000000..0a8742f --- /dev/null +++ b/node_modules/ts-interface-checker/dist/types.js @@ -0,0 +1,566 @@ +"use strict"; +/** + * This module defines nodes used to define types and validations for objects and interfaces. + */ +// tslint:disable:no-shadowed-variable prefer-for-of +var __extends = (this && this.__extends) || (function () { + var extendStatics = function (d, b) { + extendStatics = Object.setPrototypeOf || + ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) || + function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; }; + return extendStatics(d, b); + }; + return function (d, b) { + extendStatics(d, b); + function __() { this.constructor = d; } + d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __()); + }; +})(); +Object.defineProperty(exports, "__esModule", { value: true }); +exports.basicTypes = exports.BasicType = exports.TParamList = exports.TParam = exports.param = exports.TFunc = exports.func = exports.TProp = exports.TOptional = exports.opt = exports.TIface = exports.iface = exports.TEnumLiteral = exports.enumlit = exports.TEnumType = exports.enumtype = exports.TIntersection = exports.intersection = exports.TUnion = exports.union = exports.TTuple = exports.tuple = exports.TArray = exports.array = exports.TLiteral = exports.lit = exports.TName = exports.name = exports.TType = void 0; +var util_1 = require("./util"); +/** Node that represents a type. */ +var TType = /** @class */ (function () { + function TType() { + } + return TType; +}()); +exports.TType = TType; +/** Parses a type spec into a TType node. */ +function parseSpec(typeSpec) { + return typeof typeSpec === "string" ? name(typeSpec) : typeSpec; +} +function getNamedType(suite, name) { + var ttype = suite[name]; + if (!ttype) { + throw new Error("Unknown type " + name); + } + return ttype; +} +/** + * Defines a type name, either built-in, or defined in this suite. It can typically be included in + * the specs as just a plain string. + */ +function name(value) { return new TName(value); } +exports.name = name; +var TName = /** @class */ (function (_super) { + __extends(TName, _super); + function TName(name) { + var _this = _super.call(this) || this; + _this.name = name; + _this._failMsg = "is not a " + name; + return _this; + } + TName.prototype.getChecker = function (suite, strict, allowedProps) { + var _this = this; + var ttype = getNamedType(suite, this.name); + var checker = ttype.getChecker(suite, strict, allowedProps); + if (ttype instanceof BasicType || ttype instanceof TName) { + return checker; + } + // For complex types, add an additional "is not a <Type>" message on failure. + return function (value, ctx) { return checker(value, ctx) ? true : ctx.fail(null, _this._failMsg, 0); }; + }; + return TName; +}(TType)); +exports.TName = TName; +/** + * Defines a literal value, e.g. lit('hello') or lit(123). + */ +function lit(value) { return new TLiteral(value); } +exports.lit = lit; +var TLiteral = /** @class */ (function (_super) { + __extends(TLiteral, _super); + function TLiteral(value) { + var _this = _super.call(this) || this; + _this.value = value; + _this.name = JSON.stringify(value); + _this._failMsg = "is not " + _this.name; + return _this; + } + TLiteral.prototype.getChecker = function (suite, strict) { + var _this = this; + return function (value, ctx) { return (value === _this.value) ? true : ctx.fail(null, _this._failMsg, -1); }; + }; + return TLiteral; +}(TType)); +exports.TLiteral = TLiteral; +/** + * Defines an array type, e.g. array('number'). + */ +function array(typeSpec) { return new TArray(parseSpec(typeSpec)); } +exports.array = array; +var TArray = /** @class */ (function (_super) { + __extends(TArray, _super); + function TArray(ttype) { + var _this = _super.call(this) || this; + _this.ttype = ttype; + return _this; + } + TArray.prototype.getChecker = function (suite, strict) { + var itemChecker = this.ttype.getChecker(suite, strict); + return function (value, ctx) { + if (!Array.isArray(value)) { + return ctx.fail(null, "is not an array", 0); + } + for (var i = 0; i < value.length; i++) { + var ok = itemChecker(value[i], ctx); + if (!ok) { + return ctx.fail(i, null, 1); + } + } + return true; + }; + }; + return TArray; +}(TType)); +exports.TArray = TArray; +/** + * Defines a tuple type, e.g. tuple('string', 'number'). + */ +function tuple() { + var typeSpec = []; + for (var _i = 0; _i < arguments.length; _i++) { + typeSpec[_i] = arguments[_i]; + } + return new TTuple(typeSpec.map(function (t) { return parseSpec(t); })); +} +exports.tuple = tuple; +var TTuple = /** @class */ (function (_super) { + __extends(TTuple, _super); + function TTuple(ttypes) { + var _this = _super.call(this) || this; + _this.ttypes = ttypes; + return _this; + } + TTuple.prototype.getChecker = function (suite, strict) { + var itemCheckers = this.ttypes.map(function (t) { return t.getChecker(suite, strict); }); + var checker = function (value, ctx) { + if (!Array.isArray(value)) { + return ctx.fail(null, "is not an array", 0); + } + for (var i = 0; i < itemCheckers.length; i++) { + var ok = itemCheckers[i](value[i], ctx); + if (!ok) { + return ctx.fail(i, null, 1); + } + } + return true; + }; + if (!strict) { + return checker; + } + return function (value, ctx) { + if (!checker(value, ctx)) { + return false; + } + return value.length <= itemCheckers.length ? true : + ctx.fail(itemCheckers.length, "is extraneous", 2); + }; + }; + return TTuple; +}(TType)); +exports.TTuple = TTuple; +/** + * Defines a union type, e.g. union('number', 'null'). + */ +function union() { + var typeSpec = []; + for (var _i = 0; _i < arguments.length; _i++) { + typeSpec[_i] = arguments[_i]; + } + return new TUnion(typeSpec.map(function (t) { return parseSpec(t); })); +} +exports.union = union; +var TUnion = /** @class */ (function (_super) { + __extends(TUnion, _super); + function TUnion(ttypes) { + var _this = _super.call(this) || this; + _this.ttypes = ttypes; + var names = ttypes.map(function (t) { return t instanceof TName || t instanceof TLiteral ? t.name : null; }) + .filter(function (n) { return n; }); + var otherTypes = ttypes.length - names.length; + if (names.length) { + if (otherTypes > 0) { + names.push(otherTypes + " more"); + } + _this._failMsg = "is none of " + names.join(", "); + } + else { + _this._failMsg = "is none of " + otherTypes + " types"; + } + return _this; + } + TUnion.prototype.getChecker = function (suite, strict) { + var _this = this; + var itemCheckers = this.ttypes.map(function (t) { return t.getChecker(suite, strict); }); + return function (value, ctx) { + var ur = ctx.unionResolver(); + for (var i = 0; i < itemCheckers.length; i++) { + var ok = itemCheckers[i](value, ur.createContext()); + if (ok) { + return true; + } + } + ctx.resolveUnion(ur); + return ctx.fail(null, _this._failMsg, 0); + }; + }; + return TUnion; +}(TType)); +exports.TUnion = TUnion; +/** + * Defines an intersection type, e.g. intersection('number', 'null'). + */ +function intersection() { + var typeSpec = []; + for (var _i = 0; _i < arguments.length; _i++) { + typeSpec[_i] = arguments[_i]; + } + return new TIntersection(typeSpec.map(function (t) { return parseSpec(t); })); +} +exports.intersection = intersection; +var TIntersection = /** @class */ (function (_super) { + __extends(TIntersection, _super); + function TIntersection(ttypes) { + var _this = _super.call(this) || this; + _this.ttypes = ttypes; + return _this; + } + TIntersection.prototype.getChecker = function (suite, strict) { + var allowedProps = new Set(); + var itemCheckers = this.ttypes.map(function (t) { return t.getChecker(suite, strict, allowedProps); }); + return function (value, ctx) { + var ok = itemCheckers.every(function (checker) { return checker(value, ctx); }); + if (ok) { + return true; + } + return ctx.fail(null, null, 0); + }; + }; + return TIntersection; +}(TType)); +exports.TIntersection = TIntersection; +/** + * Defines an enum type, e.g. enum({'A': 1, 'B': 2}). + */ +function enumtype(values) { + return new TEnumType(values); +} +exports.enumtype = enumtype; +var TEnumType = /** @class */ (function (_super) { + __extends(TEnumType, _super); + function TEnumType(members) { + var _this = _super.call(this) || this; + _this.members = members; + _this.validValues = new Set(); + _this._failMsg = "is not a valid enum value"; + _this.validValues = new Set(Object.keys(members).map(function (name) { return members[name]; })); + return _this; + } + TEnumType.prototype.getChecker = function (suite, strict) { + var _this = this; + return function (value, ctx) { + return (_this.validValues.has(value) ? true : ctx.fail(null, _this._failMsg, 0)); + }; + }; + return TEnumType; +}(TType)); +exports.TEnumType = TEnumType; +/** + * Defines a literal enum value, such as Direction.Up, specified as enumlit("Direction", "Up"). + */ +function enumlit(name, prop) { + return new TEnumLiteral(name, prop); +} +exports.enumlit = enumlit; +var TEnumLiteral = /** @class */ (function (_super) { + __extends(TEnumLiteral, _super); + function TEnumLiteral(enumName, prop) { + var _this = _super.call(this) || this; + _this.enumName = enumName; + _this.prop = prop; + _this._failMsg = "is not " + enumName + "." + prop; + return _this; + } + TEnumLiteral.prototype.getChecker = function (suite, strict) { + var _this = this; + var ttype = getNamedType(suite, this.enumName); + if (!(ttype instanceof TEnumType)) { + throw new Error("Type " + this.enumName + " used in enumlit is not an enum type"); + } + var val = ttype.members[this.prop]; + if (!ttype.members.hasOwnProperty(this.prop)) { + throw new Error("Unknown value " + this.enumName + "." + this.prop + " used in enumlit"); + } + return function (value, ctx) { return (value === val) ? true : ctx.fail(null, _this._failMsg, -1); }; + }; + return TEnumLiteral; +}(TType)); +exports.TEnumLiteral = TEnumLiteral; +function makeIfaceProps(props) { + return Object.keys(props).map(function (name) { return makeIfaceProp(name, props[name]); }); +} +function makeIfaceProp(name, prop) { + return prop instanceof TOptional ? + new TProp(name, prop.ttype, true) : + new TProp(name, parseSpec(prop), false); +} +/** + * Defines an interface. The first argument is an array of interfaces that it extends, and the + * second is an array of properties. + */ +function iface(bases, props) { + return new TIface(bases, makeIfaceProps(props)); +} +exports.iface = iface; +var TIface = /** @class */ (function (_super) { + __extends(TIface, _super); + function TIface(bases, props) { + var _this = _super.call(this) || this; + _this.bases = bases; + _this.props = props; + _this.propSet = new Set(props.map(function (p) { return p.name; })); + return _this; + } + TIface.prototype.getChecker = function (suite, strict, allowedProps) { + var _this = this; + var baseCheckers = this.bases.map(function (b) { return getNamedType(suite, b).getChecker(suite, strict); }); + var propCheckers = this.props.map(function (prop) { return prop.ttype.getChecker(suite, strict); }); + var testCtx = new util_1.NoopContext(); + // Consider a prop required if it's not optional AND does not allow for undefined as a value. + var isPropRequired = this.props.map(function (prop, i) { + return !prop.isOpt && !propCheckers[i](undefined, testCtx); + }); + var checker = function (value, ctx) { + if (typeof value !== "object" || value === null) { + return ctx.fail(null, "is not an object", 0); + } + for (var i = 0; i < baseCheckers.length; i++) { + if (!baseCheckers[i](value, ctx)) { + return false; + } + } + for (var i = 0; i < propCheckers.length; i++) { + var name_1 = _this.props[i].name; + var v = value[name_1]; + if (v === undefined) { + if (isPropRequired[i]) { + return ctx.fail(name_1, "is missing", 1); + } + } + else { + var ok = propCheckers[i](v, ctx); + if (!ok) { + return ctx.fail(name_1, null, 1); + } + } + } + return true; + }; + if (!strict) { + return checker; + } + var propSet = this.propSet; + if (allowedProps) { + this.propSet.forEach(function (prop) { return allowedProps.add(prop); }); + propSet = allowedProps; + } + // In strict mode, check also for unknown enumerable properties. + return function (value, ctx) { + if (!checker(value, ctx)) { + return false; + } + for (var prop in value) { + if (!propSet.has(prop)) { + return ctx.fail(prop, "is extraneous", 2); + } + } + return true; + }; + }; + return TIface; +}(TType)); +exports.TIface = TIface; +/** + * Defines an optional property on an interface. + */ +function opt(typeSpec) { return new TOptional(parseSpec(typeSpec)); } +exports.opt = opt; +var TOptional = /** @class */ (function (_super) { + __extends(TOptional, _super); + function TOptional(ttype) { + var _this = _super.call(this) || this; + _this.ttype = ttype; + return _this; + } + TOptional.prototype.getChecker = function (suite, strict) { + var itemChecker = this.ttype.getChecker(suite, strict); + return function (value, ctx) { + return value === undefined || itemChecker(value, ctx); + }; + }; + return TOptional; +}(TType)); +exports.TOptional = TOptional; +/** + * Defines a property in an interface. + */ +var TProp = /** @class */ (function () { + function TProp(name, ttype, isOpt) { + this.name = name; + this.ttype = ttype; + this.isOpt = isOpt; + } + return TProp; +}()); +exports.TProp = TProp; +/** + * Defines a function. The first argument declares the function's return type, the rest declare + * its parameters. + */ +function func(resultSpec) { + var params = []; + for (var _i = 1; _i < arguments.length; _i++) { + params[_i - 1] = arguments[_i]; + } + return new TFunc(new TParamList(params), parseSpec(resultSpec)); +} +exports.func = func; +var TFunc = /** @class */ (function (_super) { + __extends(TFunc, _super); + function TFunc(paramList, result) { + var _this = _super.call(this) || this; + _this.paramList = paramList; + _this.result = result; + return _this; + } + TFunc.prototype.getChecker = function (suite, strict) { + return function (value, ctx) { + return typeof value === "function" ? true : ctx.fail(null, "is not a function", 0); + }; + }; + return TFunc; +}(TType)); +exports.TFunc = TFunc; +/** + * Defines a function parameter. + */ +function param(name, typeSpec, isOpt) { + return new TParam(name, parseSpec(typeSpec), Boolean(isOpt)); +} +exports.param = param; +var TParam = /** @class */ (function () { + function TParam(name, ttype, isOpt) { + this.name = name; + this.ttype = ttype; + this.isOpt = isOpt; + } + return TParam; +}()); +exports.TParam = TParam; +/** + * Defines a function parameter list. + */ +var TParamList = /** @class */ (function (_super) { + __extends(TParamList, _super); + function TParamList(params) { + var _this = _super.call(this) || this; + _this.params = params; + return _this; + } + TParamList.prototype.getChecker = function (suite, strict) { + var _this = this; + var itemCheckers = this.params.map(function (t) { return t.ttype.getChecker(suite, strict); }); + var testCtx = new util_1.NoopContext(); + var isParamRequired = this.params.map(function (param, i) { + return !param.isOpt && !itemCheckers[i](undefined, testCtx); + }); + var checker = function (value, ctx) { + if (!Array.isArray(value)) { + return ctx.fail(null, "is not an array", 0); + } + for (var i = 0; i < itemCheckers.length; i++) { + var p = _this.params[i]; + if (value[i] === undefined) { + if (isParamRequired[i]) { + return ctx.fail(p.name, "is missing", 1); + } + } + else { + var ok = itemCheckers[i](value[i], ctx); + if (!ok) { + return ctx.fail(p.name, null, 1); + } + } + } + return true; + }; + if (!strict) { + return checker; + } + return function (value, ctx) { + if (!checker(value, ctx)) { + return false; + } + return value.length <= itemCheckers.length ? true : + ctx.fail(itemCheckers.length, "is extraneous", 2); + }; + }; + return TParamList; +}(TType)); +exports.TParamList = TParamList; +/** + * Single TType implementation for all basic built-in types. + */ +var BasicType = /** @class */ (function (_super) { + __extends(BasicType, _super); + function BasicType(validator, message) { + var _this = _super.call(this) || this; + _this.validator = validator; + _this.message = message; + return _this; + } + BasicType.prototype.getChecker = function (suite, strict) { + var _this = this; + return function (value, ctx) { return _this.validator(value) ? true : ctx.fail(null, _this.message, 0); }; + }; + return BasicType; +}(TType)); +exports.BasicType = BasicType; +/** + * Defines the suite of basic types. + */ +exports.basicTypes = { + any: new BasicType(function (v) { return true; }, "is invalid"), + number: new BasicType(function (v) { return (typeof v === "number"); }, "is not a number"), + object: new BasicType(function (v) { return (typeof v === "object" && v); }, "is not an object"), + boolean: new BasicType(function (v) { return (typeof v === "boolean"); }, "is not a boolean"), + string: new BasicType(function (v) { return (typeof v === "string"); }, "is not a string"), + symbol: new BasicType(function (v) { return (typeof v === "symbol"); }, "is not a symbol"), + void: new BasicType(function (v) { return (v == null); }, "is not void"), + undefined: new BasicType(function (v) { return (v === undefined); }, "is not undefined"), + null: new BasicType(function (v) { return (v === null); }, "is not null"), + never: new BasicType(function (v) { return false; }, "is unexpected"), + Date: new BasicType(getIsNativeChecker("[object Date]"), "is not a Date"), + RegExp: new BasicType(getIsNativeChecker("[object RegExp]"), "is not a RegExp"), +}; +// This approach for checking native object types mirrors that of lodash. Its advantage over +// `isinstance` is that it can still return true for native objects created in different JS +// execution environments. +var nativeToString = Object.prototype.toString; +function getIsNativeChecker(tag) { + return function (v) { return typeof v === "object" && v && nativeToString.call(v) === tag; }; +} +if (typeof Buffer !== "undefined") { + exports.basicTypes.Buffer = new BasicType(function (v) { return Buffer.isBuffer(v); }, "is not a Buffer"); +} +var _loop_1 = function (array_1) { + exports.basicTypes[array_1.name] = new BasicType(function (v) { return (v instanceof array_1); }, "is not a " + array_1.name); +}; +// Support typed arrays of various flavors +for (var _i = 0, _a = [Int8Array, Uint8Array, Uint8ClampedArray, Int16Array, Uint16Array, + Int32Array, Uint32Array, Float32Array, Float64Array, ArrayBuffer]; _i < _a.length; _i++) { + var array_1 = _a[_i]; + _loop_1(array_1); +} diff --git a/node_modules/ts-interface-checker/dist/util.d.ts b/node_modules/ts-interface-checker/dist/util.d.ts new file mode 100644 index 0000000..aeab0b4 --- /dev/null +++ b/node_modules/ts-interface-checker/dist/util.d.ts @@ -0,0 +1,55 @@ +/** + * Error thrown by validation. Besides an informative message, it includes the path to the + * property which triggered the failure. + */ +export declare class VError extends Error { + path: string; + constructor(path: string, message: string); +} +/** + * IContext is used during validation to collect error messages. There is a "noop" fast + * implementation that does not pay attention to messages, and a full implementation that does. + */ +export interface IContext { + fail(relPath: string | number | null, message: string | null, score: number): false; + unionResolver(): IUnionResolver; + resolveUnion(ur: IUnionResolver): void; +} +/** + * This helper class is used to collect error messages reported while validating unions. + */ +export interface IUnionResolver { + createContext(): IContext; +} +/** + * IErrorDetail describes errors as returned by the validate() and validateStrict() methods. + */ +export interface IErrorDetail { + path: string; + message: string; + nested?: IErrorDetail[]; +} +/** + * Fast implementation of IContext used for first-pass validation. If that fails, we can validate + * using DetailContext to collect error messages. That's faster for the common case when messages + * normally pass validation. + */ +export declare class NoopContext implements IContext, IUnionResolver { + fail(relPath: string | number | null, message: string | null, score: number): false; + unionResolver(): IUnionResolver; + createContext(): IContext; + resolveUnion(ur: IUnionResolver): void; +} +/** + * Complete implementation of IContext that collects meaningfull errors. + */ +export declare class DetailContext implements IContext { + private _propNames; + private _messages; + private _score; + fail(relPath: string | number | null, message: string | null, score: number): false; + unionResolver(): IUnionResolver; + resolveUnion(unionResolver: IUnionResolver): void; + getError(path: string): VError; + getErrorDetail(path: string): IErrorDetail | null; +} diff --git a/node_modules/ts-interface-checker/dist/util.js b/node_modules/ts-interface-checker/dist/util.js new file mode 100644 index 0000000..c27e88a --- /dev/null +++ b/node_modules/ts-interface-checker/dist/util.js @@ -0,0 +1,130 @@ +"use strict"; +var __extends = (this && this.__extends) || (function () { + var extendStatics = function (d, b) { + extendStatics = Object.setPrototypeOf || + ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) || + function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; }; + return extendStatics(d, b); + }; + return function (d, b) { + extendStatics(d, b); + function __() { this.constructor = d; } + d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __()); + }; +})(); +Object.defineProperty(exports, "__esModule", { value: true }); +exports.DetailContext = exports.NoopContext = exports.VError = void 0; +/** + * Error thrown by validation. Besides an informative message, it includes the path to the + * property which triggered the failure. + */ +var VError = /** @class */ (function (_super) { + __extends(VError, _super); + function VError(path, message) { + var _this = _super.call(this, message) || this; + _this.path = path; + // See https://github.com/Microsoft/TypeScript/wiki/Breaking-Changes#extending-built-ins-like-error-array-and-map-may-no-longer-work for info about this workaround. + Object.setPrototypeOf(_this, VError.prototype); + return _this; + } + return VError; +}(Error)); +exports.VError = VError; +/** + * Fast implementation of IContext used for first-pass validation. If that fails, we can validate + * using DetailContext to collect error messages. That's faster for the common case when messages + * normally pass validation. + */ +var NoopContext = /** @class */ (function () { + function NoopContext() { + } + NoopContext.prototype.fail = function (relPath, message, score) { + return false; + }; + NoopContext.prototype.unionResolver = function () { return this; }; + NoopContext.prototype.createContext = function () { return this; }; + NoopContext.prototype.resolveUnion = function (ur) { }; + return NoopContext; +}()); +exports.NoopContext = NoopContext; +/** + * Complete implementation of IContext that collects meaningfull errors. + */ +var DetailContext = /** @class */ (function () { + function DetailContext() { + // Stack of property names and associated messages for reporting helpful error messages. + this._propNames = [""]; + this._messages = [null]; + // Score is used to choose the best union member whose DetailContext to use for reporting. + // Higher score means better match (or rather less severe mismatch). + this._score = 0; + } + DetailContext.prototype.fail = function (relPath, message, score) { + this._propNames.push(relPath); + this._messages.push(message); + this._score += score; + return false; + }; + DetailContext.prototype.unionResolver = function () { + return new DetailUnionResolver(); + }; + DetailContext.prototype.resolveUnion = function (unionResolver) { + var _a, _b; + var u = unionResolver; + var best = null; + for (var _i = 0, _c = u.contexts; _i < _c.length; _i++) { + var ctx = _c[_i]; + if (!best || ctx._score >= best._score) { + best = ctx; + } + } + if (best && best._score > 0) { + (_a = this._propNames).push.apply(_a, best._propNames); + (_b = this._messages).push.apply(_b, best._messages); + } + }; + DetailContext.prototype.getError = function (path) { + var msgParts = []; + for (var i = this._propNames.length - 1; i >= 0; i--) { + var p = this._propNames[i]; + path += (typeof p === "number") ? "[" + p + "]" : (p ? "." + p : ""); + var m = this._messages[i]; + if (m) { + msgParts.push(path + " " + m); + } + } + return new VError(path, msgParts.join("; ")); + }; + DetailContext.prototype.getErrorDetail = function (path) { + var details = []; + for (var i = this._propNames.length - 1; i >= 0; i--) { + var p = this._propNames[i]; + path += (typeof p === "number") ? "[" + p + "]" : (p ? "." + p : ""); + var message = this._messages[i]; + if (message) { + details.push({ path: path, message: message }); + } + } + var detail = null; + for (var i = details.length - 1; i >= 0; i--) { + if (detail) { + details[i].nested = [detail]; + } + detail = details[i]; + } + return detail; + }; + return DetailContext; +}()); +exports.DetailContext = DetailContext; +var DetailUnionResolver = /** @class */ (function () { + function DetailUnionResolver() { + this.contexts = []; + } + DetailUnionResolver.prototype.createContext = function () { + var ctx = new DetailContext(); + this.contexts.push(ctx); + return ctx; + }; + return DetailUnionResolver; +}()); |