z-schema 12.2.0 → 12.3.1

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.
Files changed (110) hide show
  1. package/README.md +2 -2
  2. package/bin/z-schema +1 -1
  3. package/cjs/{index.js → index.cjs} +696 -687
  4. package/cjs/{index.d.ts → index.d.cts} +47 -26
  5. package/dist/{errors.d.mts → errors.d.ts} +2 -2
  6. package/dist/{errors.mjs → errors.js} +1 -2
  7. package/dist/{format-validators.mjs → format-validators.js} +43 -36
  8. package/dist/{index.d.mts → index.d.ts} +9 -9
  9. package/dist/{index.mjs → index.js} +3 -3
  10. package/dist/{json-schema-versions.d.mts → json-schema-versions.d.ts} +34 -3
  11. package/dist/{json-schema.d.mts → json-schema.d.ts} +7 -7
  12. package/dist/{json-schema.mjs → json-schema.js} +7 -12
  13. package/dist/{json-validation.mjs → json-validation.js} +143 -127
  14. package/dist/{report.d.mts → report.d.ts} +7 -8
  15. package/dist/{report.mjs → report.js} +28 -31
  16. package/dist/{schema-cache.d.mts → schema-cache.d.ts} +4 -4
  17. package/dist/{schema-cache.mjs → schema-cache.js} +10 -11
  18. package/dist/{schema-compiler.d.mts → schema-compiler.d.ts} +4 -4
  19. package/dist/{schema-compiler.mjs → schema-compiler.js} +95 -77
  20. package/dist/{schema-validator.d.mts → schema-validator.d.ts} +5 -5
  21. package/dist/{schema-validator.mjs → schema-validator.js} +138 -166
  22. package/dist/utils/{array.mjs → array.js} +4 -3
  23. package/dist/utils/{base64.mjs → base64.js} +3 -2
  24. package/dist/utils/{clone.mjs → clone.js} +18 -20
  25. package/dist/utils/{hostname.mjs → hostname.js} +19 -22
  26. package/dist/utils/{json.mjs → json.js} +11 -7
  27. package/dist/utils/{schema-regex.mjs → schema-regex.js} +5 -5
  28. package/dist/utils/{time.mjs → time.js} +5 -5
  29. package/dist/utils/unicode.js +22 -0
  30. package/dist/utils/{what-is.mjs → what-is.js} +1 -2
  31. package/dist/validation/{array.mjs → array.js} +18 -20
  32. package/dist/validation/{combinators.mjs → combinators.js} +16 -16
  33. package/dist/validation/{numeric.mjs → numeric.js} +11 -11
  34. package/dist/validation/{object.mjs → object.js} +35 -34
  35. package/dist/validation/{ref.mjs → ref.js} +4 -4
  36. package/dist/validation/{shared.mjs → shared.js} +12 -11
  37. package/dist/validation/{string.mjs → string.js} +32 -32
  38. package/dist/validation/type.js +34 -0
  39. package/dist/{z-schema-base.d.mts → z-schema-base.d.ts} +11 -12
  40. package/dist/{z-schema-base.mjs → z-schema-base.js} +45 -40
  41. package/dist/{z-schema-options.d.mts → z-schema-options.d.ts} +3 -3
  42. package/dist/{z-schema-options.mjs → z-schema-options.js} +4 -4
  43. package/dist/{z-schema-reader.d.mts → z-schema-reader.d.ts} +1 -1
  44. package/dist/{z-schema-versions.mjs → z-schema-versions.js} +21 -21
  45. package/dist/{z-schema.d.mts → z-schema.d.ts} +5 -13
  46. package/dist/{z-schema.mjs → z-schema.js} +37 -47
  47. package/package.json +22 -23
  48. package/src/errors.ts +1 -2
  49. package/src/format-validators.ts +139 -59
  50. package/src/json-schema-versions.ts +56 -2
  51. package/src/json-schema.ts +10 -9
  52. package/src/json-validation.ts +189 -146
  53. package/src/report.ts +37 -49
  54. package/src/schema-cache.ts +13 -13
  55. package/src/schema-compiler.ts +170 -117
  56. package/src/schema-validator.ts +239 -238
  57. package/src/utils/array.ts +9 -6
  58. package/src/utils/base64.ts +13 -2
  59. package/src/utils/clone.ts +28 -30
  60. package/src/utils/date.ts +6 -3
  61. package/src/utils/hostname.ts +27 -27
  62. package/src/utils/json.ts +16 -9
  63. package/src/utils/properties.ts +2 -2
  64. package/src/utils/schema-regex.ts +4 -4
  65. package/src/utils/time.ts +5 -5
  66. package/src/utils/unicode.ts +12 -5
  67. package/src/utils/what-is.ts +1 -5
  68. package/src/validation/array.ts +24 -22
  69. package/src/validation/combinators.ts +14 -14
  70. package/src/validation/numeric.ts +14 -28
  71. package/src/validation/object.ts +32 -36
  72. package/src/validation/ref.ts +5 -6
  73. package/src/validation/shared.ts +22 -21
  74. package/src/validation/string.ts +29 -39
  75. package/src/validation/type.ts +17 -17
  76. package/src/z-schema-base.ts +49 -38
  77. package/src/z-schema-options.ts +4 -3
  78. package/src/z-schema.ts +35 -45
  79. package/umd/ZSchema.js +711 -695
  80. package/umd/ZSchema.min.js +2 -2
  81. package/umd/package.json +3 -0
  82. package/dist/utils/unicode.mjs +0 -12
  83. package/dist/validation/type.mjs +0 -32
  84. /package/dist/{format-validators.d.mts → format-validators.d.ts} +0 -0
  85. /package/dist/{json-schema-versions.mjs → json-schema-versions.js} +0 -0
  86. /package/dist/schemas/{draft-04-schema.mjs → draft-04-schema.js} +0 -0
  87. /package/dist/schemas/{draft-06-schema.mjs → draft-06-schema.js} +0 -0
  88. /package/dist/schemas/{draft-07-schema.mjs → draft-07-schema.js} +0 -0
  89. /package/dist/schemas/{draft-2019-09-meta-applicator.mjs → draft-2019-09-meta-applicator.js} +0 -0
  90. /package/dist/schemas/{draft-2019-09-meta-content.mjs → draft-2019-09-meta-content.js} +0 -0
  91. /package/dist/schemas/{draft-2019-09-meta-core.mjs → draft-2019-09-meta-core.js} +0 -0
  92. /package/dist/schemas/{draft-2019-09-meta-format.mjs → draft-2019-09-meta-format.js} +0 -0
  93. /package/dist/schemas/{draft-2019-09-meta-meta-data.mjs → draft-2019-09-meta-meta-data.js} +0 -0
  94. /package/dist/schemas/{draft-2019-09-meta-validation.mjs → draft-2019-09-meta-validation.js} +0 -0
  95. /package/dist/schemas/{draft-2019-09-schema.mjs → draft-2019-09-schema.js} +0 -0
  96. /package/dist/schemas/{draft-2020-12-meta-applicator.mjs → draft-2020-12-meta-applicator.js} +0 -0
  97. /package/dist/schemas/{draft-2020-12-meta-content.mjs → draft-2020-12-meta-content.js} +0 -0
  98. /package/dist/schemas/{draft-2020-12-meta-core.mjs → draft-2020-12-meta-core.js} +0 -0
  99. /package/dist/schemas/{draft-2020-12-meta-format-annotation.mjs → draft-2020-12-meta-format-annotation.js} +0 -0
  100. /package/dist/schemas/{draft-2020-12-meta-format-assertion.mjs → draft-2020-12-meta-format-assertion.js} +0 -0
  101. /package/dist/schemas/{draft-2020-12-meta-meta-data.mjs → draft-2020-12-meta-meta-data.js} +0 -0
  102. /package/dist/schemas/{draft-2020-12-meta-unevaluated.mjs → draft-2020-12-meta-unevaluated.js} +0 -0
  103. /package/dist/schemas/{draft-2020-12-meta-validation.mjs → draft-2020-12-meta-validation.js} +0 -0
  104. /package/dist/schemas/{draft-2020-12-schema.mjs → draft-2020-12-schema.js} +0 -0
  105. /package/dist/utils/{constants.mjs → constants.js} +0 -0
  106. /package/dist/utils/{date.mjs → date.js} +0 -0
  107. /package/dist/utils/{properties.mjs → properties.js} +0 -0
  108. /package/dist/utils/{symbols.mjs → symbols.js} +0 -0
  109. /package/dist/utils/{uri.mjs → uri.js} +0 -0
  110. /package/dist/{z-schema-reader.mjs → z-schema-reader.js} +0 -0
@@ -1,20 +1,20 @@
1
- import { isObject, whatIs } from "./utils/what-is.mjs";
2
- import { getId } from "./json-schema.mjs";
3
- import { Report } from "./report.mjs";
4
- import { compileSchemaRegex } from "./utils/schema-regex.mjs";
5
- import { VALIDATION_VOCAB_KEYWORDS, getCachedValidationResult, isValidationVocabularyEnabled } from "./validation/shared.mjs";
6
- import { additionalItemsValidator, containsValidator, itemsValidator, maxContainsValidator, maxItemsValidator, minContainsValidator, minItemsValidator, prefixItemsValidator, uniqueItemsValidator } from "./validation/array.mjs";
7
- import { allOfValidator, anyOfValidator, elseValidator, ifValidator, notValidator, oneOfValidator, thenValidator } from "./validation/combinators.mjs";
8
- import { exclusiveMaximumValidator, exclusiveMinimumValidator, maximumValidator, minimumValidator, multipleOfValidator } from "./validation/numeric.mjs";
9
- import { additionalPropertiesValidator, dependenciesValidator, dependentRequiredValidator, dependentSchemasValidator, maxPropertiesValidator, minPropertiesValidator, patternPropertiesValidator, propertiesValidator, propertyNamesValidator, requiredValidator } from "./validation/object.mjs";
10
- import { resolveDynamicRef, resolveRecursiveRef } from "./validation/ref.mjs";
11
- import { contentEncodingValidator, contentMediaTypeValidator, formatValidator, maxLengthValidator, minLengthValidator, patternValidator } from "./validation/string.mjs";
12
- import { constValidator, enumValidator, typeValidator } from "./validation/type.mjs";
1
+ import { isObject, whatIs } from "./utils/what-is.js";
2
+ import { getId } from "./json-schema.js";
3
+ import { Report } from "./report.js";
4
+ import { compileSchemaRegex } from "./utils/schema-regex.js";
5
+ import { VALIDATION_VOCAB_KEYWORDS, getCachedValidationResult, isValidationVocabularyEnabled } from "./validation/shared.js";
6
+ import { additionalItemsValidator, containsValidator, itemsValidator, maxContainsValidator, maxItemsValidator, minContainsValidator, minItemsValidator, prefixItemsValidator, uniqueItemsValidator } from "./validation/array.js";
7
+ import { allOfValidator, anyOfValidator, elseValidator, ifValidator, notValidator, oneOfValidator, thenValidator } from "./validation/combinators.js";
8
+ import { exclusiveMaximumValidator, exclusiveMinimumValidator, maximumValidator, minimumValidator, multipleOfValidator } from "./validation/numeric.js";
9
+ import { additionalPropertiesValidator, dependenciesValidator, dependentRequiredValidator, dependentSchemasValidator, maxPropertiesValidator, minPropertiesValidator, patternPropertiesValidator, propertiesValidator, propertyNamesValidator, requiredValidator } from "./validation/object.js";
10
+ import { resolveDynamicRef, resolveRecursiveRef } from "./validation/ref.js";
11
+ import { contentEncodingValidator, contentMediaTypeValidator, formatValidator, maxLengthValidator, minLengthValidator, patternValidator } from "./validation/string.js";
12
+ import { constValidator, enumValidator, typeValidator } from "./validation/type.js";
13
13
  //#region src/json-validation.ts
14
- function collectEvaluated(args) {
14
+ function collectEvaluated(ctx, args) {
15
15
  const { report, currentSchema, json, mode, depth } = args;
16
16
  if (!currentSchema || typeof currentSchema === "boolean") return /* @__PURE__ */ new Set();
17
- if (depth > (this.options.maxRecursionDepth ?? 100)) {
17
+ if (depth > (ctx.options.maxRecursionDepth ?? 100)) {
18
18
  report.addError("COLLECT_EVALUATED_DEPTH_EXCEEDED", [depth]);
19
19
  return /* @__PURE__ */ new Set();
20
20
  }
@@ -25,7 +25,7 @@ function collectEvaluated(args) {
25
25
  return false;
26
26
  };
27
27
  const recurse = (subSchema) => {
28
- if (mode === "items") return collectEvaluated.call(this, {
28
+ if (mode === "items") return collectEvaluated(ctx, {
29
29
  report,
30
30
  currentSchema: subSchema,
31
31
  json,
@@ -33,7 +33,7 @@ function collectEvaluated(args) {
33
33
  jsonArr: args.jsonArr,
34
34
  depth: depth + 1
35
35
  });
36
- return collectEvaluated.call(this, {
36
+ return collectEvaluated(ctx, {
37
37
  report,
38
38
  currentSchema: subSchema,
39
39
  json,
@@ -43,7 +43,7 @@ function collectEvaluated(args) {
43
43
  });
44
44
  };
45
45
  if (mode === "items") {
46
- const jsonArr = args.jsonArr;
46
+ const { jsonArr } = args;
47
47
  if (Array.isArray(currentSchema.prefixItems)) {
48
48
  const len = Math.min(currentSchema.prefixItems.length, jsonArr.length);
49
49
  for (let i = 0; i < len; i++) evaluated.add(i);
@@ -59,104 +59,102 @@ function collectEvaluated(args) {
59
59
  let passed = getCachedValidationResult(report, currentSchema.contains, jsonArr[i]);
60
60
  if (passed === void 0) {
61
61
  const subReport = new Report(report);
62
- validate.call(this, subReport, currentSchema.contains, jsonArr[i]);
62
+ validate(ctx, subReport, currentSchema.contains, jsonArr[i]);
63
63
  passed = subReport.errors.length === 0;
64
64
  }
65
65
  if (passed) evaluated.add(i);
66
66
  }
67
67
  if (currentSchema.unevaluatedItems === true) return "all";
68
68
  } else {
69
- const jsonData = args.jsonData;
69
+ const { jsonData } = args;
70
70
  if (isObject(currentSchema.properties)) {
71
- for (const key of Object.keys(currentSchema.properties)) if (Object.hasOwn(jsonData, key)) evaluated.add(key);
71
+ const propKeysCE = Object.keys(currentSchema.properties);
72
+ for (let i = 0; i < propKeysCE.length; i++) {
73
+ const key = propKeysCE[i];
74
+ if (Object.hasOwn(jsonData, key)) evaluated.add(key);
75
+ }
72
76
  }
73
77
  if (isObject(currentSchema.patternProperties)) for (const pattern of Object.keys(currentSchema.patternProperties)) {
74
78
  const result = compileSchemaRegex(pattern);
75
79
  if (result.ok) {
76
- for (const key of Object.keys(jsonData)) if (result.value.test(key)) evaluated.add(key);
80
+ const jdKeys = Object.keys(jsonData);
81
+ for (let i = 0; i < jdKeys.length; i++) if (result.value.test(jdKeys[i])) evaluated.add(jdKeys[i]);
77
82
  }
78
83
  }
79
84
  if (currentSchema.additionalProperties !== void 0) {
80
- const propKeys = isObject(currentSchema.properties) ? Object.keys(currentSchema.properties) : [];
85
+ const propKeySet = new Set(isObject(currentSchema.properties) ? Object.keys(currentSchema.properties) : []);
81
86
  const patternRegexes = [];
82
87
  if (isObject(currentSchema.patternProperties)) for (const pattern of Object.keys(currentSchema.patternProperties)) {
83
88
  const result = compileSchemaRegex(pattern);
84
89
  if (result.ok) patternRegexes.push(result.value);
85
90
  }
86
- for (const key of Object.keys(jsonData)) {
87
- if (propKeys.includes(key)) continue;
88
- if (patternRegexes.some((re) => re.test(key))) continue;
91
+ const apKeys = Object.keys(jsonData);
92
+ for (let i = 0; i < apKeys.length; i++) {
93
+ const key = apKeys[i];
94
+ if (propKeySet.has(key)) continue;
95
+ let matchedPattern = false;
96
+ for (let pi = 0; pi < patternRegexes.length; pi++) if (patternRegexes[pi].test(key)) {
97
+ matchedPattern = true;
98
+ break;
99
+ }
100
+ if (matchedPattern) continue;
89
101
  evaluated.add(key);
90
102
  }
91
103
  }
92
104
  if (isObject(currentSchema.dependentSchemas)) {
93
- for (const [depKey, depSchema] of Object.entries(currentSchema.dependentSchemas)) if (Object.hasOwn(jsonData, depKey)) {
94
- if (merge(recurse(depSchema))) return "all";
95
- }
105
+ for (const [depKey, depSchema] of Object.entries(currentSchema.dependentSchemas)) if (Object.hasOwn(jsonData, depKey) && merge(recurse(depSchema))) return "all";
96
106
  }
97
107
  if (currentSchema.unevaluatedProperties === true) return "all";
98
108
  }
99
109
  if (Array.isArray(currentSchema.allOf)) {
100
- for (const subSchema of currentSchema.allOf) if (merge(recurse(subSchema))) return "all";
110
+ for (let i = 0; i < currentSchema.allOf.length; i++) if (merge(recurse(currentSchema.allOf[i]))) return "all";
101
111
  }
102
- if (Array.isArray(currentSchema.anyOf)) for (const subSchema of currentSchema.anyOf) {
112
+ if (Array.isArray(currentSchema.anyOf)) for (let i = 0; i < currentSchema.anyOf.length; i++) {
113
+ const subSchema = currentSchema.anyOf[i];
103
114
  let passed = getCachedValidationResult(report, subSchema, json);
104
115
  if (passed === void 0) {
105
116
  const subReport = new Report(report);
106
- validate.call(this, subReport, subSchema, json);
117
+ validate(ctx, subReport, subSchema, json);
107
118
  passed = subReport.errors.length === 0;
108
119
  }
109
- if (passed) {
110
- if (merge(recurse(subSchema))) return "all";
111
- }
120
+ if (passed && merge(recurse(subSchema))) return "all";
112
121
  }
113
- if (Array.isArray(currentSchema.oneOf)) for (const subSchema of currentSchema.oneOf) {
122
+ if (Array.isArray(currentSchema.oneOf)) for (let i = 0; i < currentSchema.oneOf.length; i++) {
123
+ const subSchema = currentSchema.oneOf[i];
114
124
  let passed = getCachedValidationResult(report, subSchema, json);
115
125
  if (passed === void 0) {
116
126
  const subReport = new Report(report);
117
- validate.call(this, subReport, subSchema, json);
127
+ validate(ctx, subReport, subSchema, json);
118
128
  passed = subReport.errors.length === 0;
119
129
  }
120
- if (passed) {
121
- if (merge(recurse(subSchema))) return "all";
122
- }
130
+ if (passed && merge(recurse(subSchema))) return "all";
123
131
  }
124
132
  if (currentSchema.if !== void 0) {
125
133
  let condPassed = getCachedValidationResult(report, currentSchema.if, json);
126
134
  if (condPassed === void 0) {
127
135
  const condReport = new Report(report);
128
- validate.call(this, condReport, currentSchema.if, json);
136
+ validate(ctx, condReport, currentSchema.if, json);
129
137
  condPassed = condReport.errors.length === 0;
130
138
  }
131
139
  if (condPassed) {
132
140
  if (merge(recurse(currentSchema.if))) return "all";
133
- if (currentSchema.then !== void 0) {
134
- if (merge(recurse(currentSchema.then))) return "all";
135
- }
136
- } else if (currentSchema.else !== void 0) {
137
- if (merge(recurse(currentSchema.else))) return "all";
138
- }
139
- }
140
- if (currentSchema.__$refResolved && currentSchema.__$refResolved !== currentSchema) {
141
- if (merge(recurse(currentSchema.__$refResolved))) return "all";
141
+ if (currentSchema.then !== void 0 && merge(recurse(currentSchema.then))) return "all";
142
+ } else if (currentSchema.else !== void 0 && merge(recurse(currentSchema.else))) return "all";
142
143
  }
144
+ if (currentSchema.__$refResolved && currentSchema.__$refResolved !== currentSchema && merge(recurse(currentSchema.__$refResolved))) return "all";
143
145
  const recursiveTarget = resolveRecursiveRef(currentSchema, report.__$recursiveAnchorStack);
144
- if (recursiveTarget && recursiveTarget !== currentSchema) {
145
- if (merge(recurse(recursiveTarget))) return "all";
146
- }
146
+ if (recursiveTarget && recursiveTarget !== currentSchema && merge(recurse(recursiveTarget))) return "all";
147
147
  const dynamicTarget = resolveDynamicRef(currentSchema, report.__$dynamicScopeStack);
148
- if (dynamicTarget && dynamicTarget !== currentSchema) {
149
- if (merge(recurse(dynamicTarget))) return "all";
150
- }
148
+ if (dynamicTarget && dynamicTarget !== currentSchema && merge(recurse(dynamicTarget))) return "all";
151
149
  return evaluated;
152
150
  }
153
- function unevaluatedItemsValidator(report, schema, json) {
151
+ function unevaluatedItemsValidator(ctx, report, schema, json) {
154
152
  if (!Array.isArray(json)) return;
155
153
  if (schema.unevaluatedItems === true) return;
156
154
  const unevalSchema = schema.unevaluatedItems;
157
155
  if (unevalSchema === void 0) return;
158
156
  if (json.length === 0) return;
159
- const evaluatedItems = collectEvaluated.call(this, {
157
+ const evaluatedItems = collectEvaluated(ctx, {
160
158
  report,
161
159
  currentSchema: schema,
162
160
  json,
@@ -169,23 +167,24 @@ function unevaluatedItemsValidator(report, schema, json) {
169
167
  for (let i = 0; i < json.length; i++) if (!evaluatedItems.has(i)) unevaluatedIndices.push(i);
170
168
  if (unevaluatedIndices.length === 0) return;
171
169
  if (unevalSchema === false) report.addError("ARRAY_UNEVALUATED_ITEMS", void 0, void 0, schema, "unevaluatedItems");
172
- else for (const idx of unevaluatedIndices) {
170
+ else for (let i = 0; i < unevaluatedIndices.length; i++) {
171
+ const idx = unevaluatedIndices[i];
173
172
  const subReport = new Report(report);
174
- validate.call(this, subReport, unevalSchema, json[idx]);
173
+ validate(ctx, subReport, unevalSchema, json[idx]);
175
174
  if (subReport.errors.length > 0) {
176
175
  report.addError("ARRAY_UNEVALUATED_ITEMS", void 0, void 0, schema, "unevaluatedItems");
177
176
  break;
178
177
  }
179
178
  }
180
179
  }
181
- function unevaluatedPropertiesValidator(report, schema, json) {
180
+ function unevaluatedPropertiesValidator(ctx, report, schema, json) {
182
181
  if (!isObject(json)) return;
183
182
  if (schema.unevaluatedProperties === true) return;
184
183
  const unevalSchema = schema.unevaluatedProperties;
185
184
  if (unevalSchema === void 0) return;
186
185
  const allKeys = Object.keys(json);
187
186
  if (allKeys.length === 0) return;
188
- const evaluatedProperties = collectEvaluated.call(this, {
187
+ const evaluatedProperties = collectEvaluated(ctx, {
189
188
  report,
190
189
  currentSchema: schema,
191
190
  json,
@@ -194,32 +193,35 @@ function unevaluatedPropertiesValidator(report, schema, json) {
194
193
  depth: 0
195
194
  });
196
195
  if (evaluatedProperties === "all") return;
197
- const unevaluatedKeys = allKeys.filter((key) => !evaluatedProperties.has(key));
196
+ const unevaluatedKeys = [];
197
+ for (let i = 0; i < allKeys.length; i++) if (!evaluatedProperties.has(allKeys[i])) unevaluatedKeys.push(allKeys[i]);
198
198
  if (unevaluatedKeys.length === 0) return;
199
199
  if (unevalSchema === false) report.addError("OBJECT_UNEVALUATED_PROPERTIES", [unevaluatedKeys.join(", ")], void 0, schema, "unevaluatedProperties");
200
- else for (const key of unevaluatedKeys) {
200
+ else for (let i = 0; i < unevaluatedKeys.length; i++) {
201
+ const key = unevaluatedKeys[i];
201
202
  const subReport = new Report(report);
202
- validate.call(this, subReport, unevalSchema, json[key]);
203
+ validate(ctx, subReport, unevalSchema, json[key]);
203
204
  if (subReport.errors.length > 0) report.addError("OBJECT_UNEVALUATED_PROPERTIES", [key], void 0, schema, "unevaluatedProperties");
204
205
  }
205
206
  }
206
207
  function definitionsValidator() {}
208
+ const noopValidator = () => {};
207
209
  const JsonValidators = {
208
- id: () => {},
209
- $id: () => {},
210
- $ref: () => {},
211
- $schema: () => {},
212
- $dynamicAnchor: () => {},
213
- $dynamicRef: () => {},
214
- $anchor: () => {},
215
- $defs: () => {},
216
- $vocabulary: () => {},
217
- $recursiveAnchor: () => {},
218
- $recursiveRef: () => {},
219
- examples: () => {},
220
- title: () => {},
221
- description: () => {},
222
- default: () => {},
210
+ id: noopValidator,
211
+ $id: noopValidator,
212
+ $ref: noopValidator,
213
+ $schema: noopValidator,
214
+ $dynamicAnchor: noopValidator,
215
+ $dynamicRef: noopValidator,
216
+ $anchor: noopValidator,
217
+ $defs: noopValidator,
218
+ $vocabulary: noopValidator,
219
+ $recursiveAnchor: noopValidator,
220
+ $recursiveRef: noopValidator,
221
+ examples: noopValidator,
222
+ title: noopValidator,
223
+ description: noopValidator,
224
+ default: noopValidator,
223
225
  type: typeValidator,
224
226
  enum: enumValidator,
225
227
  const: constValidator,
@@ -264,18 +266,18 @@ const JsonValidators = {
264
266
  else: elseValidator,
265
267
  definitions: definitionsValidator
266
268
  };
267
- const recurseArray = function(report, schema, json) {
269
+ function recurseArray(ctx, report, schema, json) {
268
270
  const schemaUri = typeof schema.$schema === "string" ? schema.$schema : void 0;
269
- const prefixItems = (schemaUri === "https://json-schema.org/draft/2020-12/schema" || !schemaUri && this.options.version === "draft2020-12") && Array.isArray(schema.prefixItems) ? schema.prefixItems : void 0;
271
+ const prefixItems = (schemaUri === "https://json-schema.org/draft/2020-12/schema" || !schemaUri && ctx.options.version === "draft2020-12") && Array.isArray(schema.prefixItems) ? schema.prefixItems : void 0;
270
272
  if (prefixItems) {
271
273
  for (let idx = 0; idx < json.length; idx++) if (idx < prefixItems.length) {
272
274
  report.path.push(idx);
273
- validate.call(this, report, prefixItems[idx], json[idx]);
275
+ validate(ctx, report, prefixItems[idx], json[idx]);
274
276
  report.path.pop();
275
277
  } else if (schema.items !== void 0 && !Array.isArray(schema.items)) {
276
278
  report.path.push(idx);
277
279
  report.schemaPath.push("items");
278
- validate.call(this, report, schema.items, json[idx]);
280
+ validate(ctx, report, schema.items, json[idx]);
279
281
  report.schemaPath.pop();
280
282
  report.path.pop();
281
283
  }
@@ -284,50 +286,56 @@ const recurseArray = function(report, schema, json) {
284
286
  if (Array.isArray(schema.items)) {
285
287
  for (let idx = 0; idx < json.length; idx++) if (idx < schema.items.length) {
286
288
  report.path.push(idx);
287
- validate.call(this, report, schema.items[idx], json[idx]);
289
+ validate(ctx, report, schema.items[idx], json[idx]);
288
290
  report.path.pop();
289
291
  } else if (typeof schema.additionalItems === "object") {
290
292
  report.path.push(idx);
291
- validate.call(this, report, schema.additionalItems, json[idx]);
293
+ validate(ctx, report, schema.additionalItems, json[idx]);
292
294
  report.path.pop();
293
295
  }
294
296
  } else if (typeof schema.items === "object" || typeof schema.items === "boolean") for (let idx = 0; idx < json.length; idx++) {
295
297
  report.path.push(idx);
296
298
  report.schemaPath.push("items");
297
- validate.call(this, report, schema.items, json[idx]);
299
+ validate(ctx, report, schema.items, json[idx]);
298
300
  report.schemaPath.pop();
299
301
  report.path.pop();
300
302
  }
301
- };
302
- const recurseObject = function(report, schema, json) {
303
- let additionalProperties = schema.additionalProperties;
303
+ }
304
+ function recurseObject(ctx, report, schema, json) {
305
+ let { additionalProperties } = schema;
304
306
  if (additionalProperties === true || additionalProperties === void 0) additionalProperties = {};
305
307
  const p = schema.properties ? Object.keys(schema.properties) : [];
306
308
  const pp = schema.patternProperties ? Object.keys(schema.patternProperties) : [];
307
309
  const keys = Object.keys(json);
310
+ const ppCompiled = [];
311
+ for (let i = 0; i < pp.length; i++) {
312
+ const r = compileSchemaRegex(pp[i]);
313
+ if (r.ok) ppCompiled.push({
314
+ key: pp[i],
315
+ re: r.value
316
+ });
317
+ }
308
318
  for (const m of keys) {
309
319
  const propertyValue = json[m];
320
+ const isProp = p.includes(m);
310
321
  const s = [];
311
- if (p.includes(m)) s.push(schema.properties[m]);
312
- for (const regexString of pp) {
313
- const result = compileSchemaRegex(regexString);
314
- if (result.ok && result.value.test(m) === true) s.push(schema.patternProperties[regexString]);
315
- }
322
+ if (isProp) s.push(schema.properties[m]);
323
+ for (let i = 0; i < ppCompiled.length; i++) if (ppCompiled[i].re.test(m)) s.push(schema.patternProperties[ppCompiled[i].key]);
316
324
  if (s.length === 0 && additionalProperties !== false) s.push(additionalProperties);
317
325
  for (const schema_s of s) {
318
326
  report.path.push(m);
319
- if (p.includes(m)) {
327
+ if (isProp) {
320
328
  report.schemaPath.push("properties");
321
329
  report.schemaPath.push(m);
322
330
  } else report.schemaPath.push("additionalProperties");
323
- validate.call(this, report, schema_s, propertyValue);
331
+ validate(ctx, report, schema_s, propertyValue);
324
332
  report.path.pop();
325
333
  report.schemaPath.pop();
326
- if (p.includes(m)) report.schemaPath.pop();
334
+ if (isProp) report.schemaPath.pop();
327
335
  }
328
336
  }
329
- };
330
- function validate(report, schema, json) {
337
+ }
338
+ function validate(ctx, report, schema, json) {
331
339
  report.commonErrorMessage = "JSON_OBJECT_VALIDATION_FAILED";
332
340
  if (schema === true) return true;
333
341
  if (schema === false) {
@@ -351,7 +359,7 @@ function validate(report, schema, json) {
351
359
  let pushedDynamicScope = false;
352
360
  const schemaId = getId(schema);
353
361
  const dynamicScopeEntry = schema.__$resourceRoot || (isRoot || typeof schemaId === "string" ? schema : void 0);
354
- if (dynamicScopeEntry && dynamicScopeStack[dynamicScopeStack.length - 1] !== dynamicScopeEntry) {
362
+ if (dynamicScopeEntry && dynamicScopeStack.at(-1) !== dynamicScopeEntry) {
355
363
  dynamicScopeStack.push(dynamicScopeEntry);
356
364
  pushedDynamicScope = true;
357
365
  }
@@ -359,10 +367,11 @@ function validate(report, schema, json) {
359
367
  recursiveAnchorStack.push(schema);
360
368
  pushedRecursiveAnchor = true;
361
369
  }
362
- if (schema.$ref !== void 0) if (this.options.version === "draft2019-09" || this.options.version === "draft2020-12") {
363
- if (!schema.__$refResolved) report.addError("REF_UNRESOLVED", [schema.$ref], void 0, schema);
364
- else validate.call(this, report, schema.__$refResolved, json);
365
- keys = keys.filter((key) => key !== "$ref");
370
+ if (schema.$ref !== void 0) if (ctx.options.version === "draft2019-09" || ctx.options.version === "draft2020-12") {
371
+ if (schema.__$refResolved) validate(ctx, report, schema.__$refResolved, json);
372
+ else report.addError("REF_UNRESOLVED", [schema.$ref], void 0, schema);
373
+ const refIdx = keys.indexOf("$ref");
374
+ if (refIdx !== -1) keys.splice(refIdx, 1);
366
375
  } else {
367
376
  let maxRefs = 99;
368
377
  while (schema.$ref && maxRefs > 0) {
@@ -380,58 +389,65 @@ function validate(report, schema, json) {
380
389
  report.schemaPath = [];
381
390
  }
382
391
  if (schema.$recursiveRef !== void 0) {
383
- if (this.options.version === "draft2019-09" || this.options.version === "draft2020-12") {
392
+ if (ctx.options.version === "draft2019-09" || ctx.options.version === "draft2020-12") {
384
393
  const recursiveRefTarget = resolveRecursiveRef(schema, recursiveAnchorStack);
385
- if (!recursiveRefTarget) report.addError("REF_UNRESOLVED", [schema.$recursiveRef], void 0, schema);
386
- else validate.call(this, report, recursiveRefTarget, json);
387
- keys = keys.filter((key) => key !== "$recursiveRef");
394
+ if (recursiveRefTarget) validate(ctx, report, recursiveRefTarget, json);
395
+ else report.addError("REF_UNRESOLVED", [schema.$recursiveRef], void 0, schema);
396
+ const recursiveRefIdx = keys.indexOf("$recursiveRef");
397
+ if (recursiveRefIdx !== -1) keys.splice(recursiveRefIdx, 1);
388
398
  }
389
399
  }
390
400
  if (schema.$dynamicRef !== void 0) {
391
- if (this.options.version === "draft2020-12") {
401
+ if (ctx.options.version === "draft2020-12") {
392
402
  const dynamicRefTarget = resolveDynamicRef(schema, dynamicScopeStack);
393
- if (typeof dynamicRefTarget === "undefined") report.addError("REF_UNRESOLVED", [schema.$dynamicRef], void 0, schema);
394
- else validate.call(this, report, dynamicRefTarget, json);
395
- keys = keys.filter((key) => key !== "$dynamicRef");
403
+ if (dynamicRefTarget === void 0) report.addError("REF_UNRESOLVED", [schema.$dynamicRef], void 0, schema);
404
+ else validate(ctx, report, dynamicRefTarget, json);
405
+ const dynamicRefIdx = keys.indexOf("$dynamicRef");
406
+ if (dynamicRefIdx !== -1) keys.splice(dynamicRefIdx, 1);
396
407
  }
397
408
  }
398
- const validationVocabularyEnabled = isValidationVocabularyEnabled(schema, report, this.options.version);
399
- if (!validationVocabularyEnabled) keys = keys.filter((key) => !VALIDATION_VOCAB_KEYWORDS.has(key));
409
+ const validationVocabularyEnabled = isValidationVocabularyEnabled(schema, report, ctx.options.version);
410
+ if (!validationVocabularyEnabled) {
411
+ let wi = 0;
412
+ for (let ri = 0; ri < keys.length; ri++) if (!VALIDATION_VOCAB_KEYWORDS.has(keys[ri])) keys[wi++] = keys[ri];
413
+ keys.length = wi;
414
+ }
400
415
  if (validationVocabularyEnabled && schema.type) {
401
416
  keys.splice(keys.indexOf("type"), 1);
402
417
  report.schemaPath.push("type");
403
- JsonValidators.type.call(this, report, schema, json);
418
+ JsonValidators.type(ctx, report, schema, json);
404
419
  report.schemaPath.pop();
405
- if (report.errors.length && this.options.breakOnFirstError) {
420
+ if (report.errors.length && ctx.options.breakOnFirstError) {
406
421
  if (pushedRecursiveAnchor) recursiveAnchorStack.pop();
407
422
  if (pushedDynamicScope) dynamicScopeStack.pop();
408
423
  return false;
409
424
  }
410
425
  }
411
426
  const deferredUnevaluatedKeys = [];
412
- for (const key of keys) {
427
+ for (let i = 0; i < keys.length; i++) {
428
+ const key = keys[i];
413
429
  if (key === "unevaluatedItems" || key === "unevaluatedProperties") {
414
430
  deferredUnevaluatedKeys.push(key);
415
431
  continue;
416
432
  }
417
433
  const validator = JsonValidators[key];
418
434
  if (validator) {
419
- validator.call(this, report, schema, json);
420
- if (report.errors.length && this.options.breakOnFirstError) break;
435
+ validator(ctx, report, schema, json);
436
+ if (report.errors.length && ctx.options.breakOnFirstError) break;
421
437
  }
422
438
  }
423
- if (deferredUnevaluatedKeys.length > 0 && !(report.errors.length > 0 && this.options.breakOnFirstError)) for (const key of deferredUnevaluatedKeys) {
424
- const validator = JsonValidators[key];
439
+ if (deferredUnevaluatedKeys.length > 0 && !(report.errors.length > 0 && ctx.options.breakOnFirstError)) for (let i = 0; i < deferredUnevaluatedKeys.length; i++) {
440
+ const validator = JsonValidators[deferredUnevaluatedKeys[i]];
425
441
  if (validator) {
426
- validator.call(this, report, schema, json);
427
- if (report.errors.length && this.options.breakOnFirstError) break;
442
+ validator(ctx, report, schema, json);
443
+ if (report.errors.length && ctx.options.breakOnFirstError) break;
428
444
  }
429
445
  }
430
- if (report.errors.length === 0 || this.options.breakOnFirstError === false) {
431
- if (Array.isArray(json)) recurseArray.call(this, report, schema, json);
432
- else if (isObject(json)) recurseObject.call(this, report, schema, json);
446
+ if (report.errors.length === 0 || ctx.options.breakOnFirstError === false) {
447
+ if (Array.isArray(json)) recurseArray(ctx, report, schema, json);
448
+ else if (isObject(json)) recurseObject(ctx, report, schema, json);
433
449
  }
434
- if (typeof this.options.customValidator === "function") this.options.customValidator.call(this, report, schema, json);
450
+ if (typeof ctx.options.customValidator === "function") ctx.options.customValidator.call(ctx, report, schema, json);
435
451
  if (pushedRecursiveAnchor) recursiveAnchorStack.pop();
436
452
  if (pushedDynamicScope) dynamicScopeStack.pop();
437
453
  if (isRoot) report.rootSchema = void 0;
@@ -1,7 +1,7 @@
1
- import { ZSchemaOptions } from "./z-schema-options.mjs";
2
- import { ErrorCode, ErrorParam } from "./errors.mjs";
3
- import { ValidateCallback, ValidateOptions } from "./z-schema-base.mjs";
4
- import { JsonSchema, JsonSchemaAll, JsonSchemaInternal } from "./json-schema-versions.mjs";
1
+ import { ZSchemaOptions } from "./z-schema-options.js";
2
+ import { ErrorCode, ErrorParam } from "./errors.js";
3
+ import { ValidateCallback, ValidateOptions } from "./z-schema-base.js";
4
+ import { JsonSchema, JsonSchemaAll, JsonSchemaInternal } from "./json-schema-versions.js";
5
5
 
6
6
  //#region src/report.d.ts
7
7
  interface SchemaErrorDetail {
@@ -71,11 +71,10 @@ declare class Report {
71
71
  options: ZSchemaOptions;
72
72
  reportOptions: ReportOptions;
73
73
  validateOptions: ValidateOptions;
74
- constructor(zschemaOptions: ZSchemaOptions, validateOptions?: ValidateOptions);
75
- constructor(parentReport: Report, validateOptions?: ValidateOptions);
74
+ constructor(parentOrOptions: ZSchemaOptions | Report, validateOptions?: ValidateOptions);
76
75
  constructor(parentReport: Report, reportOptions: ReportOptions, validateOptions?: ValidateOptions);
77
76
  isValid(): boolean;
78
- addAsyncTask<FV, FN extends (...args: any[]) => FV>(fn: FN, args: Parameters<FN>, asyncTaskResultProcessFn: (result: ReturnType<FN>) => void): void;
77
+ addAsyncTask<FN extends (...args: any[]) => any>(fn: FN, args: Parameters<FN>, asyncTaskResultProcessFn: (result: ReturnType<FN>) => void): void;
79
78
  /**
80
79
  * Like {@link addAsyncTask}, but automatically saves the current `path` and
81
80
  * restores it around `processFn`. This eliminates the manual
@@ -88,7 +87,7 @@ declare class Report {
88
87
  getPath(returnPathAsString?: boolean): string | (string | number)[];
89
88
  getSchemaPath(): Array<string | number>;
90
89
  getSchemaId(): string | undefined;
91
- hasError(errCode: string, errParams: Array<any>): boolean;
90
+ hasError(errCode: string, errParams: any[]): boolean;
92
91
  addError(errCode: ErrorCode, errParams?: ErrorParam[], subReports?: Report | Report[], schema?: JsonSchema | boolean, keyword?: keyof JsonSchemaAll): void;
93
92
  getJson(): unknown;
94
93
  addCustomError(errorCode: ErrorCode, errorMessage: string, params?: ErrorParam[], subReports?: Report | Report[], schema?: JsonSchema | boolean, keyword?: keyof JsonSchemaAll): void;
@@ -1,10 +1,10 @@
1
- import { isAbsoluteUri } from "./utils/uri.mjs";
2
- import { MAX_ASYNC_TIMEOUT } from "./utils/constants.mjs";
3
- import { isObject } from "./utils/what-is.mjs";
4
- import { Errors, getValidateError } from "./errors.mjs";
5
- import { shallowClone } from "./utils/clone.mjs";
6
- import { get } from "./utils/json.mjs";
7
- import { jsonSymbol, schemaSymbol } from "./utils/symbols.mjs";
1
+ import { MAX_ASYNC_TIMEOUT } from "./utils/constants.js";
2
+ import { isAbsoluteUri } from "./utils/uri.js";
3
+ import { isObject } from "./utils/what-is.js";
4
+ import { Errors, getValidateError } from "./errors.js";
5
+ import { shallowClone } from "./utils/clone.js";
6
+ import { get } from "./utils/json.js";
7
+ import { jsonSymbol, schemaSymbol } from "./utils/symbols.js";
8
8
  //#region src/report.ts
9
9
  const ASYNC_TIMEOUT_POLL_MS = 10;
10
10
  var Report = class Report {
@@ -28,8 +28,8 @@ var Report = class Report {
28
28
  if (parentOrOptions instanceof Report) {
29
29
  this.reportOptions = reportOptionsOrValidate || {};
30
30
  this.validateOptions = validateOptions || parentOrOptions.validateOptions;
31
- this.__$recursiveAnchorStack = [...parentOrOptions.__$recursiveAnchorStack];
32
- this.__$dynamicScopeStack = [...parentOrOptions.__$dynamicScopeStack];
31
+ this.__$recursiveAnchorStack = parentOrOptions.__$recursiveAnchorStack.slice();
32
+ this.__$dynamicScopeStack = parentOrOptions.__$dynamicScopeStack.slice();
33
33
  this.__validationResultCache = parentOrOptions.__validationResultCache;
34
34
  } else {
35
35
  this.reportOptions = {};
@@ -112,30 +112,24 @@ var Report = class Report {
112
112
  setTimeout(checkTimeout, ASYNC_TIMEOUT_POLL_MS);
113
113
  }
114
114
  getPath(returnPathAsString) {
115
- let path = [];
116
- if (this.parentReport) path = path.concat(this.parentReport.path);
117
- path = path.concat(this.path);
118
- if (returnPathAsString !== true) return "#/" + path.map(function(segment) {
115
+ const path = this.parentReport ? this.parentReport.path.concat(this.path) : this.path.slice();
116
+ if (returnPathAsString !== true) return `#/${path.map((segment) => {
119
117
  segment = segment.toString();
120
- if (isAbsoluteUri(segment)) return "uri(" + segment + ")";
121
- return segment.replace(/~/g, "~0").replace(/\//g, "~1");
122
- }).join("/");
118
+ if (isAbsoluteUri(segment)) return `uri(${segment})`;
119
+ return segment.replaceAll("~", "~0").replaceAll("/", "~1");
120
+ }).join("/")}`;
123
121
  return path;
124
122
  }
125
123
  getSchemaPath() {
126
- let schemaPath = [];
127
- if (this.parentReport) schemaPath = schemaPath.concat(this.parentReport.schemaPath);
128
- schemaPath = schemaPath.concat(this.schemaPath);
129
- return schemaPath;
124
+ if (this.parentReport) return this.parentReport.schemaPath.concat(this.schemaPath);
125
+ return this.schemaPath.slice();
130
126
  }
131
127
  getSchemaId() {
132
128
  if (!this.rootSchema) return;
133
- let path = [];
134
- if (this.parentReport) path = path.concat(this.parentReport.path);
135
- path = path.concat(this.path);
129
+ const path = this.parentReport ? this.parentReport.path.concat(this.path) : this.path.slice();
136
130
  while (path.length > 0) {
137
131
  const obj = get(this.rootSchema, path);
138
- if (obj && obj.id) return obj.id;
132
+ if (isObject(obj) && typeof obj.id === "string") return obj.id;
139
133
  path.pop();
140
134
  }
141
135
  return this.rootSchema.id;
@@ -158,11 +152,11 @@ var Report = class Report {
158
152
  }
159
153
  addCustomError(errorCode, errorMessage, params, subReports, schema, keyword) {
160
154
  if (typeof this.reportOptions.maxErrors === "number" && this.errors.length >= this.reportOptions.maxErrors) return;
161
- if (!errorMessage) throw new Error("No errorMessage known for code " + errorCode);
162
- params = params || [];
155
+ if (!errorMessage) throw new Error(`No errorMessage known for code ${errorCode}`);
156
+ params ||= [];
163
157
  for (let idx = 0; idx < params.length; idx++) {
164
158
  const param = params[idx] === null || isObject(params[idx]) ? JSON.stringify(params[idx]) : params[idx];
165
- errorMessage = errorMessage.replace("{" + idx + "}", param.toString());
159
+ errorMessage = errorMessage.replace(`{${idx}}`, param.toString());
166
160
  }
167
161
  const err = {
168
162
  code: errorCode,
@@ -171,10 +165,10 @@ var Report = class Report {
171
165
  path: this.getPath(this.options.reportPathAsArray),
172
166
  schemaPath: this.getSchemaPath(),
173
167
  schemaId: this.getSchemaId(),
174
- keyword
168
+ keyword,
169
+ [schemaSymbol]: schema,
170
+ [jsonSymbol]: this.getJson()
175
171
  };
176
- err[schemaSymbol] = schema;
177
- err[jsonSymbol] = this.getJson();
178
172
  if (schema && typeof schema === "string") err.description = schema;
179
173
  else if (schema && typeof schema === "object") {
180
174
  if (schema.title) err.title = schema.title;
@@ -183,7 +177,10 @@ var Report = class Report {
183
177
  if (subReports != null) {
184
178
  if (!Array.isArray(subReports)) subReports = [subReports];
185
179
  err.inner = [];
186
- for (const subReport of subReports) for (const error of subReport.errors) err.inner.push(error);
180
+ for (let si = 0; si < subReports.length; si++) {
181
+ const errs = subReports[si].errors;
182
+ for (let ei = 0; ei < errs.length; ei++) err.inner.push(errs[ei]);
183
+ }
187
184
  if (err.inner.length === 0) err.inner = void 0;
188
185
  }
189
186
  if (Array.isArray(this.validateOptions.excludeErrors) && this.validateOptions.excludeErrors.includes(errorCode)) return;