@illavv/run_typer - v4.1.0
    Preparing search index...

    Class Typer<TRegistry>

    Class representing a type checker. Version: 4.0.0

    4.0.0

    Type Parameters

    Index
    • get coerce(): Coercions

      Validators that convert before validating.

      Query strings, form data and environment variables arrive as strings, so without these every HTTP handler rewrites the conversion by hand — which is exactly where the mistakes are made. Each one rejects what it cannot convert rather than inventing a value, which is the difference between these and the bare Number() / Boolean() they replace:

      Input Number() / Boolean() typer.coerce.*
      '' 0 rejected
      ' ' 0 rejected
      null 0 rejected
      [] 0 rejected
      'abc' NaN rejected
      'false' true false
      '0' true false

      In a schema slot the converted value replaces the original, so the object that comes out of parse holds the numbers and dates, not the strings that arrived.

      Returns Coercions

      const query = typer.parse({
      page: typer.coerce.number,
      perPage: typer.coerce.number,
      archived: typer.coerce.boolean,
      since: typer.coerce.date,
      }, req.query);
      // { page: 2, perPage: 50, archived: false, since: Date }
    • get validators(): BoundValidators<Typer<TRegistry>>

      The standalone validators, pre-bound to this instance.

      The schema API invites passing validators around as values, but { id: typer.isPositiveInteger } loses this and fails with an opaque "Cannot read properties of undefined" — even for input that is valid. These are bound, so they can be passed, destructured and stored freely.

      Built on first access and cached. Binding all of them eagerly onto the instance was measured to slow every other method down several-fold, by pushing the object out of V8's fast property mode — hence the single lazily-populated slot.

      Returns BoundValidators<Typer<TRegistry>>

      const schema = typer.schema({
      id: typer.validators.isPositiveInteger,
      email: typer.validators.isEmail,
      });

      // Equivalent, with no accessor:
      const same = typer.schema({ id: (v) => typer.isPositiveInteger(v) });
    • Builds a validator for an array whose elements all satisfy element, optionally constraining the length.

      Every failing element is reported, not just the first.

      Type Parameters

      • T

        The element type

      Parameters

      • element: Validator<T>

        Validator applied to each element.

      • Optionalbounds: { max?: number; min?: number } = {}

        Inclusive length bounds.

      Returns Validator<T[]>

      A validator producing T[].

      If the value is not an array, is out of bounds, or has invalid elements.

      const tags = typer.arrayOf((v) => typer.asString(v), { min: 1 });
      tags(['a', 'b']); // string[]
    • Validates and returns an array

      Type Parameters

      • T = unknown

        The expected element type

      Parameters

      • value: unknown

        The value to validate

      Returns T[]

      The validated array

      If not an array

    • Validates and returns a boolean

      Parameters

      • value: unknown

        The value to validate

      Returns boolean

      The validated boolean

      If not a boolean

    • Validates and returns a number

      Parameters

      • value: unknown

        The value to validate

      Returns number

      The validated number

      If not a number

    • Validates and returns an object

      Type Parameters

      • T extends Record<string, unknown> = Record<string, unknown>

        The expected object type

      Parameters

      • value: unknown

        The value to validate

      Returns T

      The validated object

      If not an object

    • Assert that a value is of a specific type. Logs a warning if incorrect.

      Parameters

      • value: unknown

        The value to check.

      • expectedType: string | string[]

        The expected type(s).

      Returns void

      Typer.assert(42, "number"); // No output
      Typer.assert("hello", "number"); // Warning in console
    • Validates and returns a string

      Parameters

      • value: unknown

        The value to validate

      Returns string

      The validated string

      If not a string

    • Recursively validates an object against a nested schema.

      Shares the closure compiler with parse and safeParse, so a schema validated here is compiled once and reused — and reports the same messages the other entry points do.

      Parameters

      • schema: Record<string, unknown>

        The expected structure definition.

      • obj: Record<string, unknown>

        The object to validate.

      • path: string = ''

        The current path for error reporting (internal use).

      • strictMode: boolean = false

        Whether to reject extra keys not in schema.

      Returns StructureValidationReturn

      • Validation result with errors (strings) and issues (structured).
      const schema = {
      name: "string",
      age: "number",
      hobbies: ["string"],
      address: {
      street: "string",
      city: "string?"
      }
      };
      const obj = { name: "John", age: 25, hobbies: ["reading"] };
      console.log(Typer.checkStructure(schema, obj)); // { isValid: true, errors: [], issues: [] }
    • Builds a validator for a union whose members are told apart by a single key — the shape most API payloads use.

      union tries each variant in turn, so its cost grows with the number of variants and its error lists every variant's failure. This reads the discriminant once and goes straight to the one variant that can possibly match, in constant time, and reports against that variant alone.

      The variants are keyed by discriminant value, so the mapping is exact by construction — there is no literal to extract from a schema and no way to declare two variants with the same tag.

      Type Parameters

      • const Key extends string

        The discriminant key

      • const V extends Record<string, Record<string, unknown>>

        The variants, keyed by discriminant value

      Parameters

      • key: Key

        The key that tells the variants apart.

      • variants: V

        Schema per discriminant value.

      • Optionaloptions: { strict?: boolean } = {}

        strict rejects keys the selected variant does not declare.

      Returns StandardValidator<DiscriminatedUnion<Key, V, TRegistry>>

      A validator producing the union of the variants.

      If the discriminant is missing or unknown, or the selected variant fails.

      const shape = typer.discriminatedUnion('kind', {
      circle: { radius: 'number' },
      square: { side: 'number' },
      });
      shape({ kind: 'circle', radius: 2 });
      // → { kind: 'circle'; radius: number } | { kind: 'square'; side: number }
    • Expects a function to conform to specified input and output types.

      Parameters

      • funct: Function

        The function to type-check.

      • types: TyperExpectTypes

        The expected types for the function's parameters and return value.

        Defines the expected input and output types for a function.

        • paramTypes: string[]

          The expected type(s) of the function's parameters

        • returnType: string[]

          The expected return type(s) of the function

      Returns (...args: unknown[]) => any

      A new function that type-checks its arguments and return value.

      If the types object does not contain exactly 3 keys or the required type properties.

      If the function or types object does not conform to the expected types.

      const typedFunction = Typer.expect(
      (x: number) => x * 2,
      { paramTypes: ["number"], returnType: ["number"] }
      );
      console.log(typedFunction(3)); // 6
    • Exports all registered types as a JSON string.

      Returns string

      The serialized types.

      console.log(Typer.exportTypes()); // '["array","number","string","boolean"]'
      
    • Registers a custom type and tracks it in the instance's type, so the alias becomes usable in compile-time-checked schemas and resolves to R in Infer.

      This is the type-aware counterpart of registerType: same runtime behavior, but it returns a re-typed Typer instead of void. Chain the calls and keep the returned instance — it is the same object, only seen through a wider type.

      Type Parameters

      • N extends string

        The alias being registered

      • R

        The type the validator produces

      Parameters

      • name: N

        The alias to register.

      • validator: (value: unknown) => R

        Throws on invalid input, returns the value otherwise.

      • override: boolean = false

        Whether to replace an existing registration.

      Returns Typer<TRegistry & Record<N, R>>

      The same instance, typed with the new alias.

      If the alias is already registered and override is false.

      const typer = new Typer()
      .extend('positive', (v) => {
      if (typeof v !== 'number' || v <= 0) throw new TypeError('Must be positive');
      return v;
      });

      const schema = typer.schema({ qty: 'positive' }); // accepted
      type Order = Infer<typeof schema, { positive: number }>; // { qty: number }
      typer.schema({ qty: 'positiv' }); // compile error: unknown type alias
    • Imports types from a JSON string.

      Parameters

      • json: string

        The JSON string containing type names.

      Returns void

      Typer.importTypes('["customType"]');
      
    • Composable form of isInstanceOf.

      Type Parameters

      • T

        The instance type

      Parameters

      • ctor: new (...args: never[]) => T

        The constructor to check against.

      Returns Validator<T>

      A validator producing T.

      typer.parse({ when: typer.instanceOf(Date) }, payload);
      
    • Checks if the provided value matches one or more specified types.

      Overloads:

      • When called with a known built-in alias, the type guard is automatically inferred from TypeMap (e.g. "number" narrows to number).
      • For custom registered types, an explicit generic T may be supplied.

      Type Parameters

      Parameters

      • value: unknown

        The value to check.

      • types: K | readonly K[]

        One or more types to check against.

      Returns value is TypeMap[K]

      Returns true if the value matches any type, false otherwise.

      if (typer.is(value, "string")) {
      // value is now narrowed to string by the type guard
      console.log(value.toUpperCase());
      }
      typer.is(42, "number"); // true
      typer.is("hello", ["string", "number"]); // true
      typer.is<MyShape>(payload, "my_custom_type"); // explicit generic for custom types
    • Checks if the provided value matches one or more specified types.

      Overloads:

      • When called with a known built-in alias, the type guard is automatically inferred from TypeMap (e.g. "number" narrows to number).
      • For custom registered types, an explicit generic T may be supplied.

      Type Parameters

      • T = unknown

        The expected type for better TypeScript inference

      Parameters

      • value: unknown

        The value to check.

      • types: string | readonly string[]

        One or more types to check against.

      Returns value is T

      Returns true if the value matches any type, false otherwise.

      if (typer.is(value, "string")) {
      // value is now narrowed to string by the type guard
      console.log(value.toUpperCase());
      }
      typer.is(42, "number"); // true
      typer.is("hello", ["string", "number"]); // true
      typer.is<MyShape>(payload, "my_custom_type"); // explicit generic for custom types
    • Type-safe array validation

      Type Parameters

      • T = unknown

        The expected element type

      Parameters

      • value: unknown

        The value to check

      Returns value is T[]

      Type guard for array

    • Checks if the provided parameter is an array of a specified type.

      Type Parameters

      • T = unknown

        The expected element type

      Parameters

      • elementType: string

        The type of elements that the array should contain.

      • p: unknown

        The parameter to check.

      Returns T[]

      Typed array of elements

      Throws if the parameter is not an array of the specified type.

      const numbers = typer.isArrayOf<number>("number", [1, 2, 3]); // numbers: number[]
      const strings = typer.isArrayOf<string>("string", ["a", "b"]); // strings: string[]
    • Checks that the parameter is a syntactically valid Base64 string. Supports both standard and URL-safe variants. Padding is required when requirePadding is true (default).

      Parameters

      • p: unknown

        The parameter to check

      • Optionalopts: { requirePadding?: boolean; urlSafe?: boolean } = {}

        Options

      Returns string

      The validated Base64 string

      If p is not a valid Base64 string

    • Type-safe boolean validation

      Parameters

      • value: unknown

        The value to check

      Returns value is boolean

      Type guard for boolean

    • Checks if the provided parameter is a valid email address.

      Parameters

      • p: unknown

        The parameter to check.

      Returns string

      The validated email string

      Throws if the parameter is not a valid email address.

      const email = typer.isEmail("test@example.com"); // email: string
      
    • Checks that the parameter is "empty": empty string (after trim), empty array, empty Map/Set, or object with no own enumerable keys.

      Parameters

      • p: unknown

        The parameter to check

      Returns unknown

      The validated empty value

      If p is not empty or not a supported container

    • Checks that the parameter is a finite number (rejects NaN and Infinity). Stricter than isType("number", x), which accepts NaN for compatibility with typeof x === "number".

      Parameters

      • p: unknown

        The parameter to check

      Returns number

      The validated finite number

      If p is not a finite number

    • Checks that the parameter is a valid CSS hex color (#RGB, #RGBA, #RRGGBB, or #RRGGBBAA).

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated hex color

      If p is not a valid hex color

    • Checks if the provided parameter is a number within a specified range.

      Parameters

      • min: number

        The minimum value.

      • max: number

        The maximum value. The failing value is not in the error message: a numeric range is exactly what guards PINs, one-time codes and amounts, and the message is what ends up in application logs. It is on the issue's value field instead, for callers that want to show it.

      • p: unknown

        The parameter to check.

      Returns number

      The validated number

      Throws if the parameter is not a number within the specified range.

      const age = typer.isInRange(18, 65, 25); // age: number
      
    • Checks that the parameter is an instance of the given constructor. Type-safe alternative to writing value instanceof MyClass everywhere.

      Type Parameters

      • T

        The instance type produced by the constructor

      Parameters

      • ctor: new (...args: never[]) => T

        The constructor to check against

      • p: unknown

        The parameter to check

      Returns T

      The validated instance

      If p is not an instance of ctor

    • Checks if the provided parameter is an integer.

      Parameters

      • p: unknown

        The parameter to check.

      Returns number

      The validated integer

      Throws if the parameter is not an integer.

      const count = typer.isInteger(42); // count: number
      
    • Checks that the parameter is a valid IP address, of either version.

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated address

      If p is neither a valid IPv4 nor a valid IPv6 address

      typer.isIP('192.168.0.1');
      typer.isIP('::1');
    • Checks that the parameter is a valid IPv4 address (dotted-quad notation).

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated IPv4 address

      If p is not a valid IPv4 address

    • Checks that the parameter is a valid IPv6 address. Uses the URL constructor as a permissive parser: any string accepted as the host portion of http://[<addr>]/ is considered valid.

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated IPv6 address

      If p is not a valid IPv6 address

    • Checks that the parameter is a valid ISO 8601 date string and returns the parsed Date. Accepts the formats produced by Date#toISOString plus reasonable variants (e.g. with timezone offsets).

      Parameters

      • p: unknown

        The parameter to check

      Returns Date

      The parsed date (always valid)

      If p is not a valid ISO 8601 date string

    • Checks that the parameter is structurally a JSON Web Token: three base64url segments separated by dots.

      This validates the shape only — it does not verify the signature or decode the claims, and must not be used as an authentication check.

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated token

      If p does not have the shape of a JWT

    • Checks that the length of a string or array falls within the given bounds.

      Type Parameters

      • T extends string | readonly unknown[]

        Either string or an array type

      Parameters

      • bounds: { max?: number; min?: number }

        Inclusive length bounds

      • p: unknown

        The parameter to check (string or array)

      Returns T

      The validated value

      If p is not a string/array or its length is out of range

    • Checks that the parameter is a MAC address in colon- or hyphen-separated form.

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated address

      If p is not a valid MAC address

      typer.isMACAddress('00:1A:2B:3C:4D:5E');
      
    • Checks if the provided parameter is a negative integer.

      Parameters

      • p: unknown

        The parameter to check.

      Returns number

      The validated negative integer

      Throws if the parameter is not a negative integer.

      const count = typer.isNegativeInteger(-42); // count: number
      
    • Checks if the provided parameter is a negative number.

      Parameters

      • p: unknown

        The parameter to check.

      Returns number

      The validated negative number

      Throws if the parameter is not a negative number.

      const value = typer.isNegativeNumber(-10); // value: number
      
    • Inverse of isEmpty: checks the parameter is a non-empty string, array, Map, Set, or object.

      Type Parameters

      • T = unknown

        Caller-supplied container type for narrower inference

      Parameters

      • p: unknown

        The parameter to check

      Returns T

      The validated non-empty value

      If p is empty or not a supported container

    • Checks if the provided parameter is a non-empty array.

      Type Parameters

      • T = unknown

        The expected element type

      Parameters

      • p: unknown

        The parameter to check.

      Returns T[]

      The validated non-empty array

      Throws if the parameter is not a non-empty array.

      const items = typer.isNonEmptyArray<string>(["a", "b"]); // items: string[]
      
    • Checks if the provided parameter is a non-empty string.

      Parameters

      • p: unknown

        The parameter to check.

      Returns string

      The validated non-empty string

      Throws if the parameter is not a non-empty string.

      const name = typer.isNonEmptyString("Hello"); // name: string
      
    • Type-safe number validation

      Parameters

      • value: unknown

        The value to check

      Returns value is number

      Type guard for number

    • Type-safe object validation

      Type Parameters

      • T extends Record<string, unknown> = Record<string, unknown>

        The expected object type

      Parameters

      • value: unknown

        The value to check

      Returns value is T

      Type guard for object

    • Checks if the provided parameter is one of the specified values.

      Type Parameters

      • T

        The expected type of the values

      Parameters

      • values: readonly T[]

        The values to check against.

      • p: unknown

        The parameter to check.

      Returns T

      The validated value

      Throws if the parameter is not one of the specified values.

      const color = typer.isOneOf(["red", "blue", "green"] as const, "blue"); // color: "red" | "blue" | "green"
      
    • Checks if the provided parameter is a valid phone number.

      Parameters

      • p: unknown

        The parameter to check.

      Returns string

      The validated phone number string

      Throws if the parameter is not a valid phone number.

      const phone = typer.isPhoneNumber("+1234567890"); // phone: string
      const phone2 = typer.isPhoneNumber("(555) 123-4567"); // phone2: string
    • Checks that the parameter is a plain object (object literal or Object.create(null)). Rejects class instances, arrays, dates, maps, etc.

      Type Parameters

      • T extends Record<string, unknown> = Record<string, unknown>

        The expected plain object shape

      Parameters

      • p: unknown

        The parameter to check

      Returns T

      The validated plain object

      If p is not a plain object

    • Checks that the parameter is a valid TCP/UDP port number (1–65535).

      Port 0 is rejected: it is reserved and never a valid destination.

      Parameters

      • p: unknown

        The parameter to check

      Returns number

      The validated port

      If p is not an integer in range

      typer.isPort(8080);
      
    • Checks if the provided parameter is a positive integer.

      Parameters

      • p: unknown

        The parameter to check.

      Returns number

      The validated positive integer

      Throws if the parameter is not a positive integer.

      const count = typer.isPositiveInteger(42); // count: number
      
    • Checks if the provided parameter is a positive number.

      Parameters

      • p: unknown

        The parameter to check.

      Returns number

      The validated positive number

      Throws if the parameter is not a positive number.

      const value = typer.isPositiveNumber(10); // value: number
      
    • Checks that the parameter is a Promise (or a thenable).

      Type Parameters

      • T = unknown

        The resolved promise type (caller-supplied)

      Parameters

      • p: unknown

        The parameter to check

      Returns Promise<T>

      The validated promise

      If p is not a Promise/thenable

    • Checks that the parameter is a safe integer (within Number.MIN_SAFE_INTEGER and Number.MAX_SAFE_INTEGER).

      Parameters

      • p: unknown

        The parameter to check

      Returns number

      The validated safe integer

      If p is not a safe integer

    • Checks that the parameter is a valid Semantic Versioning 2.0.0 string, including optional pre-release and build metadata.

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated version

      If p is not a valid semver string

      typer.isSemver('1.0.0');
      typer.isSemver('2.1.0-beta.1+build.5');
    • Checks that the parameter is a URL-friendly slug: lowercase alphanumeric groups separated by single hyphens.

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated slug

      If p is not a valid slug

      typer.isSlug('hello-world');
      
    • Type-safe string validation

      Parameters

      • value: unknown

        The value to check

      Returns value is string

      Type guard for string

    • Check if the parameter matches one of the specified types.

      Overloads:

      • When called with a known built-in type alias (or array of aliases), the return type is inferred from TypeMap (e.g. "string" → string).
      • Otherwise the caller can supply an explicit generic T, which falls back to unknown.

      Type Parameters

      Parameters

      • types: K | readonly K[]

        The types to check against.

      • p: unknown

        The parameter to check.

      Returns TypeMap[K]

      Returns the value cast to the expected type

      Throws if the parameter does not match any of the specified types.

      const value = typer.isType("string", "Hello"); // value is typed as string (no generic needed)
      const arr = typer.isType(["number", "boolean"], 42); // typed as number | boolean
      typer.isType<MyShape>("my_custom_type", payload); // explicit generic for custom types
    • Check if the parameter matches one of the specified types.

      Overloads:

      • When called with a known built-in type alias (or array of aliases), the return type is inferred from TypeMap (e.g. "string" → string).
      • Otherwise the caller can supply an explicit generic T, which falls back to unknown.

      Type Parameters

      • T = unknown

        The expected type for better TypeScript inference

      Parameters

      • types: string | readonly string[]

        The types to check against.

      • p: unknown

        The parameter to check.

      Returns T

      Returns the value cast to the expected type

      Throws if the parameter does not match any of the specified types.

      const value = typer.isType("string", "Hello"); // value is typed as string (no generic needed)
      const arr = typer.isType(["number", "boolean"], 42); // typed as number | boolean
      typer.isType<MyShape>("my_custom_type", payload); // explicit generic for custom types
    • Checks if the provided parameter is a valid URL.

      Parameters

      • p: unknown

        The parameter to check.

      Returns string

      Throws if the parameter is not a valid URL.

      console.log(Typer.isURL("https://example.com")); // true
      console.log(Typer.isURL("invalid-url")); // false
    • Checks that the parameter is a valid UUID (versions 1-5, RFC 4122).

      Parameters

      • p: unknown

        The parameter to check

      Returns string

      The validated UUID

      If p is not a valid UUID

    • Defers building a validator until first use, which is what makes self-referential (recursive) shapes expressible.

      The factory runs at most once; the result is reused.

      Type Parameters

      • T

        The validated type

      Parameters

      • factory: () => Validator<T>

        Returns the real validator.

      Returns Validator<T>

      A validator producing T.

      type Node = { name: string; children?: Node[] };
      const node: Validator<Node> = typer.lazy(() => typer.objectOf({
      name: 'string',
      children: typer.optional(typer.arrayOf(node)),
      }) as Validator<Node>);
    • Get all registered types.

      Returns string[]

      An array of registered type names.

      console.log(Typer.listTypes()); // ["array", "number", "string", "boolean"]
      
    • Builds a validator accepting only the listed literal values.

      The returned validator narrows to the union of those literals, so it is the composable counterpart of isOneOf.

      Type Parameters

      • const T extends readonly (string | number | boolean | null)[]

        Tuple of accepted literals

      Parameters

      • ...values: T

        The accepted values.

      Returns Validator<T[number]>

      A validator narrowing to values[number].

      If the value is none of them.

      const role = typer.literal('admin', 'user', 'guest');
      role('admin'); // 'admin' | 'user' | 'guest'
      typer.parse({ role: typer.literal('a', 'b') }, payload);
    • Checks that the parameter is a string matching the given regular expression.

      Parameters

      • regex: RegExp

        The pattern to match against

      • p: unknown

        The parameter to check

      Returns string

      The validated string

      If p is not a string or does not match

    • Combines two schemas. Keys of extension win where the two overlap.

      Type Parameters

      • A extends Record<string, unknown>

        The base schema

      • B extends Record<string, unknown>

        The schema layered on top

      Parameters

      • base: A

        The schema to start from.

      • extension: B

        The schema whose keys take precedence.

      Returns { [K in string | number | symbol]: (Omit<A, keyof B> & B)[K] }

      A new schema; neither source is touched.

      const timestamped = typer.merge(userSchema, { createdAt: 'date', updatedAt: 'date' });
      
    • Wraps an existing validator so that null is also accepted and returned as-is. Useful as a building block for nullable schema fields.

      Type Parameters

      • T

        The type produced by the underlying validator on success

      Parameters

      • validator: Validator<T>

        The validator to make nullable

      Returns Validator<T | null>

      A new validator that accepts T or null

      const maybeStr = typer.nullable(v => typer.asString(v));
      maybeStr(null); // null
      maybeStr("hi"); // "hi"
    • Turns a schema into a Validator, so object shapes can be nested inside the other combinators.

      The schema is compiled once and cached like any other, so this is as fast as calling parse directly.

      The returned validator is also a Standard Schema, so it can be handed straight to tRPC, Hono, TanStack Form and friends.

      Type Parameters

      Parameters

      • schema: S

        The shape to validate against.

      • Optionaloptions: { strict?: boolean } = {}

        strict rejects keys the schema does not declare.

      Returns StandardValidator<
          {
              [K in string
              | number
              | symbol]: (
                  {
                      [K in string
                      | number
                      | symbol]: ResolveSchemaValue<S[K], TRegistry>
                  } & {
                      [K in string
                      | number
                      | symbol]?: ResolveSchemaValue<S[K], TRegistry>
                  }
              )[K]
          },
      >

      A validator producing Infer<S>, carrying ~standard.

      With one issue per problem found.

      const users = typer.arrayOf(typer.objectOf({ id: 'number', name: 'string' }));
      users(payload); // { id: number; name: string }[]
    • Derives a schema without the listed keys — the complement of pick.

      Type Parameters

      • S extends Record<string, unknown>

        The source schema

      • const K extends string | number | symbol

        The keys to drop

      Parameters

      • schema: S

        The schema to derive from.

      • keys: readonly K[]

        The keys to drop.

      Returns { [K in string | number | symbol]: Omit<S, K>[K] }

      A new schema; the source is untouched.

      const createUser = typer.omit(userSchema, ['id']);
      
    • Wraps an existing validator so that undefined is also accepted. Useful for optional schema fields.

      Type Parameters

      • T

        The type produced by the underlying validator on success

      Parameters

      • validator: Validator<T>

        The validator to make optional

      Returns Validator<T | undefined>

      A new validator that accepts T or undefined

      const maybeNum = typer.optional(v => typer.asNumber(v));
      maybeNum(undefined); // undefined
      maybeNum(42); // 42
    • Universal "parse" entry point. Validates value against either:

      • a built-in type alias ("string", "number", ...),
      • an array of aliases (["string", "number"] → union),
      • a Validator<T> function,
      • or a Schema object.

      Returns the value typed correctly. Throws a TypeError on failure.

      No as const is needed when calling with a literal schema thanks to the <const S> parameter — the inferred type matches the schema.

      Declare the schema once, outside the hot path. Compiled checkers are cached by schema object identity, so a literal written inside a handler is a new object on every call and is recompiled every time — about an order of magnitude slower (78 ns hoisted against 873 ns inline), with nothing to show for it:

      const userSchema = typer.schema({ id: 'number' });   // once
      app.post('/u', (req) => typer.parse(userSchema, req.body));

      app.post('/u', (req) => typer.parse({ id: 'number' }, req.body)); // recompiles

      Type Parameters

      Parameters

      • types: K | readonly K[]
      • value: unknown

      Returns TypeMap[K]

      const user = typer.parse(
      { id: 'number', name: 'string', email: 'string?' },
      payload,
      );
      // user is typed as { id: number; name: string; email?: string | null }
    • Universal "parse" entry point. Validates value against either:

      • a built-in type alias ("string", "number", ...),
      • an array of aliases (["string", "number"] → union),
      • a Validator<T> function,
      • or a Schema object.

      Returns the value typed correctly. Throws a TypeError on failure.

      No as const is needed when calling with a literal schema thanks to the <const S> parameter — the inferred type matches the schema.

      Declare the schema once, outside the hot path. Compiled checkers are cached by schema object identity, so a literal written inside a handler is a new object on every call and is recompiled every time — about an order of magnitude slower (78 ns hoisted against 873 ns inline), with nothing to show for it:

      const userSchema = typer.schema({ id: 'number' });   // once
      app.post('/u', (req) => typer.parse(userSchema, req.body));

      app.post('/u', (req) => typer.parse({ id: 'number' }, req.body)); // recompiles

      Type Parameters

      • T

      Parameters

      Returns T

      const user = typer.parse(
      { id: 'number', name: 'string', email: 'string?' },
      payload,
      );
      // user is typed as { id: number; name: string; email?: string | null }
    • Universal "parse" entry point. Validates value against either:

      • a built-in type alias ("string", "number", ...),
      • an array of aliases (["string", "number"] → union),
      • a Validator<T> function,
      • or a Schema object.

      Returns the value typed correctly. Throws a TypeError on failure.

      No as const is needed when calling with a literal schema thanks to the <const S> parameter — the inferred type matches the schema.

      Declare the schema once, outside the hot path. Compiled checkers are cached by schema object identity, so a literal written inside a handler is a new object on every call and is recompiled every time — about an order of magnitude slower (78 ns hoisted against 873 ns inline), with nothing to show for it:

      const userSchema = typer.schema({ id: 'number' });   // once
      app.post('/u', (req) => typer.parse(userSchema, req.body));

      app.post('/u', (req) => typer.parse({ id: 'number' }, req.body)); // recompiles

      Type Parameters

      Parameters

      • schema: S
      • value: unknown

      Returns {
          [K in string | number | symbol]: (
              {
                  [K in string
                  | number
                  | symbol]: ResolveSchemaValue<S[K], TRegistry>
              } & {
                  [K in string
                  | number
                  | symbol]?: ResolveSchemaValue<S[K], TRegistry>
              }
          )[K]
      }

      const user = typer.parse(
      { id: 'number', name: 'string', email: 'string?' },
      payload,
      );
      // user is typed as { id: number; name: string; email?: string | null }
    • Universal "parse" entry point. Validates value against either:

      • a built-in type alias ("string", "number", ...),
      • an array of aliases (["string", "number"] → union),
      • a Validator<T> function,
      • or a Schema object.

      Returns the value typed correctly. Throws a TypeError on failure.

      No as const is needed when calling with a literal schema thanks to the <const S> parameter — the inferred type matches the schema.

      Declare the schema once, outside the hot path. Compiled checkers are cached by schema object identity, so a literal written inside a handler is a new object on every call and is recompiled every time — about an order of magnitude slower (78 ns hoisted against 873 ns inline), with nothing to show for it:

      const userSchema = typer.schema({ id: 'number' });   // once
      app.post('/u', (req) => typer.parse(userSchema, req.body));

      app.post('/u', (req) => typer.parse({ id: 'number' }, req.body)); // recompiles

      Type Parameters

      • T

      Parameters

      • types: string | readonly string[]
      • value: unknown

      Returns T

      const user = typer.parse(
      { id: 'number', name: 'string', email: 'string?' },
      payload,
      );
      // user is typed as { id: number; name: string; email?: string | null }
    • Derives a schema with every key optional, or only the listed ones.

      A type-string slot simply gains the ? marker. Every other slot kind has no marker of its own in the schema language, so it is wrapped with optional — which means a nested schema or array slot made optional reports its failures as one custom issue at the slot's path, rather than one issue per offending field. Pass the keys you actually need if that matters.

      Type Parameters

      • S extends Record<string, unknown>

        The source schema

      Parameters

      • schema: S

        The schema to derive from.

      Returns {
          [K in string | number | symbol]: {
              [P in string | number | symbol]: P extends keyof S
                  ? OptionalSlot<S[P]>
                  : S[P]
          }[K]
      }

      A new schema; the source is untouched.

      const patchUser = typer.partial(typer.omit(userSchema, ['id']));
      type PatchUser = Infer<typeof patchUser>; // { name?: string | null; … }

      // Only some keys:
      const draft = typer.partial(userSchema, ['name']);
    • Derives a schema with every key optional, or only the listed ones.

      A type-string slot simply gains the ? marker. Every other slot kind has no marker of its own in the schema language, so it is wrapped with optional — which means a nested schema or array slot made optional reports its failures as one custom issue at the slot's path, rather than one issue per offending field. Pass the keys you actually need if that matters.

      Type Parameters

      • S extends Record<string, unknown>

        The source schema

      • const K extends string | number | symbol

        The keys to make optional; all of them by default

      Parameters

      • schema: S

        The schema to derive from.

      • keys: readonly K[]

        The keys to make optional. Omit for all of them.

      Returns {
          [K in string | number | symbol]: {
              [P in string | number | symbol]: P extends K
                  ? OptionalSlot<S[P]>
                  : S[P]
          }[K]
      }

      A new schema; the source is untouched.

      const patchUser = typer.partial(typer.omit(userSchema, ['id']));
      type PatchUser = Infer<typeof patchUser>; // { name?: string | null; … }

      // Only some keys:
      const draft = typer.partial(userSchema, ['name']);
    • Derives a schema keeping only the listed keys.

      Real applications derive schemas from each other constantly — CreateUserDto from UserDto — and rewriting the shape by hand means two copies that diverge at the first change.

      Type Parameters

      • S extends Record<string, unknown>

        The source schema

      • const K extends string | number | symbol

        The keys to keep

      Parameters

      • schema: S

        The schema to derive from.

      • keys: readonly K[]

        The keys to keep.

      Returns { [K in string | number | symbol]: Pick<S, K>[K] }

      A new schema; the source is untouched.

      const userSchema = typer.schema({ id: 'number', name: 'string', password: 'string' });
      const publicUser = typer.pick(userSchema, ['id', 'name']);
      type PublicUser = Infer<typeof publicUser>; // { id: number; name: string }
    • Builds a validator for a dictionary object: any set of keys, all values satisfying value.

      Rejects arrays and null, unlike the 'object' alias.

      Keys that are dangerous to copy (__proto__, constructor, prototype) are dropped rather than written to the result: assigning out['__proto__'] would set the output's prototype instead of a field.

      Type Parameters

      • T

        The value type

      Parameters

      • value: Validator<T>

        Validator applied to each own enumerable value.

      Returns Validator<Record<string, T>>

      A validator producing Record<string, T>.

      If the input is not a plain dictionary or a value fails.

      const scores = typer.record((v) => typer.asNumber(v));
      scores({ alice: 1, bob: 2 }); // Record<string, number>
    • Adds a constraint to an existing validator without changing its type.

      Type Parameters

      • T

        The validated type

      Parameters

      • validator: Validator<T>

        The validator to run first.

      • predicate: (value: T) => boolean

        Must return true for the value to be accepted.

      • message: string

        Error message used when the predicate fails.

      Returns Validator<T>

      A validator producing T.

      If the base validator fails, or the predicate returns false.

      const even = typer.refine((v) => typer.asNumber(v), (n) => n % 2 === 0, 'must be even');
      
    • Register a new type in the typesMap.

      Type Parameters

      • T = unknown

        The input type that the validator expects

      • R = T

        The return type that the validator produces

      Parameters

      • name: string

        The name of the new type.

      • validator: (value: T) => R

        The function to validate the type.

      • override: boolean = false

        Whether to override the original configuration

      Returns void

      If the type name is already registered.

      // Register a positive number validator
      typer.registerType<unknown, number>("positive", (value) => {
      if (typeof value !== "number" || value <= 0) throw new TypeError("Must be positive");
      return value;
      });

      // Register a string length validator
      typer.registerType<unknown, string>("longString", (value) => {
      if (typeof value !== "string" || value.length < 10) throw new TypeError("Must be long string");
      return value;
      });
    • Validates value without throwing. Same input shapes as parse. Returns a discriminated union: { success: true, data } or { success: false, error }.

      Type Parameters

      Parameters

      • types: K | readonly K[]
      • value: unknown

      Returns ParseResult<TypeMap[K]>

      const result = typer.safeParse(
      { id: 'number', name: 'string' },
      payload,
      );
      if (result.success) {
      // result.data is { id: number; name: string }
      } else {
      console.error(result.error.message);
      }
    • Validates value without throwing. Same input shapes as parse. Returns a discriminated union: { success: true, data } or { success: false, error }.

      Type Parameters

      • T

      Parameters

      Returns ParseResult<T>

      const result = typer.safeParse(
      { id: 'number', name: 'string' },
      payload,
      );
      if (result.success) {
      // result.data is { id: number; name: string }
      } else {
      console.error(result.error.message);
      }
    • Validates value without throwing. Same input shapes as parse. Returns a discriminated union: { success: true, data } or { success: false, error }.

      Type Parameters

      Parameters

      • schema: S
      • value: unknown

      Returns ParseResult<
          {
              [K in string
              | number
              | symbol]: (
                  {
                      [K in string
                      | number
                      | symbol]: ResolveSchemaValue<S[K], TRegistry>
                  } & {
                      [K in string
                      | number
                      | symbol]?: ResolveSchemaValue<S[K], TRegistry>
                  }
              )[K]
          },
      >

      const result = typer.safeParse(
      { id: 'number', name: 'string' },
      payload,
      );
      if (result.success) {
      // result.data is { id: number; name: string }
      } else {
      console.error(result.error.message);
      }
    • Validates value without throwing. Same input shapes as parse. Returns a discriminated union: { success: true, data } or { success: false, error }.

      Type Parameters

      • T

      Parameters

      • types: string | readonly string[]
      • value: unknown

      Returns ParseResult<T>

      const result = typer.safeParse(
      { id: 'number', name: 'string' },
      payload,
      );
      if (result.success) {
      // result.data is { id: number; name: string }
      } else {
      console.error(result.error.message);
      }
    • Identity helper that preserves literal types of a schema declared as a variable. Use it when you want to declare the schema once, derive Infer<typeof schema>, and then call parse(schema, value) with full type inference — without sprinkling as const.

      Declaring the schema in a variable is also what makes it fast: compiled checkers are cached by object identity, so a schema hoisted out of the handler is compiled once, while a literal written inside it is a new object every call and is recompiled every time.

      Type Parameters

      Parameters

      • definition: S

      Returns S

      const userSchema = typer.schema({
      id: 'number',
      name: 'string',
      email: 'string?',
      });
      type User = Infer<typeof userSchema>;
      const user = typer.parse(userSchema, payload); // typed
    • Turns any schema, validator or type alias into a Standard Schema.

      Standard Schema is the common contract that lets a validation library be accepted by tRPC, Hono, TanStack Form and Router, Nuxt and the rest, without a per-library adapter. The returned value is still a plain validator function, so it also keeps working everywhere a Validator does.

      Schema literals are the one shape that cannot carry ~standard on their own — they are inert object literals owned by the caller, and Typer does not mutate them — which is why this wrapper exists.

      Type Parameters

      Parameters

      • target: K | readonly K[]

        A schema object, a Validator, or a type alias (or array of aliases).

      Returns StandardValidator<TypeMap[K]>

      The validator, carrying ~standard.

      const userSchema = typer.standard({ id: 'number', email: 'string' });
      userSchema['~standard'].validate({ id: 1, email: 'a@b.c' }); // { value: … }

      // tRPC, Hono, TanStack … accept it directly:
      router.post('/users', validator('json', userSchema), handler);
    • Turns any schema, validator or type alias into a Standard Schema.

      Standard Schema is the common contract that lets a validation library be accepted by tRPC, Hono, TanStack Form and Router, Nuxt and the rest, without a per-library adapter. The returned value is still a plain validator function, so it also keeps working everywhere a Validator does.

      Schema literals are the one shape that cannot carry ~standard on their own — they are inert object literals owned by the caller, and Typer does not mutate them — which is why this wrapper exists.

      Type Parameters

      • T

      Parameters

      • target: Validator<T>

        A schema object, a Validator, or a type alias (or array of aliases).

      Returns StandardValidator<T>

      The validator, carrying ~standard.

      const userSchema = typer.standard({ id: 'number', email: 'string' });
      userSchema['~standard'].validate({ id: 1, email: 'a@b.c' }); // { value: … }

      // tRPC, Hono, TanStack … accept it directly:
      router.post('/users', validator('json', userSchema), handler);
    • Turns any schema, validator or type alias into a Standard Schema.

      Standard Schema is the common contract that lets a validation library be accepted by tRPC, Hono, TanStack Form and Router, Nuxt and the rest, without a per-library adapter. The returned value is still a plain validator function, so it also keeps working everywhere a Validator does.

      Schema literals are the one shape that cannot carry ~standard on their own — they are inert object literals owned by the caller, and Typer does not mutate them — which is why this wrapper exists.

      Type Parameters

      Parameters

      • target: S

        A schema object, a Validator, or a type alias (or array of aliases).

      • Optionaloptions: { strict?: boolean }

        Schema objects only: strict rejects undeclared keys.

      Returns StandardValidator<
          {
              [K in string
              | number
              | symbol]: (
                  {
                      [K in string
                      | number
                      | symbol]: ResolveSchemaValue<S[K], TRegistry>
                  } & {
                      [K in string
                      | number
                      | symbol]?: ResolveSchemaValue<S[K], TRegistry>
                  }
              )[K]
          },
      >

      The validator, carrying ~standard.

      const userSchema = typer.standard({ id: 'number', email: 'string' });
      userSchema['~standard'].validate({ id: 1, email: 'a@b.c' }); // { value: … }

      // tRPC, Hono, TanStack … accept it directly:
      router.post('/users', validator('json', userSchema), handler);
    • Turns any schema, validator or type alias into a Standard Schema.

      Standard Schema is the common contract that lets a validation library be accepted by tRPC, Hono, TanStack Form and Router, Nuxt and the rest, without a per-library adapter. The returned value is still a plain validator function, so it also keeps working everywhere a Validator does.

      Schema literals are the one shape that cannot carry ~standard on their own — they are inert object literals owned by the caller, and Typer does not mutate them — which is why this wrapper exists.

      Type Parameters

      • T

      Parameters

      • target: string | readonly string[]

        A schema object, a Validator, or a type alias (or array of aliases).

      Returns StandardValidator<T>

      The validator, carrying ~standard.

      const userSchema = typer.standard({ id: 'number', email: 'string' });
      userSchema['~standard'].validate({ id: 1, email: 'a@b.c' }); // { value: … }

      // tRPC, Hono, TanStack … accept it directly:
      router.post('/users', validator('json', userSchema), handler);
    • Converts a schema into a JSON Schema document — the input OpenAPI and Swagger tooling expects, and the main reason people reach for TypeBox.

      Type strings, ? markers, | unions, arrays and nested objects all have exact equivalents. Validator slots do not: a validator is an opaque function, so Typer's own validators and combinators carry the fragment they correspond to (isEmail becomes { type: 'string', format: 'email' }, arrayOf(…, { min: 1 }) becomes minItems: 1), and a validator the caller wrote becomes {} — which accepts anything.

      Aliases with no JSON counterpart — symbol, function, map, set, regexp, the buffer types, and anything registered with extend — are in the same position. Pass unrepresentable: 'throw' in a build step to be told about them instead of shipping a schema that quietly accepts anything at those keys.

      Type Parameters

      Parameters

      • schema: S

        The schema to convert.

      • Optionaloptions: ToJSONSchemaOptions = {}

        Dialect, metadata, strictness, and the unrepresentable-slot policy.

      Returns JSONSchemaDocument

      A JSON Schema document, draft 2020-12 by default.

      With unrepresentable: 'throw', listing every slot that has no equivalent.

      typer.toJSONSchema({ id: 'number', email: typer.validators.isEmail, note: 'string?' });
      // {
      // $schema: 'https://json-schema.org/draft/2020-12/schema',
      // type: 'object',
      // properties: {
      // id: { type: 'number' },
      // email: { type: 'string', format: 'email' },
      // note: { type: ['string', 'null'] },
      // },
      // required: ['id', 'email'],
      // }
    • Maps a validated value to another shape. Validation runs first, so the transformer only ever sees a well-typed input.

      Type Parameters

      • T

        The validated type

      • U

        The produced type

      Parameters

      • validator: Validator<T>

        The validator to run first.

      • transformer: (value: T) => U

        Applied to the validated value.

      Returns Validator<U>

      A validator producing U.

      const trimmed = typer.transform((v) => typer.asString(v), (s) => s.trim());
      
    • Builds a validator for a fixed-length, heterogeneous array.

      Type Parameters

      • const T extends readonly Validator<unknown>[]

        Tuple of element validators

      Parameters

      • validators: T

        One validator per position.

      Returns Validator<
          {
              -readonly [K in string
              | number
              | symbol]: T[K] extends Validator<U> ? U : never
          },
      >

      A validator producing the corresponding tuple type.

      If the value is not an array of exactly that length, or an element fails.

      const point = typer.tuple([(v) => typer.asNumber(v), (v) => typer.asNumber(v)]);
      point([1, 2]); // [number, number]
    • Combines multiple validators into one that succeeds if any of them succeeds. The first matching validator's result is returned.

      Type Parameters

      • T extends readonly unknown[]

        Tuple of types produced by each validator

      Parameters

      • ...validators: { [K in string | number | symbol]: Validator<T[K]> }

        Validators to try in order

      Returns Validator<T[number]>

      A new validator that returns the first matching result

      If none of the validators accepts the value

      const stringOrNumber = typer.union(
      v => typer.asString(v),
      v => typer.asNumber(v),
      );
      stringOrNumber(42); // 42
      stringOrNumber("hi"); // "hi"
    • Unregister a type from the typesMap.

      Parameters

      • name: string

        The name of the type to remove.

      Returns void

      If the type does not exist.

      Typer.unregisterType("positive");
      
    • Validates an object against a schema.

      Parameters

      • schema: Record<string, string | string[]>

        The expected types for each key.

      • obj: Record<string, unknown>

        The object to validate.

      Returns string[]

      • An array of validation errors, or an empty array if valid.
      const schema = { name: "string", age: "number" };
      const obj = { name: "John", age: "25" };
      console.log(Typer.validate(schema, obj)); // ["Expected 'age' to be of type number, got string"]
    • Substitutes a default when the value is undefined, and validates everything else.

      Pass a factory (() => T) for object or array defaults so each call gets its own instance. A plain function default must be wrapped in a factory, since functions are treated as factories.

      Type Parameters

      • T

        The validated type

      Parameters

      • validator: Validator<T>

        Applied when the value is present.

      • fallback: T | (() => T)

        Value, or factory, used when undefined.

      Returns Validator<T>

      A validator producing T.

      const limit = typer.withDefault((v) => typer.asNumber(v), 10);
      limit(undefined); // 10