💎 Zod 4 现已稳定发布! 阅读公告。
Zod logo

Zod 核心

Edit this page

该子包导出被 Zod 和 Zod Mini 使用的核心类和工具。它不打算被直接使用;相反,它设计为供其他包进行扩展。它实现了:

import * as z from "zod/v4/core";
 
// 所有 Zod schema 的基类
z.$ZodType;
 
// 实现常用解析器的 $ZodType 子类
z.$ZodString
z.$ZodObject
z.$ZodArray
// ...
 
// 所有 Zod 校验的基类
z.$ZodCheck;
 
// 实现常用校验的 $ZodCheck 子类
z.$ZodCheckMinLength
z.$ZodCheckMaxLength
 
// 所有 Zod 错误的基类
z.$ZodError;
 
// Issue 格式(仅类型)
{} as z.$ZodIssue;
 
// 工具函数
z.util.isValidJWT(...);

Schemas(模式)

所有 Zod schema 的基类是 $ZodType,它接受两个泛型参数:OutputInput

export class $ZodType<Output = unknown, Input = unknown> {
  _zod: { /* 内部实现 */}
}

zod/v4/core 导出了一些实现常用解析器的子类。所有官方子类的联合类型导出为 z.$ZodTypes

export type $ZodTypes =
  | $ZodString
  | $ZodNumber
  | $ZodBigInt
  | $ZodBoolean
  | $ZodDate
  | $ZodSymbol
  | $ZodUndefined
  | $ZodNullable
  | $ZodNull
  | $ZodAny
  | $ZodUnknown
  | $ZodNever
  | $ZodVoid
  | $ZodArray
  | $ZodObject
  | $ZodUnion // $ZodDiscriminatedUnion extends this
  | $ZodIntersection
  | $ZodTuple
  | $ZodRecord
  | $ZodMap
  | $ZodSet
  | $ZodLiteral
  | $ZodEnum
  | $ZodPromise
  | $ZodLazy
  | $ZodOptional
  | $ZodDefault
  | $ZodTemplateLiteral
  | $ZodCustom
  | $ZodTransform
  | $ZodNonOptional
  | $ZodReadonly
  | $ZodNaN
  | $ZodPipe // $ZodCodec extends this
  | $ZodSuccess
  | $ZodCatch
  | $ZodFile;

Internals(内部实现)

所有 zod/v4/core 子类仅包含一个属性:_zod。该属性是一个包含模式内部的对象。目标是使 zod/v4/core 尽可能可扩展且不带偏见。其他库可以在这些类的基础上“构建自己的 Zod”,而不必让 zod/v4/core 使接口变得杂乱。请参考 zodzod/mini 的实现,以获取如何扩展这些类的示例。

_zod 内部属性包含一些重要属性:

  • .def — schema 的定义:你传入类构造器以创建实例的对象。它完整描述了 schema,且支持 JSON 序列化。
    • .def.type — 表示 schema 类型的字符串,比如 "string""object""array" 等。
    • .def.checks — schema 在解析后执行的 checks 数组。
  • .input — 虚拟属性,代表 schema 推断的输入类型
  • .output — 虚拟属性,代表 schema 推断的输出类型
  • .run() — schema 的内部解析实现。

如果你在实现一个需要遍历 Zod schemas 的工具(例如代码生成器),你可以将任意 schema 转换为 $ZodTypes 并使用 def 属性来区分这些类。

export function walk(_schema: z.$ZodType) {
  const schema = _schema as z.$ZodTypes;
  const def = schema._zod.def;
  switch (def.type) {
    case "string": {
      // ...
      break;
    }
    case "object": {
      // ...
      break;
    }
  }
}

有许多 $ZodString 的子类实现了各种字符串格式。它们被导出为 z.$ZodStringFormatTypes

export type $ZodStringFormatTypes =
  | $ZodGUID
  | $ZodUUID
  | $ZodEmail
  | $ZodURL
  | $ZodEmoji
  | $ZodNanoID
  | $ZodCUID
  | $ZodCUID2
  | $ZodULID
  | $ZodXID
  | $ZodKSUID
  | $ZodISODateTime
  | $ZodISODate
  | $ZodISOTime
  | $ZodISODuration
  | $ZodIPv4
  | $ZodIPv6
  | $ZodCIDRv4
  | $ZodCIDRv6
  | $ZodBase64
  | $ZodBase64URL
  | $ZodE164
  | $ZodJWT

Parsing(解析)

因为 Zod Core schema 类没有方法,解析数据用的是顶层函数。

import * as z from "zod/v4/core";
 
const schema = new z.$ZodString({ type: "string" });
z.parse(schema, "hello");
z.safeParse(schema, "hello");
await z.parseAsync(schema, "hello");
await z.safeParseAsync(schema, "hello");

Checks(校验)

每个 Zod schema 包含一个 checks 数组。这些用于在解析后执行细化(有时是变异),不影响推断类型。

const schema = z.string().check(z.email()).check(z.min(5));
// => $ZodString
 
schema._zod.def.checks;
// => [$ZodCheckEmail, $ZodCheckMinLength]

所有 Zod 校验的基类是 $ZodCheck,接受一个泛型参数 T

export class $ZodCheck<in T = unknown> {
  _zod: { /* 内部实现 */}
}

_zod 内部属性包含一些显著的属性:

  • .def — 检查的 定义:这是您传递给类构造函数以创建检查的对象。它完全描述了检查,并且是可 JSON 序列化的。
    • .def.check — 一个表示检查类型的字符串,例如 "min_length""less_than""string_format" 等。
  • .check() — 包含检查的验证逻辑。

zod/v4/core 导出了一些执行常见细化的子类。所有第一方子类都作为一个名为 z.$ZodChecks 的联合体导出。

export type $ZodChecks =
  | $ZodCheckLessThan
  | $ZodCheckGreaterThan
  | $ZodCheckMultipleOf
  | $ZodCheckNumberFormat
  | $ZodCheckBigIntFormat
  | $ZodCheckMaxSize
  | $ZodCheckMinSize
  | $ZodCheckSizeEquals
  | $ZodCheckMaxLength
  | $ZodCheckMinLength
  | $ZodCheckLengthEquals
  | $ZodCheckProperty
  | $ZodCheckMimeType
  | $ZodCheckOverwrite
  | $ZodCheckStringFormat

你可以使用 ._zod.def.check 属性区分这些类。

const check = {} as z.$ZodChecks;
const def = check._zod.def;
 
switch (def.check) {
  case "less_than":
  case "greater_than":
    // ...
    break;
}

跟模式类型类似,$ZodCheckStringFormat 有许多子类实现各种字符串格式

export type $ZodStringFormatChecks =
  | $ZodCheckRegex
  | $ZodCheckLowerCase
  | $ZodCheckUpperCase
  | $ZodCheckIncludes
  | $ZodCheckStartsWith
  | $ZodCheckEndsWith
  | $ZodGUID
  | $ZodUUID
  | $ZodEmail
  | $ZodURL
  | $ZodEmoji
  | $ZodNanoID
  | $ZodCUID
  | $ZodCUID2
  | $ZodULID
  | $ZodXID
  | $ZodKSUID
  | $ZodISODateTime
  | $ZodISODate
  | $ZodISOTime
  | $ZodISODuration
  | $ZodIPv4
  | $ZodIPv6
  | $ZodCIDRv4
  | $ZodCIDRv6
  | $ZodBase64
  | $ZodBase64URL
  | $ZodE164
  | $ZodJWT;

使用嵌套 switch 来区分不同字符串格式的校验。

const check = {} as z.$ZodChecks;
const def = check._zod.def;
 
switch (def.check) {
  case "less_than":
  case "greater_than":
  // ...
  case "string_format":
    {
      const formatCheck = check as z.$ZodStringFormatChecks;
      const formatCheckDef = formatCheck._zod.def;
 
      switch (formatCheckDef.format) {
        case "email":
        case "url":
          // 执行相关操作
      }
    }
    break;
}

你会注意到,有些字符串格式校验和上面字符串格式类型是重叠的。这是因为这些类同时实现了 $ZodCheck$ZodType 接口。也就是说,它们可以作为校验或类型使用。在这些情况下,解析时会执行 ._zod.parse(schema解析器)和 ._zod.check(校验验证)。实际上,该实例会被添加到自身的 checks 数组前端(但它不会真正存在于 ._zod.def.checks 中)。

// 作为类型
z.email().parse("user@example.com");
 
// 作为校验
z.string().check(z.email()).parse("user@example.com")

Errors(错误)

所有 Zod 错误的基类是 $ZodError

出于性能考虑,$ZodError 继承内置的 Error 类!因此使用 instanceof Error 会返回 false

  • zod 包实现了 $ZodError 的子类 ZodError,带有一些额外的便捷方法。
  • zod/mini 子包直接使用 $ZodError
export class $ZodError<T = unknown> implements Error {
 public issues: $ZodIssue[];
}

Issues(问题)

issues 属性对应 $ZodIssue 对象数组。所有 issues 都扩展了 z.$ZodIssueBase 接口。

export interface $ZodIssueBase {
  readonly code?: string;
  readonly input?: unknown;
  readonly path: PropertyKey[];
  readonly message: string;
}

Zod 定义了以下 issue 子类型:

export type $ZodIssue =
  | $ZodIssueInvalidType
  | $ZodIssueTooBig
  | $ZodIssueTooSmall
  | $ZodIssueInvalidStringFormat
  | $ZodIssueNotMultipleOf
  | $ZodIssueUnrecognizedKeys
  | $ZodIssueInvalidUnion
  | $ZodIssueInvalidKey
  | $ZodIssueInvalidElement
  | $ZodIssueInvalidValue
  | $ZodIssueCustom;

关于各类型详情,请参考实现代码

On this page