@naturalcycles/nodejs-lib 15.58.0 → 15.59.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.
@@ -39,9 +39,9 @@ export declare class AjvSchema<IN = unknown, OUT = IN> {
39
39
  *
40
40
  * Returned object is always the same object (`===`) that was passed, so it is returned just for convenience.
41
41
  */
42
- validate(input: IN, opt?: AjvValidationOptions): OUT;
43
- isValid(input: IN, opt?: AjvValidationOptions): boolean;
44
- getValidationResult(input: IN, opt?: AjvValidationOptions): ValidationFunctionResult<OUT, AjvValidationError>;
42
+ validate(input: IN, opt?: AjvValidationOptions<IN>): OUT;
43
+ isValid(input: IN, opt?: AjvValidationOptions<IN>): boolean;
44
+ getValidationResult(input: IN, opt?: AjvValidationOptions<IN>): ValidationFunctionResult<OUT, AjvValidationError>;
45
45
  getValidationFunction(): ValidationFunction<IN, OUT, AjvValidationError>;
46
46
  static isSchemaWithCachedAjvSchema<Base, IN, OUT>(schema: Base): schema is WithCachedAjvSchema<Base, IN, OUT>;
47
47
  static cacheAjvSchema<Base extends AnyObject, IN, OUT>(schema: Base, ajvSchema: AjvSchema<IN, OUT>): WithCachedAjvSchema<Base, IN, OUT>;
@@ -54,7 +54,7 @@ export declare const HIDDEN_AJV_SCHEMA: unique symbol;
54
54
  export type WithCachedAjvSchema<Base, IN, OUT> = Base & {
55
55
  [HIDDEN_AJV_SCHEMA]: AjvSchema<IN, OUT>;
56
56
  };
57
- export interface AjvValidationOptions {
57
+ export interface AjvValidationOptions<IN> {
58
58
  /**
59
59
  * Defaults to true,
60
60
  * because that's how AJV works by default,
@@ -73,6 +73,16 @@ export interface AjvValidationOptions {
73
73
  mutateInput?: boolean;
74
74
  inputName?: string;
75
75
  inputId?: string;
76
+ /**
77
+ * Function that returns "original input".
78
+ * What is original input?
79
+ * It's an input in its original non-mutated form.
80
+ * Why is it needed?
81
+ * Because we mutates the Input here. And after its been mutated - we no longer
82
+ * can include it "how it was" in an error message. So, for that reason we'll use
83
+ * `getOriginalInput()`, if it's provided.
84
+ */
85
+ getOriginalInput?: () => IN;
76
86
  }
77
87
  export interface AjvSchemaCfg {
78
88
  /**
@@ -108,7 +108,7 @@ export class AjvSchema {
108
108
  const item = opt.mutateInput !== false || typeof input !== 'object'
109
109
  ? input // mutate
110
110
  : _deepCopy(input); // not mutate
111
- const valid = fn(item); // mutates item
111
+ const valid = fn(item); // mutates item, but not input
112
112
  _typeCast(item);
113
113
  if (valid)
114
114
  return [null, item];
@@ -122,7 +122,8 @@ export class AjvSchema {
122
122
  });
123
123
  // Note: if we mutated the input already, e.g stripped unknown properties,
124
124
  // the error message Input would contain already mutated object print, such as Input: {}
125
- const inputStringified = _inspect(input, { maxLen: 4000 });
125
+ // Unless `getOriginalInput` function is provided - then it will be used to preserve the Input pureness.
126
+ const inputStringified = _inspect(opt.getOriginalInput?.() || input, { maxLen: 4000 });
126
127
  message = [message, 'Input: ' + inputStringified].join(separator);
127
128
  const err = new AjvValidationError(message, _filterNullishValues({
128
129
  errors,
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@naturalcycles/nodejs-lib",
3
3
  "type": "module",
4
- "version": "15.58.0",
4
+ "version": "15.59.0",
5
5
  "dependencies": {
6
6
  "@naturalcycles/js-lib": "^15",
7
7
  "@types/js-yaml": "^4",
@@ -120,13 +120,13 @@ export class AjvSchema<IN = unknown, OUT = IN> {
120
120
  *
121
121
  * Returned object is always the same object (`===`) that was passed, so it is returned just for convenience.
122
122
  */
123
- validate(input: IN, opt: AjvValidationOptions = {}): OUT {
123
+ validate(input: IN, opt: AjvValidationOptions<IN> = {}): OUT {
124
124
  const [err, output] = this.getValidationResult(input, opt)
125
125
  if (err) throw err
126
126
  return output
127
127
  }
128
128
 
129
- isValid(input: IN, opt?: AjvValidationOptions): boolean {
129
+ isValid(input: IN, opt?: AjvValidationOptions<IN>): boolean {
130
130
  // todo: we can make it both fast and non-mutating by using Ajv
131
131
  // with "removeAdditional" and "useDefaults" disabled.
132
132
  const [err] = this.getValidationResult(input, opt)
@@ -135,7 +135,7 @@ export class AjvSchema<IN = unknown, OUT = IN> {
135
135
 
136
136
  getValidationResult(
137
137
  input: IN,
138
- opt: AjvValidationOptions = {},
138
+ opt: AjvValidationOptions<IN> = {},
139
139
  ): ValidationFunctionResult<OUT, AjvValidationError> {
140
140
  const fn = this.getAJVValidateFunction()
141
141
 
@@ -144,7 +144,7 @@ export class AjvSchema<IN = unknown, OUT = IN> {
144
144
  ? input // mutate
145
145
  : _deepCopy(input) // not mutate
146
146
 
147
- const valid = fn(item) // mutates item
147
+ const valid = fn(item) // mutates item, but not input
148
148
  _typeCast<OUT>(item)
149
149
  if (valid) return [null, item]
150
150
 
@@ -165,7 +165,8 @@ export class AjvSchema<IN = unknown, OUT = IN> {
165
165
 
166
166
  // Note: if we mutated the input already, e.g stripped unknown properties,
167
167
  // the error message Input would contain already mutated object print, such as Input: {}
168
- const inputStringified = _inspect(input, { maxLen: 4000 })
168
+ // Unless `getOriginalInput` function is provided - then it will be used to preserve the Input pureness.
169
+ const inputStringified = _inspect(opt.getOriginalInput?.() || input, { maxLen: 4000 })
169
170
  message = [message, 'Input: ' + inputStringified].join(separator)
170
171
 
171
172
  const err = new AjvValidationError(
@@ -245,7 +246,7 @@ export type WithCachedAjvSchema<Base, IN, OUT> = Base & {
245
246
  [HIDDEN_AJV_SCHEMA]: AjvSchema<IN, OUT>
246
247
  }
247
248
 
248
- export interface AjvValidationOptions {
249
+ export interface AjvValidationOptions<IN> {
249
250
  /**
250
251
  * Defaults to true,
251
252
  * because that's how AJV works by default,
@@ -264,6 +265,16 @@ export interface AjvValidationOptions {
264
265
  mutateInput?: boolean
265
266
  inputName?: string
266
267
  inputId?: string
268
+ /**
269
+ * Function that returns "original input".
270
+ * What is original input?
271
+ * It's an input in its original non-mutated form.
272
+ * Why is it needed?
273
+ * Because we mutates the Input here. And after its been mutated - we no longer
274
+ * can include it "how it was" in an error message. So, for that reason we'll use
275
+ * `getOriginalInput()`, if it's provided.
276
+ */
277
+ getOriginalInput?: () => IN
267
278
  }
268
279
 
269
280
  export interface AjvSchemaCfg {