@oscarpalmer/jhunal 0.25.0 → 0.27.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/dist/constants.d.mts +15 -7
- package/dist/constants.mjs +15 -6
- package/dist/handler/base.handler.d.mts +6 -0
- package/dist/{validator/base.validator.mjs → handler/base.handler.mjs} +5 -5
- package/dist/handler/function.handler.d.mts +6 -0
- package/dist/handler/function.handler.mjs +9 -0
- package/dist/handler/object.handler.d.mts +7 -0
- package/dist/handler/object.handler.mjs +130 -0
- package/dist/handler/schema.handler.d.mts +7 -0
- package/dist/handler/schema.handler.mjs +16 -0
- package/dist/handler/type.handler.d.mts +9 -0
- package/dist/handler/type.handler.mjs +71 -0
- package/dist/handler/validator.handler.d.mts +10 -0
- package/dist/handler/validator.handler.mjs +34 -0
- package/dist/handler/value.handler.d.mts +14 -0
- package/dist/handler/value.handler.mjs +98 -0
- package/dist/helpers/message.helper.d.mts +9 -7
- package/dist/helpers/message.helper.mjs +34 -16
- package/dist/helpers/misc.helper.d.mts +13 -6
- package/dist/helpers/misc.helper.mjs +12 -4
- package/dist/helpers/report.helper.d.mts +23 -0
- package/dist/helpers/report.helper.mjs +19 -0
- package/dist/helpers/result.helper.d.mts +7 -0
- package/dist/helpers/result.helper.mjs +17 -0
- package/dist/index.d.mts +172 -73
- package/dist/index.mjs +396 -235
- package/dist/models/infer.model.d.mts +11 -8
- package/dist/models/misc.model.d.mts +8 -8
- package/dist/models/schematic.plain.model.d.mts +10 -9
- package/dist/models/schematic.typed.model.d.mts +1 -1
- package/dist/models/transform.model.d.mts +2 -2
- package/dist/models/validation.model.d.mts +56 -25
- package/dist/models/validation.model.mjs +11 -2
- package/dist/schema.d.mts +34 -34
- package/dist/schema.mjs +11 -19
- package/dist/validator.d.mts +83 -0
- package/dist/validator.mjs +25 -0
- package/package.json +2 -2
- package/src/constants.ts +30 -8
- package/src/{validator/base.validator.ts → handler/base.handler.ts} +6 -6
- package/src/handler/function.handler.ts +9 -0
- package/src/handler/object.handler.ts +245 -0
- package/src/handler/schema.handler.ts +25 -0
- package/src/handler/type.handler.ts +160 -0
- package/src/handler/validator.handler.ts +49 -0
- package/src/handler/value.handler.ts +202 -0
- package/src/helpers/message.helper.ts +72 -30
- package/src/helpers/misc.helper.ts +23 -6
- package/src/helpers/report.helper.ts +72 -0
- package/src/helpers/result.helper.ts +33 -0
- package/src/index.ts +1 -0
- package/src/models/infer.model.ts +31 -13
- package/src/models/misc.model.ts +9 -9
- package/src/models/schematic.plain.model.ts +12 -9
- package/src/models/schematic.typed.model.ts +3 -3
- package/src/models/transform.model.ts +2 -2
- package/src/models/validation.model.ts +75 -37
- package/src/schema.ts +44 -70
- package/src/validator.ts +135 -0
- package/dist/validator/base.validator.d.mts +0 -6
- package/dist/validator/function.validator.d.mts +0 -6
- package/dist/validator/function.validator.mjs +0 -9
- package/dist/validator/named.handler.d.mts +0 -6
- package/dist/validator/named.handler.mjs +0 -23
- package/dist/validator/named.validator.d.mts +0 -7
- package/dist/validator/named.validator.mjs +0 -38
- package/dist/validator/object.validator.d.mts +0 -7
- package/dist/validator/object.validator.mjs +0 -185
- package/dist/validator/schematic.validator.d.mts +0 -7
- package/dist/validator/schematic.validator.mjs +0 -16
- package/src/validator/function.validator.ts +0 -9
- package/src/validator/named.handler.ts +0 -65
- package/src/validator/named.validator.ts +0 -61
- package/src/validator/object.validator.ts +0 -366
- package/src/validator/schematic.validator.ts +0 -25
package/src/validator.ts
ADDED
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
import type {Constructor} from '@oscarpalmer/atoms/models';
|
|
2
|
+
import type {Result} from '@oscarpalmer/atoms/result/models';
|
|
3
|
+
import {PROPERTY_VALIDATOR} from './constants';
|
|
4
|
+
import {getValidatorHandler} from './handler/validator.handler';
|
|
5
|
+
import {isResult} from './helpers/result.helper';
|
|
6
|
+
import type {InferValidatorValue} from './models/infer.model';
|
|
7
|
+
import type {Values, ValueType} from './models/misc.model';
|
|
8
|
+
import type {
|
|
9
|
+
ValidationHandler,
|
|
10
|
+
ValidationHandlerType,
|
|
11
|
+
Validators,
|
|
12
|
+
ValueValidation,
|
|
13
|
+
} from './models/validation.model';
|
|
14
|
+
|
|
15
|
+
export class Validator<Value> {
|
|
16
|
+
declare private readonly $validator: true;
|
|
17
|
+
|
|
18
|
+
readonly #handler: ValidationHandler;
|
|
19
|
+
|
|
20
|
+
constructor(handler: ValidationHandler, types: ValidationHandlerType[]) {
|
|
21
|
+
Object.defineProperty(this, PROPERTY_VALIDATOR, {
|
|
22
|
+
value: true,
|
|
23
|
+
});
|
|
24
|
+
|
|
25
|
+
this.#handler = handler;
|
|
26
|
+
|
|
27
|
+
validatorHandlers.set(this, handler);
|
|
28
|
+
validatorTypes.set(this, types);
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
/**
|
|
32
|
+
* Is the value valid?
|
|
33
|
+
*
|
|
34
|
+
* Will assert that the value is valid and throws an error if it does not
|
|
35
|
+
* @param value Value to validate
|
|
36
|
+
* @returns `true` if the value is valid, otherwise throws an error
|
|
37
|
+
*/
|
|
38
|
+
is(value: unknown, reporting: 'throw'): asserts value is Value;
|
|
39
|
+
|
|
40
|
+
/**
|
|
41
|
+
* Is the value valid?
|
|
42
|
+
*
|
|
43
|
+
* Will validate that the value is valid and return a result of `true` or validation information for the first validation failure
|
|
44
|
+
* @param value Value to validate
|
|
45
|
+
* @return Result holding `true` or validation information
|
|
46
|
+
*/
|
|
47
|
+
is(value: unknown, reporting: 'result'): Result<Value, ValueValidation>;
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Is the value valid?
|
|
51
|
+
* @param value Value to validate
|
|
52
|
+
* @returns `true` if the value is valid, otherwise `false`
|
|
53
|
+
*/
|
|
54
|
+
is(value: unknown, reporting?: 'none'): value is Value;
|
|
55
|
+
|
|
56
|
+
is(value: unknown, options?: unknown): unknown {
|
|
57
|
+
return isResult(this.#handler, value, options);
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Create a validator for value types
|
|
63
|
+
* @param types Types to validate against
|
|
64
|
+
* @param validators Custom validators to use for validation
|
|
65
|
+
* @returns Validator
|
|
66
|
+
*/
|
|
67
|
+
export function validator<
|
|
68
|
+
Types extends Array<Constructor | ((value: unknown) => boolean) | ValueType>,
|
|
69
|
+
>(types: Types, validators?: Validators): Validator<InferValidatorValue<Types>>;
|
|
70
|
+
|
|
71
|
+
/**
|
|
72
|
+
* Create a validator for a constructor
|
|
73
|
+
* @param constructor Constructor to validate against
|
|
74
|
+
* @returns Validator
|
|
75
|
+
*/
|
|
76
|
+
export function validator<Instance>(constructor: Constructor<Instance>): Validator<Instance>;
|
|
77
|
+
|
|
78
|
+
/**
|
|
79
|
+
* Create a validator for a callback
|
|
80
|
+
* @param callback Callback for validation
|
|
81
|
+
* @returns Validator
|
|
82
|
+
*/
|
|
83
|
+
export function validator<Value>(callback: (value: unknown) => value is Value): Validator<Value>;
|
|
84
|
+
|
|
85
|
+
/**
|
|
86
|
+
* Create a validator for a callback
|
|
87
|
+
* @param callback Callback for validation
|
|
88
|
+
* @returns Validator
|
|
89
|
+
*/
|
|
90
|
+
export function validator<Value>(callback: (value: unknown) => boolean): Validator<Value>;
|
|
91
|
+
|
|
92
|
+
/**
|
|
93
|
+
* Create a validator for a type
|
|
94
|
+
* @param type Type to validate against
|
|
95
|
+
* @param validators Custom validators to use for validation
|
|
96
|
+
* @returns Validator
|
|
97
|
+
*/
|
|
98
|
+
export function validator<Type extends ValueType>(
|
|
99
|
+
type: Type,
|
|
100
|
+
validators?:
|
|
101
|
+
| ((value: Values[Type]) => boolean)
|
|
102
|
+
| Array<(value: Values[Type]) => boolean>
|
|
103
|
+
| Record<Type, ((value: Values[Type]) => boolean) | Array<(value: Values[Type]) => boolean>>,
|
|
104
|
+
): Validator<Values[Type]>;
|
|
105
|
+
|
|
106
|
+
/**
|
|
107
|
+
* Create a validator for value types
|
|
108
|
+
* @param types Types to validate against
|
|
109
|
+
* @param validators Custom validators to use for validation
|
|
110
|
+
* @returns Validator
|
|
111
|
+
*/
|
|
112
|
+
export function validator<Types extends ValueType[]>(
|
|
113
|
+
types: Types,
|
|
114
|
+
validators?: Validators,
|
|
115
|
+
): Validator<unknown>;
|
|
116
|
+
|
|
117
|
+
/**
|
|
118
|
+
* Create a validator for an array of items
|
|
119
|
+
* @param type Type of items in the array
|
|
120
|
+
* @returns Validator
|
|
121
|
+
*/
|
|
122
|
+
export function validator<Item>(type: 'array'): Validator<Item[]>;
|
|
123
|
+
|
|
124
|
+
export function validator(value: unknown, validators?: unknown): Validator<unknown> {
|
|
125
|
+
if (value instanceof Validator) {
|
|
126
|
+
return value;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
const {handler, types} = getValidatorHandler(value, validators);
|
|
130
|
+
|
|
131
|
+
return new Validator(handler, types);
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
export const validatorHandlers = new WeakMap<Validator<unknown>, ValidationHandler>();
|
|
135
|
+
export const validatorTypes = new WeakMap<Validator<unknown>, ValidationHandlerType[]>();
|
|
@@ -1,9 +0,0 @@
|
|
|
1
|
-
import { instanceOf } from "../helpers/misc.helper.mjs";
|
|
2
|
-
import { isConstructor } from "@oscarpalmer/atoms/is";
|
|
3
|
-
//#region src/validator/function.validator.ts
|
|
4
|
-
function getFunctionValidator(fn) {
|
|
5
|
-
const validator = isConstructor(fn) ? instanceOf(fn) : fn;
|
|
6
|
-
return (input) => validator(input) ? true : [];
|
|
7
|
-
}
|
|
8
|
-
//#endregion
|
|
9
|
-
export { getFunctionValidator };
|
|
@@ -1,6 +0,0 @@
|
|
|
1
|
-
import { NamedValidatorHandlers } from "../models/validation.model.mjs";
|
|
2
|
-
|
|
3
|
-
//#region src/validator/named.handler.d.ts
|
|
4
|
-
declare function getNamedHandlers(original: unknown, prefix: string, allowed: boolean): NamedValidatorHandlers;
|
|
5
|
-
//#endregion
|
|
6
|
-
export { getNamedHandlers };
|
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
import { PROPERTY_VALIDATORS, SCHEMATIC_MESSAGE_SCHEMA_INVALID_PROPERTY_DISALLOWED, SCHEMATIC_MESSAGE_VALIDATOR_INVALID_KEY, SCHEMATIC_MESSAGE_VALIDATOR_INVALID_TYPE, SCHEMATIC_MESSAGE_VALIDATOR_INVALID_VALUE, TYPE_ALL } from "../constants.mjs";
|
|
2
|
-
import { isPlainObject } from "@oscarpalmer/atoms/is";
|
|
3
|
-
//#region src/validator/named.handler.ts
|
|
4
|
-
function getNamedHandlers(original, prefix, allowed) {
|
|
5
|
-
const handlers = {};
|
|
6
|
-
if (original == null) return handlers;
|
|
7
|
-
if (!allowed) throw new TypeError(SCHEMATIC_MESSAGE_SCHEMA_INVALID_PROPERTY_DISALLOWED.replace("<>", prefix).replace("<>", PROPERTY_VALIDATORS));
|
|
8
|
-
if (!isPlainObject(original)) throw new TypeError(SCHEMATIC_MESSAGE_VALIDATOR_INVALID_TYPE);
|
|
9
|
-
const keys = Object.keys(original);
|
|
10
|
-
const { length } = keys;
|
|
11
|
-
for (let index = 0; index < length; index += 1) {
|
|
12
|
-
const key = keys[index];
|
|
13
|
-
if (!TYPE_ALL.has(key)) throw new TypeError(SCHEMATIC_MESSAGE_VALIDATOR_INVALID_KEY.replace("<>", key));
|
|
14
|
-
const value = original[key];
|
|
15
|
-
handlers[key] = (Array.isArray(value) ? value : [value]).map((item) => {
|
|
16
|
-
if (typeof item !== "function") throw new TypeError(SCHEMATIC_MESSAGE_VALIDATOR_INVALID_VALUE.replace("<>", key).replace("<>", prefix));
|
|
17
|
-
return item;
|
|
18
|
-
});
|
|
19
|
-
}
|
|
20
|
-
return handlers;
|
|
21
|
-
}
|
|
22
|
-
//#endregion
|
|
23
|
-
export { getNamedHandlers };
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
import { NamedValidatorHandlers, ValidationInformationKey, Validator } from "../models/validation.model.mjs";
|
|
2
|
-
import { ValueName } from "../models/misc.model.mjs";
|
|
3
|
-
|
|
4
|
-
//#region src/validator/named.validator.d.ts
|
|
5
|
-
declare function getNamedValidator(key: ValidationInformationKey, name: ValueName, handlers: NamedValidatorHandlers): Validator;
|
|
6
|
-
//#endregion
|
|
7
|
-
export { getNamedValidator };
|
|
@@ -1,38 +0,0 @@
|
|
|
1
|
-
import { getInputPropertyValidatorMessage } from "../helpers/message.helper.mjs";
|
|
2
|
-
//#region src/validator/named.validator.ts
|
|
3
|
-
function getNamedValidator(key, name, handlers) {
|
|
4
|
-
const validator = namedValidators[name];
|
|
5
|
-
const named = handlers[name] ?? [];
|
|
6
|
-
const { length } = named;
|
|
7
|
-
return (input, parameters) => {
|
|
8
|
-
if (!validator(input)) return [];
|
|
9
|
-
for (let index = 0; index < length; index += 1) {
|
|
10
|
-
const handler = named[index];
|
|
11
|
-
if (handler(input) === true) continue;
|
|
12
|
-
const information = {
|
|
13
|
-
key,
|
|
14
|
-
validator,
|
|
15
|
-
message: getInputPropertyValidatorMessage(key.full, name, index, length),
|
|
16
|
-
value: input
|
|
17
|
-
};
|
|
18
|
-
parameters.information?.push(information);
|
|
19
|
-
return parameters.reporting.none ? [] : [information];
|
|
20
|
-
}
|
|
21
|
-
return true;
|
|
22
|
-
};
|
|
23
|
-
}
|
|
24
|
-
const namedValidators = {
|
|
25
|
-
array: Array.isArray,
|
|
26
|
-
bigint: (value) => typeof value === "bigint",
|
|
27
|
-
boolean: (value) => typeof value === "boolean",
|
|
28
|
-
date: (value) => value instanceof Date,
|
|
29
|
-
function: (value) => typeof value === "function",
|
|
30
|
-
null: (value) => value === null,
|
|
31
|
-
number: (value) => typeof value === "number",
|
|
32
|
-
object: (value) => typeof value === "object" && value !== null,
|
|
33
|
-
string: (value) => typeof value === "string",
|
|
34
|
-
symbol: (value) => typeof value === "symbol",
|
|
35
|
-
undefined: (value) => value === void 0
|
|
36
|
-
};
|
|
37
|
-
//#endregion
|
|
38
|
-
export { getNamedValidator };
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
import { ValidationInformationKey, Validator } from "../models/validation.model.mjs";
|
|
2
|
-
import { PlainObject } from "@oscarpalmer/atoms/models";
|
|
3
|
-
|
|
4
|
-
//#region src/validator/object.validator.d.ts
|
|
5
|
-
declare function getObjectValidator(original: PlainObject, origin?: ValidationInformationKey, fromType?: boolean): Validator;
|
|
6
|
-
//#endregion
|
|
7
|
-
export { getObjectValidator };
|
|
@@ -1,185 +0,0 @@
|
|
|
1
|
-
import { PROPERTY_DEFAULT, PROPERTY_REQUIRED, PROPERTY_TYPE, PROPERTY_VALIDATORS, SCHEMATIC_MESSAGE_SCHEMA_INVALID_EMPTY, TYPE_ALL } from "../constants.mjs";
|
|
2
|
-
import { getParameters, isSchema } from "../helpers/misc.helper.mjs";
|
|
3
|
-
import { SchematicError, ValidationError } from "../models/validation.model.mjs";
|
|
4
|
-
import { getDefaultRequiredMessage, getDefaultTypeMessage, getDisallowedMessage, getInputPropertyMissingMessage, getInputPropertyTypeMessage, getInputTypeMessage, getRequiredMessage, getSchematicPropertyNullableMessage, getSchematicPropertyTypeMessage, getUnknownKeysMessage } from "../helpers/message.helper.mjs";
|
|
5
|
-
import { getBaseValidator } from "./base.validator.mjs";
|
|
6
|
-
import { getFunctionValidator } from "./function.validator.mjs";
|
|
7
|
-
import { getNamedHandlers } from "./named.handler.mjs";
|
|
8
|
-
import { getNamedValidator } from "./named.validator.mjs";
|
|
9
|
-
import { getSchemaValidator } from "./schematic.validator.mjs";
|
|
10
|
-
import { isPlainObject } from "@oscarpalmer/atoms/is";
|
|
11
|
-
import { join } from "@oscarpalmer/atoms/string";
|
|
12
|
-
import { clone } from "@oscarpalmer/atoms/value/clone";
|
|
13
|
-
//#region src/validator/object.validator.ts
|
|
14
|
-
function getDefaults(obj, key, allowed) {
|
|
15
|
-
if (!("$default" in obj)) return;
|
|
16
|
-
if (!allowed) throw new SchematicError(getDisallowedMessage(key, PROPERTY_DEFAULT));
|
|
17
|
-
return { value: obj[PROPERTY_DEFAULT] };
|
|
18
|
-
}
|
|
19
|
-
function getDisallowedProperty(obj) {
|
|
20
|
-
if ("$default" in obj) return PROPERTY_DEFAULT;
|
|
21
|
-
if ("$required" in obj) return PROPERTY_REQUIRED;
|
|
22
|
-
if ("$type" in obj) return PROPERTY_TYPE;
|
|
23
|
-
if ("$validators" in obj) return PROPERTY_VALIDATORS;
|
|
24
|
-
}
|
|
25
|
-
function getObjectValidator(original, origin, fromType) {
|
|
26
|
-
const keys = Object.keys(original);
|
|
27
|
-
const keysLength = keys.length;
|
|
28
|
-
if (keysLength === 0) throw new SchematicError(SCHEMATIC_MESSAGE_SCHEMA_INVALID_EMPTY);
|
|
29
|
-
if (fromType ?? false) {
|
|
30
|
-
const property = getDisallowedProperty(original);
|
|
31
|
-
if (property != null) throw new SchematicError(getDisallowedMessage(origin.full, property));
|
|
32
|
-
}
|
|
33
|
-
const set = /* @__PURE__ */ new Set();
|
|
34
|
-
const items = [];
|
|
35
|
-
for (let keyIndex = 0; keyIndex < keysLength; keyIndex += 1) {
|
|
36
|
-
const key = keys[keyIndex];
|
|
37
|
-
const value = original[key];
|
|
38
|
-
if (value == null) throw new SchematicError(getSchematicPropertyNullableMessage(join([origin?.full, key], ".")));
|
|
39
|
-
const prefixedKey = origin == null ? key : join([origin.full, key], ".");
|
|
40
|
-
const fullKey = {
|
|
41
|
-
full: prefixedKey,
|
|
42
|
-
short: key
|
|
43
|
-
};
|
|
44
|
-
let handlers = {};
|
|
45
|
-
let required = true;
|
|
46
|
-
let typed = false;
|
|
47
|
-
let defaults;
|
|
48
|
-
let types;
|
|
49
|
-
const validators = [];
|
|
50
|
-
if (isPlainObject(value)) {
|
|
51
|
-
typed = PROPERTY_TYPE in value;
|
|
52
|
-
const type = typed ? value[PROPERTY_TYPE] : value;
|
|
53
|
-
defaults = getDefaults(value, prefixedKey, typed);
|
|
54
|
-
handlers = getNamedHandlers(value[PROPERTY_VALIDATORS], prefixedKey, typed);
|
|
55
|
-
required = getRequired(value, prefixedKey, typed) ?? required;
|
|
56
|
-
types = Array.isArray(type) ? type : [type];
|
|
57
|
-
} else types = Array.isArray(value) ? value : [value];
|
|
58
|
-
if (types.length === 0) throw new SchematicError(getSchematicPropertyTypeMessage(prefixedKey));
|
|
59
|
-
const typesLength = types.length;
|
|
60
|
-
for (let typeIndex = 0; typeIndex < typesLength; typeIndex += 1) {
|
|
61
|
-
const type = types[typeIndex];
|
|
62
|
-
let validator;
|
|
63
|
-
switch (true) {
|
|
64
|
-
case typeof type === "function":
|
|
65
|
-
validator = getFunctionValidator(type);
|
|
66
|
-
break;
|
|
67
|
-
case isPlainObject(type):
|
|
68
|
-
validator = getObjectValidator(type, fullKey, typed);
|
|
69
|
-
break;
|
|
70
|
-
case isSchema(type):
|
|
71
|
-
validator = getSchemaValidator(type);
|
|
72
|
-
break;
|
|
73
|
-
case TYPE_ALL.has(type):
|
|
74
|
-
validator = getNamedValidator(fullKey, type, handlers);
|
|
75
|
-
break;
|
|
76
|
-
default: throw new SchematicError(getSchematicPropertyTypeMessage(prefixedKey));
|
|
77
|
-
}
|
|
78
|
-
validators.push(validator);
|
|
79
|
-
}
|
|
80
|
-
required = required && !types.includes("undefined");
|
|
81
|
-
if (defaults != null && !required) throw new SchematicError(getDefaultRequiredMessage(prefixedKey));
|
|
82
|
-
const validator = getBaseValidator(validators);
|
|
83
|
-
if (defaults != null && Array.isArray(validator(defaults.value, getParameters(), false))) throw new SchematicError(getDefaultTypeMessage(prefixedKey, types));
|
|
84
|
-
items.push({
|
|
85
|
-
defaults,
|
|
86
|
-
required,
|
|
87
|
-
types,
|
|
88
|
-
validator,
|
|
89
|
-
key: fullKey
|
|
90
|
-
});
|
|
91
|
-
set.add(key);
|
|
92
|
-
}
|
|
93
|
-
const validatorsLength = items.length;
|
|
94
|
-
return (input, parameters, get) => {
|
|
95
|
-
if (!isPlainObject(input)) {
|
|
96
|
-
if (origin != null) return [];
|
|
97
|
-
const information = {
|
|
98
|
-
key: {
|
|
99
|
-
full: "",
|
|
100
|
-
short: ""
|
|
101
|
-
},
|
|
102
|
-
value: input,
|
|
103
|
-
message: getInputTypeMessage(input)
|
|
104
|
-
};
|
|
105
|
-
if (parameters.reporting.throw) throw new ValidationError([information]);
|
|
106
|
-
parameters.information?.push(information);
|
|
107
|
-
return [information];
|
|
108
|
-
}
|
|
109
|
-
if (parameters.strict) {
|
|
110
|
-
const unknownKeys = Object.keys(input).filter((key) => !set.has(key));
|
|
111
|
-
if (unknownKeys.length > 0) {
|
|
112
|
-
const information = {
|
|
113
|
-
key: origin ?? {
|
|
114
|
-
full: "",
|
|
115
|
-
short: ""
|
|
116
|
-
},
|
|
117
|
-
message: getUnknownKeysMessage(unknownKeys),
|
|
118
|
-
value: input
|
|
119
|
-
};
|
|
120
|
-
if (parameters.reporting.throw) throw new ValidationError([information]);
|
|
121
|
-
parameters.information?.push(information);
|
|
122
|
-
return [information];
|
|
123
|
-
}
|
|
124
|
-
}
|
|
125
|
-
const allInformation = [];
|
|
126
|
-
const output = {};
|
|
127
|
-
for (let validatorIndex = 0; validatorIndex < validatorsLength; validatorIndex += 1) {
|
|
128
|
-
const { defaults, key, required, types, validator } = items[validatorIndex];
|
|
129
|
-
const value = input[key.short];
|
|
130
|
-
if (value === void 0) {
|
|
131
|
-
if (required) {
|
|
132
|
-
if (get && defaults != null) {
|
|
133
|
-
output[key.short] = clone(defaults.value);
|
|
134
|
-
continue;
|
|
135
|
-
}
|
|
136
|
-
if (parameters.reporting.none) return [];
|
|
137
|
-
const information = {
|
|
138
|
-
key,
|
|
139
|
-
value,
|
|
140
|
-
message: getInputPropertyMissingMessage(key.full, types)
|
|
141
|
-
};
|
|
142
|
-
if (parameters.reporting.throw) throw new ValidationError([information]);
|
|
143
|
-
parameters.information?.push(information);
|
|
144
|
-
if (parameters.reporting.all) {
|
|
145
|
-
allInformation.push(information);
|
|
146
|
-
continue;
|
|
147
|
-
}
|
|
148
|
-
return [information];
|
|
149
|
-
}
|
|
150
|
-
continue;
|
|
151
|
-
}
|
|
152
|
-
const previousOutput = parameters.output;
|
|
153
|
-
parameters.output = output;
|
|
154
|
-
const result = validator(value, parameters, get);
|
|
155
|
-
parameters.output = previousOutput;
|
|
156
|
-
if (result === true) {
|
|
157
|
-
if (get && !isPlainObject(value)) output[key.short] = parameters.clone ? clone(value) : value;
|
|
158
|
-
continue;
|
|
159
|
-
}
|
|
160
|
-
if (parameters.reporting.none) return [];
|
|
161
|
-
const information = typeof result !== "boolean" && result.length > 0 ? result : [{
|
|
162
|
-
key,
|
|
163
|
-
value,
|
|
164
|
-
message: getInputPropertyTypeMessage(key.full, types, value)
|
|
165
|
-
}];
|
|
166
|
-
if (parameters.reporting.throw) throw new ValidationError(information);
|
|
167
|
-
if (parameters.reporting.all) {
|
|
168
|
-
allInformation.push(...information);
|
|
169
|
-
continue;
|
|
170
|
-
}
|
|
171
|
-
return information;
|
|
172
|
-
}
|
|
173
|
-
if (get) if (origin == null) parameters.output = output;
|
|
174
|
-
else parameters.output[origin.short] = output;
|
|
175
|
-
return allInformation.length === 0 ? true : allInformation;
|
|
176
|
-
};
|
|
177
|
-
}
|
|
178
|
-
function getRequired(obj, key, allowed) {
|
|
179
|
-
if (!("$required" in obj)) return;
|
|
180
|
-
if (!allowed) throw new SchematicError(getDisallowedMessage(key, PROPERTY_REQUIRED));
|
|
181
|
-
if (typeof obj["$required"] !== "boolean") throw new SchematicError(getRequiredMessage(key));
|
|
182
|
-
return obj[PROPERTY_REQUIRED];
|
|
183
|
-
}
|
|
184
|
-
//#endregion
|
|
185
|
-
export { getObjectValidator };
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
import { Validator } from "../models/validation.model.mjs";
|
|
2
|
-
import { Schema } from "../schema.mjs";
|
|
3
|
-
|
|
4
|
-
//#region src/validator/schematic.validator.d.ts
|
|
5
|
-
declare function getSchemaValidator(schematic: Schema<unknown>): Validator;
|
|
6
|
-
//#endregion
|
|
7
|
-
export { getSchemaValidator };
|
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
import { schemaValidators } from "../schema.mjs";
|
|
2
|
-
import { isPlainObject } from "@oscarpalmer/atoms/is";
|
|
3
|
-
//#region src/validator/schematic.validator.ts
|
|
4
|
-
function getSchemaValidator(schematic) {
|
|
5
|
-
const validator = schemaValidators.get(schematic);
|
|
6
|
-
return (input, parameters, get) => {
|
|
7
|
-
let result;
|
|
8
|
-
if (isPlainObject(input)) result = validator(input, parameters, get);
|
|
9
|
-
else result = [];
|
|
10
|
-
if (result === true) return result;
|
|
11
|
-
parameters.information?.push(...result);
|
|
12
|
-
return result;
|
|
13
|
-
};
|
|
14
|
-
}
|
|
15
|
-
//#endregion
|
|
16
|
-
export { getSchemaValidator };
|
|
@@ -1,9 +0,0 @@
|
|
|
1
|
-
import {isConstructor} from '@oscarpalmer/atoms/is';
|
|
2
|
-
import {instanceOf} from '../helpers/misc.helper';
|
|
3
|
-
import type {Validator} from '../models/validation.model';
|
|
4
|
-
|
|
5
|
-
export function getFunctionValidator(fn: Function): Validator {
|
|
6
|
-
const validator = isConstructor(fn) ? instanceOf(fn) : fn;
|
|
7
|
-
|
|
8
|
-
return input => (validator(input) ? true : []);
|
|
9
|
-
}
|
|
@@ -1,65 +0,0 @@
|
|
|
1
|
-
import {isPlainObject} from '@oscarpalmer/atoms/is';
|
|
2
|
-
import {
|
|
3
|
-
PROPERTY_VALIDATORS,
|
|
4
|
-
SCHEMATIC_MESSAGE_SCHEMA_INVALID_PROPERTY_DISALLOWED,
|
|
5
|
-
SCHEMATIC_MESSAGE_VALIDATOR_INVALID_KEY,
|
|
6
|
-
SCHEMATIC_MESSAGE_VALIDATOR_INVALID_TYPE,
|
|
7
|
-
SCHEMATIC_MESSAGE_VALIDATOR_INVALID_VALUE,
|
|
8
|
-
TEMPLATE_PATTERN,
|
|
9
|
-
TYPE_ALL,
|
|
10
|
-
} from '../constants';
|
|
11
|
-
import type {ValueName} from '../models/misc.model';
|
|
12
|
-
import type {NamedValidatorHandlers} from '../models/validation.model';
|
|
13
|
-
|
|
14
|
-
export function getNamedHandlers(
|
|
15
|
-
original: unknown,
|
|
16
|
-
prefix: string,
|
|
17
|
-
allowed: boolean,
|
|
18
|
-
): NamedValidatorHandlers {
|
|
19
|
-
const handlers: NamedValidatorHandlers = {};
|
|
20
|
-
|
|
21
|
-
if (original == null) {
|
|
22
|
-
return handlers;
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
if (!allowed) {
|
|
26
|
-
throw new TypeError(
|
|
27
|
-
SCHEMATIC_MESSAGE_SCHEMA_INVALID_PROPERTY_DISALLOWED.replace(
|
|
28
|
-
TEMPLATE_PATTERN,
|
|
29
|
-
prefix,
|
|
30
|
-
).replace(TEMPLATE_PATTERN, PROPERTY_VALIDATORS),
|
|
31
|
-
);
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
if (!isPlainObject(original)) {
|
|
35
|
-
throw new TypeError(SCHEMATIC_MESSAGE_VALIDATOR_INVALID_TYPE);
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
const keys = Object.keys(original);
|
|
39
|
-
const {length} = keys;
|
|
40
|
-
|
|
41
|
-
for (let index = 0; index < length; index += 1) {
|
|
42
|
-
const key = keys[index];
|
|
43
|
-
|
|
44
|
-
if (!TYPE_ALL.has(key as never)) {
|
|
45
|
-
throw new TypeError(SCHEMATIC_MESSAGE_VALIDATOR_INVALID_KEY.replace(TEMPLATE_PATTERN, key));
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
const value = original[key];
|
|
49
|
-
|
|
50
|
-
handlers[key as ValueName] = (Array.isArray(value) ? value : [value]).map(item => {
|
|
51
|
-
if (typeof item !== 'function') {
|
|
52
|
-
throw new TypeError(
|
|
53
|
-
SCHEMATIC_MESSAGE_VALIDATOR_INVALID_VALUE.replace(TEMPLATE_PATTERN, key).replace(
|
|
54
|
-
TEMPLATE_PATTERN,
|
|
55
|
-
prefix,
|
|
56
|
-
),
|
|
57
|
-
);
|
|
58
|
-
}
|
|
59
|
-
|
|
60
|
-
return item;
|
|
61
|
-
});
|
|
62
|
-
}
|
|
63
|
-
|
|
64
|
-
return handlers;
|
|
65
|
-
}
|
|
@@ -1,61 +0,0 @@
|
|
|
1
|
-
import {getInputPropertyValidatorMessage} from '../helpers/message.helper';
|
|
2
|
-
import type {ValueName} from '../models/misc.model';
|
|
3
|
-
import type {
|
|
4
|
-
NamedValidatorHandlers,
|
|
5
|
-
NamedValidators,
|
|
6
|
-
ValidationInformation,
|
|
7
|
-
ValidationInformationKey,
|
|
8
|
-
Validator,
|
|
9
|
-
} from '../models/validation.model';
|
|
10
|
-
|
|
11
|
-
export function getNamedValidator(
|
|
12
|
-
key: ValidationInformationKey,
|
|
13
|
-
name: ValueName,
|
|
14
|
-
handlers: NamedValidatorHandlers,
|
|
15
|
-
): Validator {
|
|
16
|
-
const validator = namedValidators[name];
|
|
17
|
-
|
|
18
|
-
const named = handlers[name] ?? [];
|
|
19
|
-
const {length} = named;
|
|
20
|
-
|
|
21
|
-
return (input, parameters) => {
|
|
22
|
-
if (!validator(input)) {
|
|
23
|
-
return [];
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
for (let index = 0; index < length; index += 1) {
|
|
27
|
-
const handler = named[index];
|
|
28
|
-
|
|
29
|
-
if (handler(input) === true) {
|
|
30
|
-
continue;
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
const information: ValidationInformation = {
|
|
34
|
-
key,
|
|
35
|
-
validator,
|
|
36
|
-
message: getInputPropertyValidatorMessage(key.full, name, index, length),
|
|
37
|
-
value: input,
|
|
38
|
-
};
|
|
39
|
-
|
|
40
|
-
parameters.information?.push(information);
|
|
41
|
-
|
|
42
|
-
return parameters.reporting.none ? [] : [information];
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
return true;
|
|
46
|
-
};
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
const namedValidators: NamedValidators = {
|
|
50
|
-
array: Array.isArray,
|
|
51
|
-
bigint: value => typeof value === 'bigint',
|
|
52
|
-
boolean: value => typeof value === 'boolean',
|
|
53
|
-
date: value => value instanceof Date,
|
|
54
|
-
function: value => typeof value === 'function',
|
|
55
|
-
null: value => value === null,
|
|
56
|
-
number: value => typeof value === 'number',
|
|
57
|
-
object: value => typeof value === 'object' && value !== null,
|
|
58
|
-
string: value => typeof value === 'string',
|
|
59
|
-
symbol: value => typeof value === 'symbol',
|
|
60
|
-
undefined: value => value === undefined,
|
|
61
|
-
};
|