Skip to content

Commit

Permalink
Merge pull request #163 from binary-butterfly/fix-on-error-for-array-…
Browse files Browse the repository at this point in the history
…fields

Make ArrayValidator call onError function if any contained values have an error
  • Loading branch information
DysphoricUnicorn authored Jul 8, 2024
2 parents 49191be + 309f3da commit 7390f5d
Show file tree
Hide file tree
Showing 5 changed files with 33 additions and 13 deletions.
6 changes: 5 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -934,7 +934,10 @@ This will validate the child fields `foo` and `number` with a String- and Number
This validator is used when your data model contains multiple of the same fields. When the validation fails, it will return an array with
all the tests results for its children in it.

It has to be constructed with Validator that is used for the field's children as the first param.
It has to be constructed with Validator that is used for the field's children as the first param.
In addition to the default params, there is an additional `recursiveOnError` constructor param that lets you control if
the `onError` function should be called if contained fields have an error. This is false by default as it is a newly added
feature and enabling it by default would be a breaking API change.

Available methods:

Expand All @@ -948,6 +951,7 @@ Available methods:
Use `{{min}}` and/ or `{{max}}` to include the minimum and/ or maximum amount of children in your custom error string respectively.
- `validateWithoutRecursion(values, otherValues, siblings)` This function allows you to validate the array entries non recursively.
Note that it only works on Array and ObjectValidators since other validators are not recursive by design.
- `setRecursiveOnError(newRecursiveOnError)` This function allows you to control if the onError function should be called if contained fields have an error.

Example:

Expand Down
4 changes: 2 additions & 2 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "formifly",
"version": "2.8.6",
"version": "2.9.0",
"description": "React form handling as light as a butterfly",
"main": "dist/formifly.umd.js",
"module": "dist/formifly.js",
Expand Down
12 changes: 12 additions & 0 deletions src/js/__tests__/classes/ArrayValidator.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -147,3 +147,15 @@ test('Test ArrayValidator uses correct translation namespace', () => {
validator.validate('string' as any, {}, {}, t as unknown as TFunction);
expect(t).toHaveBeenCalledWith('formifly:array');
});

test('Test ArrayValidator calls onError function if contained element does not validate', () => {
const onError = vi.fn();
const validator = new ArrayValidator(new StringValidator().maxLength(1), undefined, undefined, onError, undefined, true);

validator.validate(['bla', '1', 'abc']);
expect(onError).toHaveBeenCalledOnce();

validator.setRecursiveOnError(false);
validator.validate(['bla', '1', 'abc']);
expect(onError).toHaveBeenCalledOnce(); // Make sure it still was only called once
});
22 changes: 13 additions & 9 deletions src/js/classes/ArrayValidator.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,23 +24,23 @@ class ArrayValidator<T extends BaseValidator<any>> extends BaseValidator<ValueOf
public minChildCount: number = 0;
public maxChildCount: number = Number.POSITIVE_INFINITY;
public defaultInputType: InputType = 'select';
public recursiveOnError: boolean = false;

/**
* Validate an array of fields
* @param {BaseValidator} of
* @param {String} [defaultMessage]
* @param {MutationFunction} [mutationFunc]
* @param {ErrorFunction} [onError]
* @param {Dependent} [dependent]
*/
constructor(of: T,
defaultMessage?: string,
mutationFunc?: MutationFunction,
onError?: ErrorFunction,
dependent?: Dependent) {
dependent?: Dependent,
recursiveOnError = false
) {
super([], defaultMessage, mutationFunc, onError, dependent);
this.of = of;
this.propType = PropTypes.arrayOf(of.getPropType());
this.recursiveOnError = recursiveOnError;
}

public setRecursiveOnError(newRecursiveOnError: boolean): void {
this.recursiveOnError = newRecursiveOnError;
}

/**
Expand Down Expand Up @@ -204,6 +204,10 @@ class ArrayValidator<T extends BaseValidator<any>> extends BaseValidator<ValueOf
}
}

if (!allOk && this.recursiveOnError && this.onError) {
this.onError(values, otherValues);
}

return allOk ? [true, testValues] : [false, tests];
}
}
Expand Down

0 comments on commit 7390f5d

Please sign in to comment.