zod 3.14.1 → 3.14.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -3,11 +3,11 @@
3
3
  <h1 align="center">Zod</h1>
4
4
  </p>
5
5
  <p align="center">
6
+ <a href="https://github.com/edgedb/edgedb-js/actions"><img src="https://github.com/colinhacks/zod/actions/workflows/test.yml/badge.svg?event=push&branch=master" alt="Zod CI status" /></a>
6
7
  <a href="https://twitter.com/colinhacks" rel="nofollow"><img src="https://img.shields.io/badge/created%20by-@colinhacks-4BBAAB.svg" alt="Created by Colin McDonnell"></a>
7
8
  <a href="https://opensource.org/licenses/MIT" rel="nofollow"><img src="https://img.shields.io/github/license/colinhacks/zod" alt="License"></a>
8
9
  <a href="https://www.npmjs.com/package/zod" rel="nofollow"><img src="https://img.shields.io/npm/dw/zod.svg" alt="npm"></a>
9
10
  <a href="https://www.npmjs.com/package/zod" rel="nofollow"><img src="https://img.shields.io/github/stars/colinhacks/zod" alt="stars"></a>
10
- <a href="./src/__tests__" rel="nofollow"><img src="./coverage.svg" alt="coverage"></a>
11
11
  <a href="https://discord.gg/KaSRdyX2vc" rel="nofollow"><img src="https://img.shields.io/discord/893487829802418277?label=Discord&logo=discord&logoColor=white" alt="discord server"></a>
12
12
  </p>
13
13
 
@@ -94,8 +94,10 @@ These docs have been translated into [Chinese](./README_ZH.md).
94
94
  - [.promise](#promise)
95
95
  - [.or](#or)
96
96
  - [.and](#and)
97
- - [Type inference](#type-inference)
98
- - [Errors](#errors)
97
+ - [Guides and concepts](#guides-and-concepts)
98
+ - [Type inference](#type-inference)
99
+ - [Writing generic functions](#writing-generic-functions)
100
+ - [Error handling](#error-handling)
99
101
  - [Comparison](#comparison)
100
102
  - [Joi](#joi)
101
103
  - [Yup](#yup)
@@ -241,6 +243,8 @@ There are a growing number of tools that are built atop or support Zod natively!
241
243
  - [`soly`](https://github.com/mdbetancourt/soly): Create CLI applications with zod.
242
244
  - [`graphql-codegen-typescript-validation-schema`](https://github.com/Code-Hex/graphql-codegen-typescript-validation-schema): GraphQL Code Generator plugin to generate form validation schema from your GraphQL schema
243
245
  - [`zod-prisma`](https://github.com/CarterGrimmeisen/zod-prisma): Generate Zod schemas from your Prisma schema.
246
+ - [`fastify-type-provider-zod`](https://github.com/turkerdev/fastify-type-provider-zod): Create Fastify type providers from Zod schemas
247
+ - [`Supervillain`](https://github.com/Southclaws/supervillain): Generate Zod schemas from your Go structs
244
248
 
245
249
  ### Form integrations
246
250
 
@@ -1687,7 +1691,9 @@ z.object({ name: z.string() }).and(z.object({ age: z.number() })); // { name: st
1687
1691
  z.intersection(z.object({ name: z.string() }), z.object({ age: z.number() }));
1688
1692
  ```
1689
1693
 
1690
- # Type inference
1694
+ # Guides and concepts
1695
+
1696
+ ## Type inference
1691
1697
 
1692
1698
  You can extract the TypeScript type of any schema with `z.infer<typeof mySchema>` .
1693
1699
 
@@ -1716,16 +1722,72 @@ type output = z.output<typeof stringToNumber>; // number
1716
1722
  type inferred = z.infer<typeof stringToNumber>; // number
1717
1723
  ```
1718
1724
 
1719
- # Errors
1725
+ ## Writing generic functions
1726
+
1727
+ When attempting to write a functions that accepts a Zod schemas as an input, it's common to try something like this:
1728
+
1729
+ ```ts
1730
+ function makeSchemaOptional<T>(schema: z.ZodType<T>) {
1731
+ return schema.optional();
1732
+ }
1733
+ ```
1734
+
1735
+ This approach has some issues. The `schema` variable in this function is typed as an instance of `ZodType`, which is an abstract class that all Zod schemas inherit from. This approach loses type information, namely _which subclass_ the input actually is.
1736
+
1737
+ ```ts
1738
+ const arg = makeSchemaOptional(z.string());
1739
+ arg.unwrap();
1740
+ ```
1741
+
1742
+ A better approach is for the generate parameter to refer to _the schema as a whole_.
1743
+
1744
+ ```ts
1745
+ function makeSchemaOptional<T extends z.ZodTypeAny>(schema: T) {
1746
+ return schema.optional();
1747
+ }
1748
+ ```
1749
+
1750
+ > `ZodTypeAny` is just a shorthand for `ZodType<any, any, any>`, a type that is broad enough to match any Zod schema.
1751
+
1752
+ As you can see, `schema` is now fully and properly typed.
1753
+
1754
+ ```ts
1755
+ const arg = makeSchemaOptional(z.string());
1756
+ arg.unwrap(); // ZodString
1757
+ ```
1758
+
1759
+ ### Restricting valid schemas
1760
+
1761
+ The `ZodType` class has three generic parameters.
1762
+
1763
+ ```ts
1764
+ class ZodType<
1765
+ Output,
1766
+ Def extends ZodTypeDef = ZodTypeDef,
1767
+ Input = Output
1768
+ > { ... }
1769
+ ```
1770
+
1771
+ By contraining these in your generic input, you can limit what schemas are allowable as inputs to your function:
1772
+
1773
+ ```ts
1774
+ function makeSchemaOptional<T extends z.ZodType<string>>(schema: T) {
1775
+ return schema.optional();
1776
+ }
1777
+
1778
+ makeSchemaOptional(z.string());
1779
+ // works fine
1780
+
1781
+ makeSchemaOptional(z.number());
1782
+ // Error: 'ZodNumber' is not assignable to parameter of type 'ZodType<string, ZodTypeDef, string>'
1783
+ ```
1784
+
1785
+ ## Error handling
1720
1786
 
1721
1787
  Zod provides a subclass of Error called `ZodError`. ZodErrors contain an `issues` array containing detailed information about the validation problems.
1722
1788
 
1723
1789
  ```ts
1724
- const data = z
1725
- .object({
1726
- name: z.string(),
1727
- })
1728
- .safeParse({ name: 12 });
1790
+ const data = z.object({ name: z.string() }).safeParse({ name: 12 });
1729
1791
 
1730
1792
  if (!data.success) {
1731
1793
  data.error.issues;
package/lib/ZodError.d.ts CHANGED
@@ -3,6 +3,7 @@ import { Primitive } from "./helpers/typeAliases";
3
3
  import { util } from "./helpers/util";
4
4
  export declare const ZodIssueCode: {
5
5
  invalid_type: "invalid_type";
6
+ invalid_literal: "invalid_literal";
6
7
  custom: "custom";
7
8
  invalid_union: "invalid_union";
8
9
  invalid_union_discriminator: "invalid_union_discriminator";
@@ -27,6 +28,10 @@ export interface ZodInvalidTypeIssue extends ZodIssueBase {
27
28
  expected: ZodParsedType;
28
29
  received: ZodParsedType;
29
30
  }
31
+ export interface ZodInvalidLiteralIssue extends ZodIssueBase {
32
+ code: typeof ZodIssueCode.invalid_literal;
33
+ expected: unknown;
34
+ }
30
35
  export interface ZodUnrecognizedKeysIssue extends ZodIssueBase {
31
36
  code: typeof ZodIssueCode.unrecognized_keys;
32
37
  keys: string[];
@@ -87,7 +92,7 @@ export interface ZodCustomIssue extends ZodIssueBase {
87
92
  export declare type DenormalizedError = {
88
93
  [k: string]: DenormalizedError | string[];
89
94
  };
90
- export declare type ZodIssueOptionalMessage = ZodInvalidTypeIssue | ZodUnrecognizedKeysIssue | ZodInvalidUnionIssue | ZodInvalidUnionDiscriminatorIssue | ZodInvalidEnumValueIssue | ZodInvalidArgumentsIssue | ZodInvalidReturnTypeIssue | ZodInvalidDateIssue | ZodInvalidStringIssue | ZodTooSmallIssue | ZodTooBigIssue | ZodInvalidIntersectionTypesIssue | ZodNotMultipleOfIssue | ZodCustomIssue;
95
+ export declare type ZodIssueOptionalMessage = ZodInvalidTypeIssue | ZodInvalidLiteralIssue | ZodUnrecognizedKeysIssue | ZodInvalidUnionIssue | ZodInvalidUnionDiscriminatorIssue | ZodInvalidEnumValueIssue | ZodInvalidArgumentsIssue | ZodInvalidReturnTypeIssue | ZodInvalidDateIssue | ZodInvalidStringIssue | ZodTooSmallIssue | ZodTooBigIssue | ZodInvalidIntersectionTypesIssue | ZodNotMultipleOfIssue | ZodCustomIssue;
91
96
  export declare type ZodIssue = ZodIssueOptionalMessage & {
92
97
  message: string;
93
98
  };
package/lib/ZodError.js CHANGED
@@ -4,6 +4,7 @@ exports.setErrorMap = exports.overrideErrorMap = exports.defaultErrorMap = expor
4
4
  const util_1 = require("./helpers/util");
5
5
  exports.ZodIssueCode = util_1.util.arrayToEnum([
6
6
  "invalid_type",
7
+ "invalid_literal",
7
8
  "custom",
8
9
  "invalid_union",
9
10
  "invalid_union_discriminator",
@@ -135,6 +136,9 @@ const defaultErrorMap = (issue, _ctx) => {
135
136
  message = `Expected ${issue.expected}, received ${issue.received}`;
136
137
  }
137
138
  break;
139
+ case exports.ZodIssueCode.invalid_literal:
140
+ message = `Invalid literal value, expected ${JSON.stringify(issue.expected)}`;
141
+ break;
138
142
  case exports.ZodIssueCode.unrecognized_keys:
139
143
  message = `Unrecognized key(s) in object: ${issue.keys
140
144
  .map((k) => `'${k}'`)
@@ -17,6 +17,8 @@ const manual = (str) => {
17
17
  return str;
18
18
  };
19
19
  const stringSchema = index_1.z.string();
20
+ const optionalStringSchema = index_1.z.string().optional();
21
+ const optionalNullableStringSchema = index_1.z.string().optional().nullable();
20
22
  suite
21
23
  .add("empty string", () => {
22
24
  stringSchema.parse(empty);
@@ -26,6 +28,15 @@ suite
26
28
  })
27
29
  .add("long string", () => {
28
30
  stringSchema.parse(long);
31
+ })
32
+ .add("optional string", () => {
33
+ optionalStringSchema.parse(long);
34
+ })
35
+ .add("nullable string", () => {
36
+ optionalNullableStringSchema.parse(long);
37
+ })
38
+ .add("nullable (null) string", () => {
39
+ optionalNullableStringSchema.parse(null);
29
40
  })
30
41
  .add("invalid: null", () => {
31
42
  try {
@@ -42,7 +42,6 @@ export interface ParseContext {
42
42
  readonly issues: ZodIssue[];
43
43
  readonly contextualErrorMap?: ZodErrorMap;
44
44
  readonly async: boolean;
45
- readonly typeCache: Map<any, ZodParsedType> | undefined;
46
45
  };
47
46
  readonly path: ParsePath;
48
47
  readonly schemaErrorMap?: ZodErrorMap;
package/lib/index.mjs CHANGED
@@ -49,6 +49,7 @@ var util;
49
49
 
50
50
  const ZodIssueCode = util.arrayToEnum([
51
51
  "invalid_type",
52
+ "invalid_literal",
52
53
  "custom",
53
54
  "invalid_union",
54
55
  "invalid_union_discriminator",
@@ -178,6 +179,9 @@ const defaultErrorMap = (issue, _ctx) => {
178
179
  message = `Expected ${issue.expected}, received ${issue.received}`;
179
180
  }
180
181
  break;
182
+ case ZodIssueCode.invalid_literal:
183
+ message = `Invalid literal value, expected ${JSON.stringify(issue.expected)}`;
184
+ break;
181
185
  case ZodIssueCode.unrecognized_keys:
182
186
  message = `Unrecognized key(s) in object: ${issue.keys
183
187
  .map((k) => `'${k}'`)
@@ -419,6 +423,17 @@ var errorUtil;
419
423
  errorUtil.toString = (message) => typeof message === "string" ? message : message === null || message === void 0 ? void 0 : message.message;
420
424
  })(errorUtil || (errorUtil = {}));
421
425
 
426
+ class ParseInputLazyPath {
427
+ constructor(parent, value, path, key) {
428
+ this.parent = parent;
429
+ this.data = value;
430
+ this._path = path;
431
+ this._key = key;
432
+ }
433
+ get path() {
434
+ return this._path.concat(this._key);
435
+ }
436
+ }
422
437
  const handleResult = (ctx, result) => {
423
438
  if (isValid(result)) {
424
439
  return { success: true, data: result.value };
@@ -475,8 +490,8 @@ class ZodType {
475
490
  this.transform = this.transform.bind(this);
476
491
  this.default = this.default.bind(this);
477
492
  this.describe = this.describe.bind(this);
478
- this.isOptional = this.isOptional.bind(this);
479
493
  this.isNullable = this.isNullable.bind(this);
494
+ this.isOptional = this.isOptional.bind(this);
480
495
  }
481
496
  get description() {
482
497
  return this._def.description;
@@ -530,7 +545,6 @@ class ZodType {
530
545
  common: {
531
546
  issues: [],
532
547
  async: (_a = params === null || params === void 0 ? void 0 : params.async) !== null && _a !== void 0 ? _a : false,
533
- typeCache: typeof Map !== "undefined" ? new Map() : undefined,
534
548
  contextualErrorMap: params === null || params === void 0 ? void 0 : params.errorMap,
535
549
  },
536
550
  path: (params === null || params === void 0 ? void 0 : params.path) || [],
@@ -554,7 +568,6 @@ class ZodType {
554
568
  issues: [],
555
569
  contextualErrorMap: params === null || params === void 0 ? void 0 : params.errorMap,
556
570
  async: true,
557
- typeCache: typeof Map !== "undefined" ? new Map() : undefined,
558
571
  },
559
572
  path: (params === null || params === void 0 ? void 0 : params.path) || [],
560
573
  schemaErrorMap: this._def.errorMap,
@@ -1308,21 +1321,13 @@ class ZodArray extends ZodType {
1308
1321
  }
1309
1322
  if (ctx.common.async) {
1310
1323
  return Promise.all(ctx.data.map((item, i) => {
1311
- return def.type._parseAsync({
1312
- parent: ctx,
1313
- path: [...ctx.path, i],
1314
- data: item,
1315
- });
1324
+ return def.type._parseAsync(new ParseInputLazyPath(ctx, item, ctx.path, i));
1316
1325
  })).then((result) => {
1317
1326
  return ParseStatus.mergeArray(status, result);
1318
1327
  });
1319
1328
  }
1320
1329
  const result = ctx.data.map((item, i) => {
1321
- return def.type._parseSync({
1322
- parent: ctx,
1323
- path: [...ctx.path, i],
1324
- data: item,
1325
- });
1330
+ return def.type._parseSync(new ParseInputLazyPath(ctx, item, ctx.path, i));
1326
1331
  });
1327
1332
  return ParseStatus.mergeArray(status, result);
1328
1333
  }
@@ -1442,19 +1447,19 @@ class ZodObject extends ZodType {
1442
1447
  }
1443
1448
  const { status, ctx } = this._processInputParams(input);
1444
1449
  const { shape, keys: shapeKeys } = this._getCached();
1445
- const dataKeys = util.objectKeys(ctx.data);
1446
- const extraKeys = dataKeys.filter((k) => !shapeKeys.includes(k));
1450
+ const extraKeys = [];
1451
+ for (const key in ctx.data) {
1452
+ if (!shapeKeys.includes(key)) {
1453
+ extraKeys.push(key);
1454
+ }
1455
+ }
1447
1456
  const pairs = [];
1448
1457
  for (const key of shapeKeys) {
1449
1458
  const keyValidator = shape[key];
1450
1459
  const value = ctx.data[key];
1451
1460
  pairs.push({
1452
1461
  key: { status: "valid", value: key },
1453
- value: keyValidator._parse({
1454
- parent: ctx,
1455
- data: value,
1456
- path: [...ctx.path, key],
1457
- }),
1462
+ value: keyValidator._parse(new ParseInputLazyPath(ctx, value, ctx.path, key)),
1458
1463
  alwaysSet: key in ctx.data,
1459
1464
  });
1460
1465
  }
@@ -1489,7 +1494,7 @@ class ZodObject extends ZodType {
1489
1494
  const value = ctx.data[key];
1490
1495
  pairs.push({
1491
1496
  key: { status: "valid", value: key },
1492
- value: catchall._parse({ parent: ctx, path: [...ctx.path, key], data: value } //, ctx.child(key), value, getParsedType(value)
1497
+ value: catchall._parse(new ParseInputLazyPath(ctx, value, ctx.path, key) //, ctx.child(key), value, getParsedType(value)
1493
1498
  ),
1494
1499
  alwaysSet: key in ctx.data,
1495
1500
  });
@@ -1985,11 +1990,7 @@ class ZodTuple extends ZodType {
1985
1990
  const schema = this._def.items[itemIndex] || this._def.rest;
1986
1991
  if (!schema)
1987
1992
  return null;
1988
- return schema._parse({
1989
- data: item,
1990
- path: [...ctx.path, itemIndex],
1991
- parent: ctx,
1992
- });
1993
+ return schema._parse(new ParseInputLazyPath(ctx, item, ctx.path, itemIndex));
1993
1994
  })
1994
1995
  .filter((x) => !!x); // filter nulls
1995
1996
  if (ctx.common.async) {
@@ -2041,16 +2042,8 @@ class ZodRecord extends ZodType {
2041
2042
  const valueType = this._def.valueType;
2042
2043
  for (const key in ctx.data) {
2043
2044
  pairs.push({
2044
- key: keyType._parse({
2045
- data: key,
2046
- path: [...ctx.path, key],
2047
- parent: ctx,
2048
- }),
2049
- value: valueType._parse({
2050
- data: ctx.data[key],
2051
- path: [...ctx.path, key],
2052
- parent: ctx,
2053
- }),
2045
+ key: keyType._parse(new ParseInputLazyPath(ctx, key, ctx.path, key)),
2046
+ value: valueType._parse(new ParseInputLazyPath(ctx, ctx.data[key], ctx.path, key)),
2054
2047
  });
2055
2048
  }
2056
2049
  if (ctx.common.async) {
@@ -2095,16 +2088,8 @@ class ZodMap extends ZodType {
2095
2088
  const valueType = this._def.valueType;
2096
2089
  const pairs = [...ctx.data.entries()].map(([key, value], index) => {
2097
2090
  return {
2098
- key: keyType._parse({
2099
- data: key,
2100
- path: [...ctx.path, index, "key"],
2101
- parent: ctx,
2102
- }),
2103
- value: valueType._parse({
2104
- data: value,
2105
- path: [...ctx.path, index, "value"],
2106
- parent: ctx,
2107
- }),
2091
+ key: keyType._parse(new ParseInputLazyPath(ctx, key, ctx.path, [index, "key"])),
2092
+ value: valueType._parse(new ParseInputLazyPath(ctx, value, ctx.path, [index, "value"])),
2108
2093
  };
2109
2094
  });
2110
2095
  if (ctx.common.async) {
@@ -2197,7 +2182,7 @@ class ZodSet extends ZodType {
2197
2182
  }
2198
2183
  return { status: status.value, value: parsedSet };
2199
2184
  }
2200
- const elements = [...ctx.data.values()].map((item, i) => valueType._parse({ data: item, path: [...ctx.path, i], parent: ctx }));
2185
+ const elements = [...ctx.data.values()].map((item, i) => valueType._parse(new ParseInputLazyPath(ctx, item, ctx.path, i)));
2201
2186
  if (ctx.common.async) {
2202
2187
  return Promise.all(elements).then((elements) => finalizeSet(elements));
2203
2188
  }
@@ -2375,9 +2360,8 @@ class ZodLiteral extends ZodType {
2375
2360
  if (input.data !== this._def.value) {
2376
2361
  const ctx = this._getOrReturnCtx(input);
2377
2362
  addIssueToContext(ctx, {
2378
- code: ZodIssueCode.invalid_type,
2379
- expected: getParsedType(this._def.value),
2380
- received: ctx.parsedType,
2363
+ code: ZodIssueCode.invalid_literal,
2364
+ expected: this._def.value,
2381
2365
  });
2382
2366
  return INVALID;
2383
2367
  }
@@ -2632,12 +2616,7 @@ class ZodOptional extends ZodType {
2632
2616
  if (parsedType === ZodParsedType.undefined) {
2633
2617
  return OK(undefined);
2634
2618
  }
2635
- const { ctx } = this._processInputParams(input);
2636
- return this._def.innerType._parse({
2637
- data: ctx.data,
2638
- path: ctx.path,
2639
- parent: ctx,
2640
- });
2619
+ return this._def.innerType._parse(input);
2641
2620
  }
2642
2621
  unwrap() {
2643
2622
  return this._def.innerType;
@@ -2656,12 +2635,7 @@ class ZodNullable extends ZodType {
2656
2635
  if (parsedType === ZodParsedType.null) {
2657
2636
  return OK(null);
2658
2637
  }
2659
- const { ctx } = this._processInputParams(input);
2660
- return this._def.innerType._parse({
2661
- data: ctx.data,
2662
- path: ctx.path,
2663
- parent: ctx,
2664
- });
2638
+ return this._def.innerType._parse(input);
2665
2639
  }
2666
2640
  unwrap() {
2667
2641
  return this._def.innerType;
package/lib/types.d.ts CHANGED
@@ -44,7 +44,7 @@ export declare type SafeParseError<Input> = {
44
44
  error: ZodError<Input>;
45
45
  };
46
46
  export declare type SafeParseReturnType<Input, Output> = SafeParseSuccess<Output> | SafeParseError<Input>;
47
- export declare abstract class ZodType<Output, Def extends ZodTypeDef = ZodTypeDef, Input = Output> {
47
+ export declare abstract class ZodType<Output = any, Def extends ZodTypeDef = ZodTypeDef, Input = Output> {
48
48
  readonly _type: Output;
49
49
  readonly _output: Output;
50
50
  readonly _input: Input;
@@ -65,10 +65,6 @@ export declare abstract class ZodType<Output, Def extends ZodTypeDef = ZodTypeDe
65
65
  safeParseAsync(data: unknown, params?: Partial<ParseParams>): Promise<SafeParseReturnType<Input, Output>>;
66
66
  /** Alias of safeParseAsync */
67
67
  spa: (data: unknown, params?: Partial<ParseParams> | undefined) => Promise<SafeParseReturnType<Input, Output>>;
68
- /** The .is method has been removed in Zod 3. For details see https://github.com/colinhacks/zod/tree/v3. */
69
- is: never;
70
- /** The .check method has been removed in Zod 3. For details see https://github.com/colinhacks/zod/tree/v3. */
71
- check: never;
72
68
  refine<RefinedOutput extends Output>(check: (arg: Output) => arg is RefinedOutput, message?: string | CustomErrorParams | ((arg: Output) => CustomErrorParams)): ZodEffects<this, RefinedOutput, RefinedOutput>;
73
69
  refine(check: (arg: Output) => unknown | Promise<unknown>, message?: string | CustomErrorParams | ((arg: Output) => CustomErrorParams)): ZodEffects<this, Output, Input>;
74
70
  refinement<RefinedOutput extends Output>(check: (arg: Output) => arg is RefinedOutput, refinementData: IssueData | ((arg: Output, ctx: RefinementCtx) => IssueData)): ZodEffects<this, RefinedOutput, RefinedOutput>;
@@ -441,7 +437,7 @@ export declare class ZodIntersection<T extends ZodTypeAny, U extends ZodTypeAny>
441
437
  static create: <T_1 extends ZodTypeAny, U_1 extends ZodTypeAny>(left: T_1, right: U_1, params?: RawCreateParams) => ZodIntersection<T_1, U_1>;
442
438
  }
443
439
  export declare type ZodTupleItems = [ZodTypeAny, ...ZodTypeAny[]];
444
- export declare type AssertArray<T extends any> = T extends any[] ? T : never;
440
+ export declare type AssertArray<T> = T extends any[] ? T : never;
445
441
  export declare type OutputTypeOfTuple<T extends ZodTupleItems | []> = AssertArray<{
446
442
  [k in keyof T]: T[k] extends ZodType<any, any> ? T[k]["_output"] : never;
447
443
  }>;
@@ -532,11 +528,11 @@ export declare class ZodLazy<T extends ZodTypeAny> extends ZodType<output<T>, Zo
532
528
  _parse(input: ParseInput): ParseReturnType<this["_output"]>;
533
529
  static create: <T_1 extends ZodTypeAny>(getter: () => T_1, params?: RawCreateParams) => ZodLazy<T_1>;
534
530
  }
535
- export interface ZodLiteralDef<T extends any = any> extends ZodTypeDef {
531
+ export interface ZodLiteralDef<T = any> extends ZodTypeDef {
536
532
  value: T;
537
533
  typeName: ZodFirstPartyTypeKind.ZodLiteral;
538
534
  }
539
- export declare class ZodLiteral<T extends any> extends ZodType<T, ZodLiteralDef<T>> {
535
+ export declare class ZodLiteral<T> extends ZodType<T, ZodLiteralDef<T>> {
540
536
  _parse(input: ParseInput): ParseReturnType<this["_output"]>;
541
537
  get value(): T;
542
538
  static create: <T_1 extends Primitive>(value: T_1, params?: RawCreateParams) => ZodLiteral<T_1>;
package/lib/types.js CHANGED
@@ -6,6 +6,17 @@ const errorUtil_1 = require("./helpers/errorUtil");
6
6
  const parseUtil_1 = require("./helpers/parseUtil");
7
7
  const util_1 = require("./helpers/util");
8
8
  const ZodError_1 = require("./ZodError");
9
+ class ParseInputLazyPath {
10
+ constructor(parent, value, path, key) {
11
+ this.parent = parent;
12
+ this.data = value;
13
+ this._path = path;
14
+ this._key = key;
15
+ }
16
+ get path() {
17
+ return this._path.concat(this._key);
18
+ }
19
+ }
9
20
  const handleResult = (ctx, result) => {
10
21
  if ((0, parseUtil_1.isValid)(result)) {
11
22
  return { success: true, data: result.value };
@@ -62,8 +73,8 @@ class ZodType {
62
73
  this.transform = this.transform.bind(this);
63
74
  this.default = this.default.bind(this);
64
75
  this.describe = this.describe.bind(this);
65
- this.isOptional = this.isOptional.bind(this);
66
76
  this.isNullable = this.isNullable.bind(this);
77
+ this.isOptional = this.isOptional.bind(this);
67
78
  }
68
79
  get description() {
69
80
  return this._def.description;
@@ -117,7 +128,6 @@ class ZodType {
117
128
  common: {
118
129
  issues: [],
119
130
  async: (_a = params === null || params === void 0 ? void 0 : params.async) !== null && _a !== void 0 ? _a : false,
120
- typeCache: typeof Map !== "undefined" ? new Map() : undefined,
121
131
  contextualErrorMap: params === null || params === void 0 ? void 0 : params.errorMap,
122
132
  },
123
133
  path: (params === null || params === void 0 ? void 0 : params.path) || [],
@@ -141,7 +151,6 @@ class ZodType {
141
151
  issues: [],
142
152
  contextualErrorMap: params === null || params === void 0 ? void 0 : params.errorMap,
143
153
  async: true,
144
- typeCache: typeof Map !== "undefined" ? new Map() : undefined,
145
154
  },
146
155
  path: (params === null || params === void 0 ? void 0 : params.path) || [],
147
156
  schemaErrorMap: this._def.errorMap,
@@ -214,6 +223,8 @@ class ZodType {
214
223
  });
215
224
  }
216
225
  optional() {
226
+ ("");
227
+ ("asdf");
217
228
  return ZodOptional.create(this);
218
229
  }
219
230
  nullable() {
@@ -909,21 +920,13 @@ class ZodArray extends ZodType {
909
920
  }
910
921
  if (ctx.common.async) {
911
922
  return Promise.all(ctx.data.map((item, i) => {
912
- return def.type._parseAsync({
913
- parent: ctx,
914
- path: [...ctx.path, i],
915
- data: item,
916
- });
923
+ return def.type._parseAsync(new ParseInputLazyPath(ctx, item, ctx.path, i));
917
924
  })).then((result) => {
918
925
  return parseUtil_1.ParseStatus.mergeArray(status, result);
919
926
  });
920
927
  }
921
928
  const result = ctx.data.map((item, i) => {
922
- return def.type._parseSync({
923
- parent: ctx,
924
- path: [...ctx.path, i],
925
- data: item,
926
- });
929
+ return def.type._parseSync(new ParseInputLazyPath(ctx, item, ctx.path, i));
927
930
  });
928
931
  return parseUtil_1.ParseStatus.mergeArray(status, result);
929
932
  }
@@ -1044,19 +1047,19 @@ class ZodObject extends ZodType {
1044
1047
  }
1045
1048
  const { status, ctx } = this._processInputParams(input);
1046
1049
  const { shape, keys: shapeKeys } = this._getCached();
1047
- const dataKeys = util_1.util.objectKeys(ctx.data);
1048
- const extraKeys = dataKeys.filter((k) => !shapeKeys.includes(k));
1050
+ const extraKeys = [];
1051
+ for (const key in ctx.data) {
1052
+ if (!shapeKeys.includes(key)) {
1053
+ extraKeys.push(key);
1054
+ }
1055
+ }
1049
1056
  const pairs = [];
1050
1057
  for (const key of shapeKeys) {
1051
1058
  const keyValidator = shape[key];
1052
1059
  const value = ctx.data[key];
1053
1060
  pairs.push({
1054
1061
  key: { status: "valid", value: key },
1055
- value: keyValidator._parse({
1056
- parent: ctx,
1057
- data: value,
1058
- path: [...ctx.path, key],
1059
- }),
1062
+ value: keyValidator._parse(new ParseInputLazyPath(ctx, value, ctx.path, key)),
1060
1063
  alwaysSet: key in ctx.data,
1061
1064
  });
1062
1065
  }
@@ -1092,7 +1095,7 @@ class ZodObject extends ZodType {
1092
1095
  const value = ctx.data[key];
1093
1096
  pairs.push({
1094
1097
  key: { status: "valid", value: key },
1095
- value: catchall._parse({ parent: ctx, path: [...ctx.path, key], data: value } //, ctx.child(key), value, getParsedType(value)
1098
+ value: catchall._parse(new ParseInputLazyPath(ctx, value, ctx.path, key) //, ctx.child(key), value, getParsedType(value)
1096
1099
  ),
1097
1100
  alwaysSet: key in ctx.data,
1098
1101
  });
@@ -1592,11 +1595,7 @@ class ZodTuple extends ZodType {
1592
1595
  const schema = this._def.items[itemIndex] || this._def.rest;
1593
1596
  if (!schema)
1594
1597
  return null;
1595
- return schema._parse({
1596
- data: item,
1597
- path: [...ctx.path, itemIndex],
1598
- parent: ctx,
1599
- });
1598
+ return schema._parse(new ParseInputLazyPath(ctx, item, ctx.path, itemIndex));
1600
1599
  })
1601
1600
  .filter((x) => !!x); // filter nulls
1602
1601
  if (ctx.common.async) {
@@ -1649,16 +1648,8 @@ class ZodRecord extends ZodType {
1649
1648
  const valueType = this._def.valueType;
1650
1649
  for (const key in ctx.data) {
1651
1650
  pairs.push({
1652
- key: keyType._parse({
1653
- data: key,
1654
- path: [...ctx.path, key],
1655
- parent: ctx,
1656
- }),
1657
- value: valueType._parse({
1658
- data: ctx.data[key],
1659
- path: [...ctx.path, key],
1660
- parent: ctx,
1661
- }),
1651
+ key: keyType._parse(new ParseInputLazyPath(ctx, key, ctx.path, key)),
1652
+ value: valueType._parse(new ParseInputLazyPath(ctx, ctx.data[key], ctx.path, key)),
1662
1653
  });
1663
1654
  }
1664
1655
  if (ctx.common.async) {
@@ -1704,16 +1695,8 @@ class ZodMap extends ZodType {
1704
1695
  const valueType = this._def.valueType;
1705
1696
  const pairs = [...ctx.data.entries()].map(([key, value], index) => {
1706
1697
  return {
1707
- key: keyType._parse({
1708
- data: key,
1709
- path: [...ctx.path, index, "key"],
1710
- parent: ctx,
1711
- }),
1712
- value: valueType._parse({
1713
- data: value,
1714
- path: [...ctx.path, index, "value"],
1715
- parent: ctx,
1716
- }),
1698
+ key: keyType._parse(new ParseInputLazyPath(ctx, key, ctx.path, [index, "key"])),
1699
+ value: valueType._parse(new ParseInputLazyPath(ctx, value, ctx.path, [index, "value"])),
1717
1700
  };
1718
1701
  });
1719
1702
  if (ctx.common.async) {
@@ -1807,7 +1790,7 @@ class ZodSet extends ZodType {
1807
1790
  }
1808
1791
  return { status: status.value, value: parsedSet };
1809
1792
  }
1810
- const elements = [...ctx.data.values()].map((item, i) => valueType._parse({ data: item, path: [...ctx.path, i], parent: ctx }));
1793
+ const elements = [...ctx.data.values()].map((item, i) => valueType._parse(new ParseInputLazyPath(ctx, item, ctx.path, i)));
1811
1794
  if (ctx.common.async) {
1812
1795
  return Promise.all(elements).then((elements) => finalizeSet(elements));
1813
1796
  }
@@ -1988,9 +1971,8 @@ class ZodLiteral extends ZodType {
1988
1971
  if (input.data !== this._def.value) {
1989
1972
  const ctx = this._getOrReturnCtx(input);
1990
1973
  (0, parseUtil_1.addIssueToContext)(ctx, {
1991
- code: ZodError_1.ZodIssueCode.invalid_type,
1992
- expected: (0, parseUtil_1.getParsedType)(this._def.value),
1993
- received: ctx.parsedType,
1974
+ code: ZodError_1.ZodIssueCode.invalid_literal,
1975
+ expected: this._def.value,
1994
1976
  });
1995
1977
  return parseUtil_1.INVALID;
1996
1978
  }
@@ -2251,12 +2233,7 @@ class ZodOptional extends ZodType {
2251
2233
  if (parsedType === parseUtil_1.ZodParsedType.undefined) {
2252
2234
  return (0, parseUtil_1.OK)(undefined);
2253
2235
  }
2254
- const { ctx } = this._processInputParams(input);
2255
- return this._def.innerType._parse({
2256
- data: ctx.data,
2257
- path: ctx.path,
2258
- parent: ctx,
2259
- });
2236
+ return this._def.innerType._parse(input);
2260
2237
  }
2261
2238
  unwrap() {
2262
2239
  return this._def.innerType;
@@ -2276,12 +2253,7 @@ class ZodNullable extends ZodType {
2276
2253
  if (parsedType === parseUtil_1.ZodParsedType.null) {
2277
2254
  return (0, parseUtil_1.OK)(null);
2278
2255
  }
2279
- const { ctx } = this._processInputParams(input);
2280
- return this._def.innerType._parse({
2281
- data: ctx.data,
2282
- path: ctx.path,
2283
- parent: ctx,
2284
- });
2256
+ return this._def.innerType._parse(input);
2285
2257
  }
2286
2258
  unwrap() {
2287
2259
  return this._def.innerType;
package/package.json CHANGED
@@ -1,10 +1,11 @@
1
1
  {
2
2
  "name": "zod",
3
- "version": "3.14.1",
3
+ "version": "3.14.4",
4
4
  "description": "TypeScript-first schema declaration and validation library with static type inference",
5
5
  "main": "./lib/index.js",
6
6
  "types": "./lib/index.d.ts",
7
7
  "module": "./lib/index.mjs",
8
+ "dependencies": {},
8
9
  "exports": {
9
10
  ".": {
10
11
  "require": "./lib/index.js",
@@ -41,12 +42,12 @@
41
42
  "inference"
42
43
  ],
43
44
  "scripts": {
44
- "check:format": "prettier --check \"src/**/*.ts\" \"deno/lib/**/*.ts\"",
45
- "fix:format": "prettier --write \"src/**/*.ts\" \"deno/lib/**/*.ts\"",
46
- "check:lint": "eslint --ext .ts ./src",
47
- "fix:lint": "eslint --fix --ext .ts ./src",
48
- "check": "yarn check:lint && yarn check:format",
49
- "fix": "yarn fix:lint && yarn fix:format",
45
+ "prettier:check": "prettier --check src/**/*.ts deno/lib/**/*.ts --no-error-on-unmatched-pattern",
46
+ "prettier:fix": "prettier --write src/**/*.ts deno/lib/**/*.ts --ignore-unknown --no-error-on-unmatched-pattern",
47
+ "lint:check": "eslint --ext .ts ./src",
48
+ "lint:fix": "eslint --fix --ext .ts ./src",
49
+ "check": "yarn lint:check && yarn prettier:check",
50
+ "fix": "yarn lint:fix && yarn prettier:fix",
50
51
  "clean": "rm -rf lib/* deno/lib/*",
51
52
  "build": "yarn run clean && npm run build:cjs && npm run build:esm && npm run build:deno",
52
53
  "build:deno": "node ./deno/build.mjs",
@@ -56,51 +57,43 @@
56
57
  "rollup": "rollup --config rollup.config.js",
57
58
  "test": "jest --coverage",
58
59
  "test:deno": "cd deno && deno test",
59
- "badge": "make-coverage-badge --output-path ./coverage.svg",
60
60
  "prepublishOnly": "npm run test && npm run build && npm run build:deno",
61
61
  "play": "nodemon -e ts -w . -x ts-node src/playground.ts --project tsconfig.json --trace-warnings",
62
62
  "depcruise": "depcruise -c .dependency-cruiser.js src",
63
- "benchmark": "ts-node src/benchmarks/index.ts"
63
+ "benchmark": "ts-node src/benchmarks/index.ts",
64
+ "prepare": "husky install"
64
65
  },
65
66
  "devDependencies": {
66
67
  "@rollup/plugin-typescript": "^8.2.0",
67
68
  "@types/benchmark": "^2.1.0",
68
69
  "@types/jest": "^26.0.17",
69
- "@types/node": "^14.14.10",
70
- "@typescript-eslint/eslint-plugin": "^4.11.1",
71
- "@typescript-eslint/parser": "^4.11.1",
70
+ "@types/node": "14",
71
+ "@typescript-eslint/eslint-plugin": "^5.15.0",
72
+ "@typescript-eslint/parser": "^5.15.0",
72
73
  "benchmark": "^2.1.4",
73
74
  "dependency-cruiser": "^9.19.0",
74
- "eslint": "^7.15.0",
75
- "eslint-config-prettier": "^7.1.0",
76
- "eslint-plugin-ban": "^1.5.2",
77
- "eslint-plugin-import": "^2.22.1",
75
+ "eslint": "^8.11.0",
76
+ "eslint-config-prettier": "^8.5.0",
77
+ "eslint-plugin-ban": "^1.6.0",
78
+ "eslint-plugin-import": "^2.25.4",
78
79
  "eslint-plugin-simple-import-sort": "^7.0.0",
79
- "eslint-plugin-unused-imports": "^1.1.0",
80
- "husky": "^4.3.4",
81
- "jest": "^26.6.3",
82
- "lint-staged": "^10.5.3",
83
- "make-coverage-badge": "^1.2.0",
84
- "nodemon": "^2.0.2",
85
- "prettier": "^2.2.1",
86
- "rollup": "^2.42.1",
87
- "rollup-plugin-uglify": "^6.0.4",
88
- "table": "^6.8.0",
89
- "ts-jest": "^26.4.4",
90
- "ts-node": "^9.1.0",
80
+ "eslint-plugin-unused-imports": "^2.0.0",
81
+ "husky": "^7.0.4",
82
+ "jest": "^27.5.1",
83
+ "lint-staged": "^12.3.7",
84
+ "nodemon": "^2.0.15",
85
+ "prettier": "^2.6.0",
86
+ "pretty-quick": "^3.1.3",
87
+ "rollup": "^2.70.1",
88
+ "ts-jest": "^27.1.3",
89
+ "ts-node": "^10.7.0",
91
90
  "tslib": "^2.3.1",
92
- "typescript": "^4.5.2"
93
- },
94
- "husky": {
95
- "hooks": {
96
- "pre-commit": "lint-staged && yarn build:deno && git add .",
97
- "pre-push": "lint-staged && yarn build && yarn test && yarn badge"
98
- }
91
+ "typescript": "^4.6.2"
99
92
  },
100
93
  "lint-staged": {
101
- "*.ts": [
102
- "yarn fix:lint",
103
- "yarn fix:format"
94
+ "src/*.ts": [
95
+ "eslint --cache --fix",
96
+ "prettier --ignore-unknown --write"
104
97
  ]
105
98
  }
106
99
  }