ascertain 0.14.39 → 0.15.0-0

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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2019-2024 Ivan Zakharchanka
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -12,19 +12,56 @@
12
12
 
13
13
  ## Features
14
14
 
15
- - value validation
16
- - class validation
17
- - structure validation
18
- - regexp validation
19
- - and/or validation
20
- - object keys validation
21
- - object values validation
15
+ - Type-safe validation: Ensures your data conforms to predefined schemas.
16
+ - Composite schemas: Supports logical AND, OR, and optional schemas.
17
+ - Type casting: Automatically parse and cast strings to other types.
18
+ - Error handling: Provides detailed error messages for invalid data.
22
19
 
23
20
  ## Usage Example
24
21
 
22
+ ### Schema compilation
23
+ ```typescript
24
+ import { compile, optional, and, or, $keys, $values, Schema, as } from 'ascertain';
25
+
26
+ const validate = compile({
27
+ number: Number,
28
+ string: String,
29
+ boolean: Boolean,
30
+ function: Function,
31
+ array: Array,
32
+ object: Object,
33
+ date: and(Date, { toJSON: Function }),
34
+ regexp: /regexp/,
35
+ oneOfValue: or(1, 2, 3),
36
+ arrayOfNumbers: [Number],
37
+ objectSchema: {
38
+ number: Number,
39
+ },
40
+ optional: optional({
41
+ number: Number,
42
+ }),
43
+ keyValue: {
44
+ [$keys]: /^key[A-Z]/,
45
+ [$values]: Number
46
+ },
47
+ parsedNumber: Number,
48
+ parsedString: String,
49
+ parsedBoolean: Boolean,
50
+ parsedArray: [String],
51
+ parsedJSON: {
52
+ number: 1,
53
+ },
54
+ parsedBase64: String,
55
+ parsedTime: 2 * 60 * 1000, // two minutes
56
+ parsedDate: Date,
57
+ });
58
+
59
+ ```
60
+
61
+ ### Runtime validation
25
62
  Create data ascertain
26
63
  ```typescript
27
- import ascertain, { optional, and, or, $keys, $values, Schema, as } from 'ascertain';
64
+ import { ascertain, optional, and, or, $keys, $values, Schema, as } from 'ascertain';
28
65
 
29
66
  // create data sample
30
67
  const data = {
@@ -49,11 +86,13 @@ const data = {
49
86
  },
50
87
  // fault tolernat type casting
51
88
  parsedNumber: as.number('1'),
52
- parsedString: as.number('string'),
89
+ parsedString: as.string('string'),
53
90
  parsedBoolean: as.boolean('false'),
54
91
  parsedArray: as.array('1,2,3,4,5', ','),
55
92
  parsedJSON: as.json('{ "number": 1 }'),
56
93
  parsedBase64: as.base64('dGVzdA=='),
94
+ parsedTime: as.time('2m'),
95
+ parsedDate: as.date('31-12-2024'),
57
96
  };
58
97
 
59
98
  // create data schema
@@ -86,6 +125,8 @@ const schema: Schema<typeof data> = {
86
125
  number: 1,
87
126
  },
88
127
  parsedBase64: String,
128
+ parsedTime: 2 * 60 * 1000, // two minutes
129
+ parsedDate: Date,
89
130
  };
90
131
 
91
132
  // validate
@@ -94,7 +135,7 @@ const validate = ascertain<typeof data>(schema, data, '[DATA]');
94
135
 
95
136
  ## License
96
137
  License [The MIT License](http://opensource.org/licenses/MIT)
97
- Copyright (c) 2024 Ivan Zakharchanka
138
+ Copyright (c) 2019-2024 Ivan Zakharchanka
98
139
 
99
140
  [npm-url]: https://www.npmjs.com/package/ascertain
100
141
  [downloads-image]: https://img.shields.io/npm/dw/ascertain.svg?maxAge=43200
package/build/index.cjs CHANGED
@@ -15,6 +15,12 @@ _export(exports, {
15
15
  $values: function() {
16
16
  return $values;
17
17
  },
18
+ AssertError: function() {
19
+ return AssertError;
20
+ },
21
+ Context: function() {
22
+ return Context;
23
+ },
18
24
  and: function() {
19
25
  return and;
20
26
  },
@@ -24,8 +30,8 @@ _export(exports, {
24
30
  ascertain: function() {
25
31
  return ascertain;
26
32
  },
27
- default: function() {
28
- return _default;
33
+ compile: function() {
34
+ return compile;
29
35
  },
30
36
  fromBase64: function() {
31
37
  return fromBase64;
@@ -35,63 +41,53 @@ _export(exports, {
35
41
  },
36
42
  or: function() {
37
43
  return or;
44
+ },
45
+ tuple: function() {
46
+ return tuple;
38
47
  }
39
48
  });
40
- let AssertError = class AssertError {
49
+ class AssertError extends TypeError {
50
+ value;
51
+ expected;
52
+ path;
53
+ subject;
54
+ static join(errors, separator = ' or ') {
55
+ return new AssertError(errors[0].value, errors.map((e)=>`${e.expected}`).join(separator), errors[0].path, errors[0].subject);
56
+ }
41
57
  constructor(value, expected, path, subject = 'value'){
58
+ super(`Invalid ${subject} ${JSON.stringify(value)} for path ${path}, expected ${expected}.`);
42
59
  this.value = value;
43
60
  this.expected = expected;
44
61
  this.path = path;
45
62
  this.subject = subject;
46
63
  }
47
- toString() {
48
- return `Invalid ${this.subject} ${JSON.stringify(this.value)} specified by path ${this.path} expected ${this.expected}`;
49
- }
50
- };
51
- function findFirstError(array, map) {
52
- for(let i = 0; i < array.length; i++){
53
- const error = map(array[i], i);
54
- if (error) {
55
- return error;
56
- }
57
- }
58
- return false;
59
64
  }
60
- function findNotError(array, map) {
61
- const errors = [];
62
- for(let i = 0; i < array.length; i++){
63
- const error = map(array[i], i);
64
- if (!error) {
65
- return false;
66
- } else {
67
- errors.push(error);
65
+ class Operation {
66
+ schemas;
67
+ constructor(schemas){
68
+ this.schemas = schemas;
69
+ if (schemas.length === 0) {
70
+ throw new TypeError(`Operation schema ${this.constructor.name} must have at least one element`);
68
71
  }
69
72
  }
70
- return errors.reduce((result, error)=>{
71
- return new AssertError(result.value, [
72
- result.expected,
73
- error.expected
74
- ].join(' or '), result.path, result.string);
75
- });
76
73
  }
77
- function Optional(schema) {
78
- this.schema = schema;
74
+ class Or extends Operation {
79
75
  }
80
- function And(schema) {
81
- this.schema = schema;
76
+ const or = (...schemas)=>new Or(schemas);
77
+ class And extends Operation {
82
78
  }
83
- function Or(schema) {
84
- this.schema = schema;
79
+ const and = (...schemas)=>new And(schemas);
80
+ class Optional extends Operation {
81
+ constructor(schema){
82
+ super([
83
+ schema
84
+ ]);
85
+ }
85
86
  }
86
- const optional = (schema)=>{
87
- return new Optional(schema);
88
- };
89
- const and = (...schema)=>{
90
- return new And(schema);
91
- };
92
- const or = (...schema)=>{
93
- return new Or(schema);
94
- };
87
+ const optional = (schema)=>new Optional(schema);
88
+ class Tuple extends Operation {
89
+ }
90
+ const tuple = (...schemas)=>new Tuple(schemas);
95
91
  const $keys = Symbol.for('@@keys');
96
92
  const $values = Symbol.for('@@values');
97
93
  const fromBase64 = typeof Buffer === 'undefined' ? (value)=>atob(value) : (value)=>Buffer.from(value, 'base64').toString('utf-8');
@@ -118,7 +114,7 @@ const as = {
118
114
  time: (value)=>{
119
115
  const matches = value?.match(/^(\d+)(ms|s|m|h|d|w)?$/);
120
116
  if (matches) {
121
- const [_, amount, unit = 'ms'] = matches;
117
+ const [, amount, unit = 'ms'] = matches;
122
118
  return parseInt(amount, 10) * MULTIPLIERS[unit];
123
119
  }
124
120
  return undefined;
@@ -140,28 +136,196 @@ const as = {
140
136
  }
141
137
  }
142
138
  };
143
- function certain(target, schema, path, optional) {
139
+ class Context {
140
+ options;
141
+ Error;
142
+ errors;
143
+ registry;
144
+ varIndex;
145
+ constructor(options = {}){
146
+ this.options = options;
147
+ this.errors = [];
148
+ this.registry = [];
149
+ this.varIndex = 0;
150
+ this.Error = options.error ?? AssertError;
151
+ }
152
+ error(errors) {
153
+ this.errors.push(...errors);
154
+ return true;
155
+ }
156
+ register(value) {
157
+ if (!this.registry.includes(value)) {
158
+ this.registry.push(value);
159
+ }
160
+ return this.registry.indexOf(value);
161
+ }
162
+ unique(prefix) {
163
+ return `${prefix}$$${this.varIndex++}`;
164
+ }
165
+ }
166
+ const codeGen = (schema, context, valuePath, path)=>{
167
+ if (schema instanceof And) {
168
+ const valueAlias = context.unique('v');
169
+ const errorsAlias = context.unique('err');
170
+ const code = schema.schemas.map((s)=>`try { ${codeGen(s, context, valueAlias, path)} } catch (e) { ${errorsAlias}.push(e); }`).join('\n');
171
+ return `// And
172
+ const ${errorsAlias} = [];
173
+ const ${valueAlias} = ${valuePath};
174
+ ${code}
175
+ if (${errorsAlias}.length !== 0) { throw ctx.Error.join(${errorsAlias}, ' and '); }
176
+ `;
177
+ } else if (schema instanceof Or) {
178
+ const valueAlias = context.unique('v');
179
+ const errorsAlias = context.unique('err');
180
+ const code = schema.schemas.map((s)=>codeGen(s, context, valueAlias, path)).reduceRight((result, code)=>`try {${code}} catch (e) {${errorsAlias}.push(e);${result}}`, `throw ctx.Error.join(${errorsAlias}, ' or ')`);
181
+ return `// Or
182
+ const ${errorsAlias} = [];
183
+ const ${valueAlias} = ${valuePath};
184
+ ${code}
185
+ `;
186
+ } else if (schema instanceof Optional) {
187
+ const valueAlias = context.unique('v');
188
+ return `// Optional
189
+ const ${valueAlias} = ${valuePath};
190
+ if (${valueAlias} !== undefined && ${valueAlias} !== null) { ${codeGen(schema.schemas[0], context, valueAlias, path)} }
191
+ `;
192
+ } else if (schema instanceof Tuple) {
193
+ const valueAlias = context.unique('v');
194
+ const errorsAlias = context.unique('err');
195
+ const code = schema.schemas.map((s, idx)=>`try { ${codeGen(s, context, `${valueAlias}[${idx}]`, `${path}[${idx}]`)} } catch (e) { ${errorsAlias}.push(e); }`).join('\n');
196
+ return `// Tuple
197
+ const ${valueAlias} = ${valuePath};
198
+ const ${errorsAlias} = [];
199
+ if (!Array.isArray(${valueAlias})) { throw new ctx.Error(${valueAlias}, 'Array', \`${path}\`); }
200
+ ${code}
201
+ if (${errorsAlias}.length !== 0) { throw ctx.Error.join(${errorsAlias}, ', '); }
202
+ `;
203
+ }
204
+ if (typeof schema === 'function') {
205
+ const index = context.register(schema);
206
+ const valueAlias = context.unique('v');
207
+ const registryAlias = context.unique('r');
208
+ return `
209
+ const ${valueAlias} = ${valuePath};
210
+ const ${registryAlias} = ctx.registry[${index}];
211
+ if (${valueAlias} === null || ${valueAlias} === undefined) { throw new ctx.Error(${valueAlias}, 'a non-nullable', \`${path}\`); }
212
+ if (typeof ${valueAlias} === 'object' && !(${valueAlias} instanceof ${registryAlias})) { throw new ctx.Error(${valueAlias}?.constructor?.name, \`instance of \${${registryAlias}.name}\`, \`${path}\`, 'instance of'); }
213
+ else if (typeof ${valueAlias} !== 'object' && ${valueAlias}?.constructor !== ${registryAlias}) { throw new ctx.Error(${valueAlias}?.constructor?.name, ${registryAlias}.name, \`${path}\`, 'type'); }
214
+ `;
215
+ } else if (Array.isArray(schema)) {
216
+ const valueAlias = context.unique('v');
217
+ const code = [
218
+ `const ${valueAlias} = ${valuePath};`,
219
+ `if (!Array.isArray(${valueAlias})) { throw new ctx.Error(${valueAlias}, '${schema.constructor.name}', \`${path}\`); }`
220
+ ];
221
+ if (schema.length > 0) {
222
+ const value = context.unique('val');
223
+ const key = context.unique('key');
224
+ const errorsAlias = context.unique('err');
225
+ const orCode = schema.map((s)=>codeGen(s, context, value, `${path}[\${${key}}]`)).reduceRight((result, code)=>`try {${code}} catch (e) {${errorsAlias}.push(e);${result}}`, `throw ctx.Error.join(${errorsAlias}, ' or ')`);
226
+ code.push(`for(const ${key} in ${valueAlias}) {`, `const ${errorsAlias} = [];`, `const ${value} = ${valueAlias}[${key}];`, orCode, `}`);
227
+ }
228
+ return code.join('\n');
229
+ } else if (typeof schema === 'object' && schema !== null) {
230
+ if (schema instanceof RegExp) {
231
+ const valueAlias = context.unique('v');
232
+ return `
233
+ const ${valueAlias} = ${valuePath};
234
+ if (!${schema.toString()}.test('' + ${valueAlias})) { throw new ctx.Error(${valueAlias}, 'matching ${schema.toString()}', \`${path}\`); }
235
+ `;
236
+ } else {
237
+ const valueAlias = context.unique('v');
238
+ const code = [
239
+ `const ${valueAlias} = ${valuePath};`,
240
+ `if (typeof ${valueAlias} !== 'object') { throw new ctx.Error(${valueAlias}, '${schema.constructor.name}', \`${path}\`); }`,
241
+ `if (${valueAlias} === null) { throw new ctx.Error(${valueAlias}, 'object', \`${path}\`); }`
242
+ ];
243
+ if ($keys in schema) {
244
+ const keysAlias = context.unique('key');
245
+ const errorsAlias = context.unique('err');
246
+ const value = context.unique('v');
247
+ code.push(`
248
+ const ${keysAlias} = Object.keys(${valueAlias});
249
+ const ${errorsAlias} = ${keysAlias}.map((${value}) => { ${codeGen(schema[$keys], context, value, path)} }).flat().filter(Boolean);
250
+ if (${errorsAlias}.length !== 0) { throw ctx.Error.join(${errorsAlias}, ', '); }
251
+ `);
252
+ }
253
+ if ($values in schema) {
254
+ const vAlias = context.unique('val');
255
+ const valuesAlias = context.unique('vals');
256
+ const errorsAlias = context.unique('err');
257
+ code.push(`{
258
+ const ${valuesAlias} = Object.values(${valuePath});
259
+ const ${errorsAlias} = ${valuesAlias}.map((${vAlias}) => { ${codeGen(schema[$values], context, vAlias, path)} }).flat().filter(Boolean);
260
+ if (${errorsAlias}.length !== 0) { throw ctx.Error.join(${errorsAlias}, ', '); }
261
+ }`);
262
+ }
263
+ const keys = Object.keys(schema);
264
+ code.push(...keys.map((key)=>codeGen(schema[key], context, `${valueAlias}['${key}']`, `${path}.${key}`)));
265
+ return `{${code.join('\n')}}`;
266
+ }
267
+ } else {
268
+ const valueAlias = context.unique('v');
269
+ return `
270
+ const ${valueAlias} = ${valuePath};
271
+ if (${valueAlias} !== ${schema}) { throw new ctx.Error(${valueAlias}, ${schema}, \`${path}\`); }
272
+ `;
273
+ }
274
+ };
275
+ const compile = (schema, rootName, options = {})=>{
276
+ const context = new Context(options);
277
+ const code = codeGen(schema, context, 'data', rootName);
278
+ const validator = new Function('ctx', 'data', code);
279
+ return (data)=>validator(context, data);
280
+ };
281
+ const findFirstError = (array, map)=>{
282
+ for(let i = 0; i < array.length; i++){
283
+ const error = map(array[i], i);
284
+ if (error) {
285
+ return error;
286
+ }
287
+ }
288
+ return false;
289
+ };
290
+ const findNotError = (array, map)=>{
291
+ const errors = [];
292
+ for(let i = 0; i < array.length; i++){
293
+ const error = map(array[i], i);
294
+ if (!error) {
295
+ return false;
296
+ } else {
297
+ errors.push(error);
298
+ }
299
+ }
300
+ return errors.reduce((result, error)=>{
301
+ return new AssertError(result.value, [
302
+ result.expected,
303
+ error.expected
304
+ ].join(' or '), result.path, result.subject);
305
+ });
306
+ };
307
+ const assert = (target, schema, path, optional = false)=>{
144
308
  if (schema === null || typeof schema === 'undefined') {
145
309
  return new AssertError(schema, 'any value', path, 'schema value');
146
310
  }
147
311
  if (schema instanceof Optional) {
148
- return certain(target, schema.schema, path, true);
312
+ return assert(target, schema.schemas[0], path, true);
149
313
  }
150
314
  const isValue = target !== null && typeof target !== 'undefined';
151
315
  if (!isValue && optional) {
152
316
  return;
153
317
  }
154
318
  if (schema instanceof Or) {
155
- if (!schema.schema.length) {
319
+ if (!schema.schemas.length) {
156
320
  return new AssertError(target, 'values', path, 'OR schema');
157
321
  }
158
- return findNotError(schema.schema, (schema)=>certain(target, schema, path));
322
+ return findNotError(schema.schemas, (schema)=>assert(target, schema, path));
159
323
  }
160
324
  if (schema instanceof And) {
161
- if (!schema.schema.length) {
325
+ if (!schema.schemas.length) {
162
326
  return new AssertError(target, 'values', path, 'AND schema');
163
327
  }
164
- return findFirstError(schema.schema, (schema)=>certain(target, schema, path));
328
+ return findFirstError(schema.schemas, (schema)=>assert(target, schema, path));
165
329
  }
166
330
  if (typeof schema === 'function') {
167
331
  if (!isValue) {
@@ -178,7 +342,7 @@ function certain(target, schema, path, optional) {
178
342
  return new AssertError(target, schema.constructor.name, path);
179
343
  }
180
344
  return findFirstError(target, (value, idx)=>{
181
- return findNotError(schema, (itemSchemaType)=>certain(value, itemSchemaType, `${path}.${idx}`));
345
+ return findNotError(schema, (itemSchemaType)=>assert(value, itemSchemaType, `${path}.${idx}`));
182
346
  });
183
347
  } else if (typeof schema === 'object') {
184
348
  if (schema instanceof RegExp) {
@@ -194,30 +358,29 @@ function certain(target, schema, path, optional) {
194
358
  }
195
359
  if ($keys in schema) {
196
360
  const targetKeys = Object.keys(target);
197
- const assertError = findFirstError(targetKeys, (targetKey)=>certain(targetKey, schema[$keys], `${path}.${targetKey}`));
361
+ const assertError = findFirstError(targetKeys, (targetKey)=>assert(targetKey, schema[$keys], `${path}.${targetKey}`));
198
362
  if (assertError) {
199
363
  return assertError;
200
364
  }
201
365
  }
202
366
  if ($values in schema) {
203
367
  const targetKeys = Object.keys(target);
204
- const assertError = findFirstError(targetKeys, (targetKey)=>certain(target[targetKey], schema[$values], `${path}.${targetKey}`));
368
+ const assertError = findFirstError(targetKeys, (targetKey)=>assert(target[targetKey], schema[$values], `${path}.${targetKey}`));
205
369
  if (assertError) {
206
370
  return assertError;
207
371
  }
208
372
  }
209
- return findFirstError(Object.keys(schema), (key)=>certain(target[key], schema[key], `${path}.${key}`));
373
+ return findFirstError(Object.keys(schema), (key)=>assert(target[key], schema[key], `${path}.${key}`));
210
374
  }
211
375
  } else if (target !== schema) {
212
376
  return new AssertError(target, schema, path);
213
377
  }
214
- }
378
+ };
215
379
  const ascertain = (schema, data, rootName = '[root]')=>{
216
- const result = certain(data, schema, rootName);
380
+ const result = assert(data, schema, rootName);
217
381
  if (result instanceof AssertError) {
218
382
  throw new TypeError(result.toString());
219
383
  }
220
384
  };
221
- const _default = ascertain;
222
385
 
223
386
  //# sourceMappingURL=index.cjs.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.js"],"sourcesContent":["class AssertError {\n constructor(value, expected, path, subject = 'value') {\n this.value = value;\n this.expected = expected;\n this.path = path;\n this.subject = subject;\n }\n\n toString() {\n return `Invalid ${this.subject} ${JSON.stringify(this.value)} specified by path ${this.path} expected ${this.expected}`;\n }\n}\n\nfunction findFirstError(array, map) {\n for (let i = 0; i < array.length; i++) {\n const error = map(array[i], i);\n if (error) {\n return error;\n }\n }\n return false;\n}\n\nfunction findNotError(array, map) {\n const errors = [];\n for (let i = 0; i < array.length; i++) {\n const error = map(array[i], i);\n if (!error) {\n return false;\n } else {\n errors.push(error);\n }\n }\n return errors.reduce((result, error) => {\n return new AssertError(result.value, [result.expected, error.expected].join(' or '), result.path, result.string);\n });\n}\n\nfunction Optional(schema) {\n this.schema = schema;\n}\n\nfunction And(schema) {\n this.schema = schema;\n}\n\nfunction Or(schema) {\n this.schema = schema;\n}\n\nexport const optional = (schema) => {\n return new Optional(schema);\n};\n\nexport const and = (...schema) => {\n return new And(schema);\n};\n\nexport const or = (...schema) => {\n return new Or(schema);\n};\n\nexport const $keys = Symbol.for('@@keys');\nexport const $values = Symbol.for('@@values');\n\nexport const fromBase64 =\n typeof Buffer === 'undefined' ? (value) => atob(value) : (value) => Buffer.from(value, 'base64').toString('utf-8');\n\nconst MULTIPLIERS = {\n ms: 1,\n s: 1000,\n m: 60000,\n h: 3600000,\n d: 86400000,\n w: 604800000,\n};\n\nexport const as = {\n string: (value) => {\n return typeof value === 'string' ? value : undefined;\n },\n number: (value) => {\n const result = parseFloat(value);\n return Number.isFinite(result) ? result : undefined;\n },\n date: (value) => {\n const result = Date.parse(value);\n return Number.isFinite(result) ? new Date(result) : undefined;\n },\n time: (value) => {\n const matches = value?.match(/^(\\d+)(ms|s|m|h|d|w)?$/);\n if (matches) {\n const [_, amount, unit = 'ms'] = matches;\n return parseInt(amount, 10) * MULTIPLIERS[unit];\n }\n return undefined;\n },\n boolean: (value) => (/^(0|1|true|false|enabled|disabled)$/i.test(value) ? /^(1|true|enabled)$/i.test(value) : undefined),\n array: (value, delimiter) => value?.split(delimiter) ?? undefined,\n json: (value) => {\n try {\n return JSON.parse(value);\n } catch (e) {\n return undefined;\n }\n },\n base64: (value) => {\n try {\n return fromBase64(value);\n } catch (e) {\n return undefined;\n }\n },\n};\n\nfunction certain(target, schema, path, optional) {\n if (schema === null || typeof schema === 'undefined') {\n return new AssertError(schema, 'any value', path, 'schema value');\n }\n if (schema instanceof Optional) {\n return certain(target, schema.schema, path, true);\n }\n const isValue = target !== null && typeof target !== 'undefined';\n if (!isValue && optional) {\n return;\n }\n if (schema instanceof Or) {\n if (!schema.schema.length) {\n return new AssertError(target, 'values', path, 'OR schema');\n }\n return findNotError(schema.schema, (schema) => certain(target, schema, path));\n }\n if (schema instanceof And) {\n if (!schema.schema.length) {\n return new AssertError(target, 'values', path, 'AND schema');\n }\n return findFirstError(schema.schema, (schema) => certain(target, schema, path));\n }\n\n if (typeof schema === 'function') {\n if (!isValue) {\n return new AssertError(target, schema.name, path);\n }\n if (typeof target === 'object' && !(target instanceof schema)) {\n return new AssertError(target, schema.name, path);\n }\n if (typeof target !== 'object' && target.constructor !== schema) {\n return new AssertError(target, schema.name, path);\n }\n } else if (Array.isArray(schema)) {\n if (!Array.isArray(target)) {\n return new AssertError(target, schema.constructor.name, path);\n }\n return findFirstError(target, (value, idx) => {\n return findNotError(schema, (itemSchemaType) => certain(value, itemSchemaType, `${path}.${idx}`));\n });\n } else if (typeof schema === 'object') {\n if (schema instanceof RegExp) {\n if (!schema.test('' + target)) {\n return new AssertError(target, `matching /${schema.source}/`, path);\n }\n } else {\n if (typeof target !== 'object') {\n return new AssertError(target, schema.constructor.name, path);\n }\n if (target === null) {\n return new AssertError(target, 'an object', path);\n }\n if ($keys in schema) {\n const targetKeys = Object.keys(target);\n const assertError = findFirstError(targetKeys, (targetKey) =>\n certain(targetKey, schema[$keys], `${path}.${targetKey}`)\n );\n if (assertError) {\n return assertError;\n }\n }\n if ($values in schema) {\n const targetKeys = Object.keys(target);\n const assertError = findFirstError(targetKeys, (targetKey) =>\n certain(target[targetKey], schema[$values], `${path}.${targetKey}`)\n );\n if (assertError) {\n return assertError;\n }\n }\n return findFirstError(Object.keys(schema), (key) => certain(target[key], schema[key], `${path}.${key}`));\n }\n } else if (target !== schema) {\n return new AssertError(target, schema, path);\n }\n}\n\nexport const ascertain = (schema, data, rootName = '[root]') => {\n const result = certain(data, schema, rootName);\n if (result instanceof AssertError) {\n throw new TypeError(result.toString());\n }\n};\n\nexport default ascertain;\n"],"names":["$keys","$values","and","as","ascertain","fromBase64","optional","or","AssertError","constructor","value","expected","path","subject","toString","JSON","stringify","findFirstError","array","map","i","length","error","findNotError","errors","push","reduce","result","join","string","Optional","schema","And","Or","Symbol","for","Buffer","atob","from","MULTIPLIERS","ms","s","m","h","d","w","undefined","number","parseFloat","Number","isFinite","date","Date","parse","time","matches","match","_","amount","unit","parseInt","boolean","test","delimiter","split","json","e","base64","certain","target","isValue","name","Array","isArray","idx","itemSchemaType","RegExp","source","targetKeys","Object","keys","assertError","targetKey","key","data","rootName","TypeError"],"rangeMappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;","mappings":"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"}
1
+ {"version":3,"sources":["../src/index.ts"],"sourcesContent":["export class AssertError extends TypeError {\n static join(errors: AssertError[], separator = ' or ') {\n return new AssertError(errors[0].value, errors.map((e) => `${e.expected}`).join(separator), errors[0].path, errors[0].subject);\n }\n constructor(\n public readonly value: unknown,\n public readonly expected: unknown,\n public readonly path: string,\n public readonly subject = 'value',\n ) {\n super(`Invalid ${subject} ${JSON.stringify(value)} for path ${path}, expected ${expected}.`);\n }\n}\n\ntype AssertErrorConstructor = new (value: unknown, expected: unknown, path: string, subject?: string) => Error;\n\ntype Keys = string | number | symbol;\ntype DataValue = any;\ntype Data = Record<Keys, unknown>;\ntype DataArray = DataValue[];\n\nexport type Schema<T> = T extends Data ? { [S in keyof T]?: Schema<T[S]> } : T extends DataArray ? [Schema<T[number]>] : DataValue;\n\nexport type SchemaData<S> =\n S extends Record<Keys, unknown>\n ? { [K in keyof S as Exclude<K, typeof $keys | typeof $values>]?: SchemaData<S[K]> } & Record<string, unknown>\n : S extends unknown[]\n ? unknown[]\n : unknown;\n\nabstract class Operation<T extends Data = DataValue> {\n constructor(public readonly schemas: Schema<T>[]) {\n if (schemas.length === 0) {\n throw new TypeError(`Operation schema ${this.constructor.name} must have at least one element`);\n }\n }\n}\n\nclass Or<T extends Data = DataValue> extends Operation<T> {}\nexport const or = <T extends Data = DataValue>(...schemas: Schema<T>[]) => new Or(schemas);\n\nclass And<T extends Data = DataValue> extends Operation<T> {}\nexport const and = <T extends Data = DataValue>(...schemas: Schema<T>[]) => new And(schemas);\n\nclass Optional<T extends Data = DataValue> extends Operation<T> {\n constructor(schema: Schema<T>) {\n super([schema]);\n }\n}\nexport const optional = <T extends Data = DataValue>(schema: Schema<T>) => new Optional(schema);\n\nclass Tuple<T extends Data = DataValue> extends Operation<T> {}\nexport const tuple = <T extends Data = DataValue>(...schemas: Schema<T>[]) => new Tuple(schemas);\n\nexport const $keys = Symbol.for('@@keys');\nexport const $values = Symbol.for('@@values');\nexport const fromBase64 = typeof Buffer === 'undefined' ? (value: string) => atob(value) : (value: string) => Buffer.from(value, 'base64').toString('utf-8');\n\nconst MULTIPLIERS = {\n ms: 1,\n s: 1000,\n m: 60000,\n h: 3600000,\n d: 86400000,\n w: 604800000,\n};\n\nexport const as = {\n string: (value: string | undefined) => {\n return typeof value === 'string' ? value : undefined;\n },\n number: (value: string | undefined) => {\n const result = parseFloat(value as string);\n return Number.isFinite(result) ? result : undefined;\n },\n date: (value: string | undefined) => {\n const result = Date.parse(value as string);\n return Number.isFinite(result) ? new Date(result) : undefined;\n },\n time: (value: string | undefined) => {\n const matches = value?.match(/^(\\d+)(ms|s|m|h|d|w)?$/);\n if (matches) {\n const [, amount, unit = 'ms'] = matches;\n return parseInt(amount, 10) * MULTIPLIERS[unit as keyof typeof MULTIPLIERS];\n }\n return undefined;\n },\n boolean: (value: string | undefined) =>\n /^(0|1|true|false|enabled|disabled)$/i.test(value as string) ? /^(1|true|enabled)$/i.test(value as string) : undefined,\n array: (value: string | undefined, delimiter: string) => value?.split(delimiter) ?? undefined,\n json: (value: string | undefined) => {\n try {\n return JSON.parse(value as string);\n } catch (e) {\n return undefined;\n }\n },\n base64: (value: string | undefined) => {\n try {\n return fromBase64(value as string);\n } catch (e) {\n return undefined;\n }\n },\n};\n\nexport class Context {\n public readonly Error: AssertErrorConstructor;\n public readonly errors: AssertError[] = [];\n public readonly registry: unknown[] = [];\n private varIndex = 0;\n constructor(public readonly options: CompilerOptions = {}) {\n this.Error = options.error ?? AssertError;\n }\n\n error(errors: AssertError[]) {\n this.errors.push(...errors);\n return true;\n }\n\n register(value: unknown): number {\n if (!this.registry.includes(value)) {\n this.registry.push(value);\n }\n return this.registry.indexOf(value);\n }\n\n unique(prefix: string) {\n return `${prefix}$$${this.varIndex++}`;\n }\n}\n\nexport interface CompilerOptions {\n error?: AssertErrorConstructor;\n}\n\nconst codeGen = <T extends Data = DataValue>(schema: Schema<T>, context: Context, valuePath: string, path: string): string => {\n if (schema instanceof And) {\n const valueAlias = context.unique('v');\n const errorsAlias = context.unique('err');\n const code = schema.schemas.map((s) => `try { ${codeGen(s, context, valueAlias, path)} } catch (e) { ${errorsAlias}.push(e); }`).join('\\n');\n return `// And\n const ${errorsAlias} = [];\n const ${valueAlias} = ${valuePath};\n ${code}\n if (${errorsAlias}.length !== 0) { throw ctx.Error.join(${errorsAlias}, ' and '); }\n`;\n } else if (schema instanceof Or) {\n const valueAlias = context.unique('v');\n const errorsAlias = context.unique('err');\n const code = schema.schemas\n .map((s) => codeGen(s, context, valueAlias, path))\n .reduceRight((result, code) => `try {${code}} catch (e) {${errorsAlias}.push(e);${result}}`, `throw ctx.Error.join(${errorsAlias}, ' or ')`);\n return `// Or\nconst ${errorsAlias} = [];\nconst ${valueAlias} = ${valuePath};\n${code}\n `;\n } else if (schema instanceof Optional) {\n const valueAlias = context.unique('v');\n return `// Optional\nconst ${valueAlias} = ${valuePath};\nif (${valueAlias} !== undefined && ${valueAlias} !== null) { ${codeGen(schema.schemas[0], context, valueAlias, path)} }\n`;\n } else if (schema instanceof Tuple) {\n const valueAlias = context.unique('v');\n const errorsAlias = context.unique('err');\n const code = schema.schemas\n .map((s, idx) => `try { ${codeGen(s, context, `${valueAlias}[${idx}]`, `${path}[${idx}]`)} } catch (e) { ${errorsAlias}.push(e); }`)\n .join('\\n');\n return `// Tuple\n const ${valueAlias} = ${valuePath};\n const ${errorsAlias} = [];\n if (!Array.isArray(${valueAlias})) { throw new ctx.Error(${valueAlias}, 'Array', \\`${path}\\`); }\n ${code}\n if (${errorsAlias}.length !== 0) { throw ctx.Error.join(${errorsAlias}, ', '); }\n`;\n }\n if (typeof schema === 'function') {\n const index = context.register(schema);\n const valueAlias = context.unique('v');\n const registryAlias = context.unique('r');\n return `\nconst ${valueAlias} = ${valuePath};\nconst ${registryAlias} = ctx.registry[${index}];\nif (${valueAlias} === null || ${valueAlias} === undefined) { throw new ctx.Error(${valueAlias}, 'a non-nullable', \\`${path}\\`); }\nif (typeof ${valueAlias} === 'object' && !(${valueAlias} instanceof ${registryAlias})) { throw new ctx.Error(${valueAlias}?.constructor?.name, \\`instance of \\${${registryAlias}.name}\\`, \\`${path}\\`, 'instance of'); }\nelse if (typeof ${valueAlias} !== 'object' && ${valueAlias}?.constructor !== ${registryAlias}) { throw new ctx.Error(${valueAlias}?.constructor?.name, ${registryAlias}.name, \\`${path}\\`, 'type'); }\n`;\n } else if (Array.isArray(schema)) {\n const valueAlias = context.unique('v');\n const code: string[] = [\n `const ${valueAlias} = ${valuePath};`,\n `if (!Array.isArray(${valueAlias})) { throw new ctx.Error(${valueAlias}, '${schema.constructor.name}', \\`${path}\\`); }`,\n ];\n if (schema.length > 0) {\n const value = context.unique('val');\n const key = context.unique('key');\n const errorsAlias = context.unique('err');\n\n const orCode = schema\n .map((s) => codeGen(s, context, value, `${path}[\\${${key}}]`))\n .reduceRight((result, code) => `try {${code}} catch (e) {${errorsAlias}.push(e);${result}}`, `throw ctx.Error.join(${errorsAlias}, ' or ')`);\n code.push(`for(const ${key} in ${valueAlias}) {`, `const ${errorsAlias} = [];`, `const ${value} = ${valueAlias}[${key}];`, orCode, `}`);\n }\n return code.join('\\n');\n } else if (typeof schema === 'object' && schema !== null) {\n if (schema instanceof RegExp) {\n const valueAlias = context.unique('v');\n return `\nconst ${valueAlias} = ${valuePath};\nif (!${schema.toString()}.test('' + ${valueAlias})) { throw new ctx.Error(${valueAlias}, 'matching ${schema.toString()}', \\`${path}\\`); }\n`;\n } else {\n const valueAlias = context.unique('v');\n const code: string[] = [\n `const ${valueAlias} = ${valuePath};`,\n `if (typeof ${valueAlias} !== 'object') { throw new ctx.Error(${valueAlias}, '${schema.constructor.name}', \\`${path}\\`); }`,\n `if (${valueAlias} === null) { throw new ctx.Error(${valueAlias}, 'object', \\`${path}\\`); }`,\n ];\n if ($keys in schema) {\n const keysAlias = context.unique('key');\n const errorsAlias = context.unique('err');\n const value = context.unique('v');\n code.push(`\nconst ${keysAlias} = Object.keys(${valueAlias});\nconst ${errorsAlias} = ${keysAlias}.map((${value}) => { ${codeGen(schema[$keys], context, value, path)} }).flat().filter(Boolean);\nif (${errorsAlias}.length !== 0) { throw ctx.Error.join(${errorsAlias}, ', '); }\n`);\n }\n if ($values in schema) {\n const vAlias = context.unique('val');\n const valuesAlias = context.unique('vals');\n const errorsAlias = context.unique('err');\n code.push(`{\nconst ${valuesAlias} = Object.values(${valuePath});\nconst ${errorsAlias} = ${valuesAlias}.map((${vAlias}) => { ${codeGen(schema[$values], context, vAlias, path)} }).flat().filter(Boolean);\nif (${errorsAlias}.length !== 0) { throw ctx.Error.join(${errorsAlias}, ', '); }\n}`);\n }\n const keys = Object.keys(schema);\n code.push(...keys.map((key) => codeGen(schema[key], context, `${valueAlias}['${key}']`, `${path}.${key}`)));\n return `{${code.join('\\n')}}`;\n }\n } else {\n const valueAlias = context.unique('v');\n return `\nconst ${valueAlias} = ${valuePath};\nif (${valueAlias} !== ${schema}) { throw new ctx.Error(${valueAlias}, ${schema}, \\`${path}\\`); }\n`;\n }\n};\n\nexport const compile = <S>(schema: S, rootName: string, options: CompilerOptions = {}) => {\n const context = new Context(options);\n const code = codeGen(schema, context, 'data', rootName);\n const validator = new Function('ctx', 'data', code);\n return (data: SchemaData<S>) => validator(context, data);\n};\n\nconst findFirstError = <T>(array: T[], map: (value: T, index: number) => AssertError | false | null | void | undefined): false | AssertError => {\n for (let i = 0; i < array.length; i++) {\n const error = map(array[i], i);\n if (error) {\n return error;\n }\n }\n return false;\n};\n\nconst findNotError = <T>(array: T[], map: (value: T, index: number) => AssertError | false | null | void | undefined): false | AssertError => {\n const errors: AssertError[] = [];\n for (let i = 0; i < array.length; i++) {\n const error = map(array[i], i);\n if (!error) {\n return false;\n } else {\n errors.push(error);\n }\n }\n return errors.reduce((result, error) => {\n return new AssertError(result.value, [result.expected, error.expected].join(' or '), result.path, result.subject);\n });\n};\n\nconst assert = (target: unknown, schema: unknown, path: string, optional = false): AssertError | false | void => {\n if (schema === null || typeof schema === 'undefined') {\n return new AssertError(schema, 'any value', path, 'schema value');\n }\n if (schema instanceof Optional) {\n return assert(target, schema.schemas[0], path, true);\n }\n const isValue = target !== null && typeof target !== 'undefined';\n if (!isValue && optional) {\n return;\n }\n if (schema instanceof Or) {\n if (!schema.schemas.length) {\n return new AssertError(target, 'values', path, 'OR schema');\n }\n return findNotError(schema.schemas, (schema) => assert(target, schema, path));\n }\n if (schema instanceof And) {\n if (!schema.schemas.length) {\n return new AssertError(target, 'values', path, 'AND schema');\n }\n return findFirstError(schema.schemas, (schema) => assert(target, schema, path));\n }\n\n if (typeof schema === 'function') {\n if (!isValue) {\n return new AssertError(target, schema.name, path);\n }\n if (typeof target === 'object' && !(target instanceof schema)) {\n return new AssertError(target, schema.name, path);\n }\n if (typeof target !== 'object' && target.constructor !== schema) {\n return new AssertError(target, schema.name, path);\n }\n } else if (Array.isArray(schema)) {\n if (!Array.isArray(target)) {\n return new AssertError(target, schema.constructor.name, path);\n }\n return findFirstError(target, (value, idx) => {\n return findNotError(schema, (itemSchemaType) => assert(value, itemSchemaType, `${path}.${idx}`));\n });\n } else if (typeof schema === 'object') {\n if (schema instanceof RegExp) {\n if (!schema.test('' + target)) {\n return new AssertError(target, `matching /${schema.source}/`, path);\n }\n } else {\n if (typeof target !== 'object') {\n return new AssertError(target, schema.constructor.name, path);\n }\n if (target === null) {\n return new AssertError(target, 'an object', path);\n }\n if ($keys in schema) {\n const targetKeys = Object.keys(target);\n const assertError = findFirstError(targetKeys, (targetKey) => assert(targetKey, schema[$keys], `${path}.${targetKey}`));\n if (assertError) {\n return assertError;\n }\n }\n if ($values in schema) {\n const targetKeys = Object.keys(target);\n const assertError = findFirstError(targetKeys, (targetKey) =>\n assert(target[targetKey as keyof typeof target], schema[$values], `${path}.${targetKey}`),\n );\n if (assertError) {\n return assertError;\n }\n }\n return findFirstError(Object.keys(schema), (key) => assert(target[key as keyof typeof target], schema[key as keyof typeof target], `${path}.${key}`));\n }\n } else if (target !== schema) {\n return new AssertError(target, schema, path);\n }\n};\n\nexport const ascertain = <T extends Data = DataValue>(schema: Schema<T>, data: T, rootName = '[root]') => {\n const result = assert(data, schema, rootName);\n if (result instanceof AssertError) {\n throw new TypeError(result.toString());\n }\n};\n"],"names":["$keys","$values","AssertError","Context","and","as","ascertain","compile","fromBase64","optional","or","tuple","TypeError","join","errors","separator","value","map","e","expected","path","subject","constructor","JSON","stringify","Operation","schemas","length","name","Or","And","Optional","schema","Tuple","Symbol","for","Buffer","atob","from","toString","MULTIPLIERS","ms","s","m","h","d","w","string","undefined","number","result","parseFloat","Number","isFinite","date","Date","parse","time","matches","match","amount","unit","parseInt","boolean","test","array","delimiter","split","json","base64","Error","registry","varIndex","options","error","push","register","includes","indexOf","unique","prefix","codeGen","context","valuePath","valueAlias","errorsAlias","code","reduceRight","idx","index","registryAlias","Array","isArray","key","orCode","RegExp","keysAlias","vAlias","valuesAlias","keys","Object","rootName","validator","Function","data","findFirstError","i","findNotError","reduce","assert","target","isValue","itemSchemaType","source","targetKeys","assertError","targetKey"],"mappings":"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"}