react-hook-form 7.71.2 → 7.72.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.
- package/dist/__tests__/useFieldArray/dirtyFields.test.d.ts +2 -0
- package/dist/__tests__/useFieldArray/dirtyFields.test.d.ts.map +1 -0
- package/dist/constants.d.ts +5 -0
- package/dist/constants.d.ts.map +1 -1
- package/dist/index.cjs.js +1 -1
- package/dist/index.cjs.js.map +1 -1
- package/dist/index.esm.mjs +158 -59
- package/dist/index.esm.mjs.map +1 -1
- package/dist/index.umd.js +1 -1
- package/dist/index.umd.js.map +1 -1
- package/dist/logic/createFormControl.d.ts.map +1 -1
- package/dist/logic/isNameInFieldArray.d.ts.map +1 -1
- package/dist/logic/updateFieldArrayRootError.d.ts.map +1 -1
- package/dist/react-server.esm.mjs +123 -24
- package/dist/react-server.esm.mjs.map +1 -1
- package/dist/types/errors.d.ts +1 -0
- package/dist/types/errors.d.ts.map +1 -1
- package/dist/types/form.d.ts +7 -3
- package/dist/types/form.d.ts.map +1 -1
- package/dist/types/validator.d.ts +13 -1
- package/dist/types/validator.d.ts.map +1 -1
- package/dist/useFormContext.d.ts.map +1 -1
- package/package.json +21 -21
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createFormControl.d.ts","sourceRoot":"","sources":["../../src/logic/createFormControl.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"createFormControl.d.ts","sourceRoot":"","sources":["../../src/logic/createFormControl.ts"],"names":[],"mappings":"AAOA,OAAO,KAAK,EAaV,WAAW,EAiBX,YAAY,EAIZ,aAAa,EAWd,MAAM,UAAU,CAAC;AAsDlB,wBAAgB,iBAAiB,CAC/B,YAAY,SAAS,WAAW,GAAG,WAAW,EAC9C,QAAQ,GAAG,GAAG,EACd,kBAAkB,GAAG,YAAY,EAEjC,KAAK,GAAE,YAAY,CAAC,YAAY,EAAE,QAAQ,EAAE,kBAAkB,CAAM,GACnE,IAAI,CACL,aAAa,CAAC,YAAY,EAAE,QAAQ,EAAE,kBAAkB,CAAC,EACzD,WAAW,CACZ,GAAG;IACF,WAAW,EAAE,IAAI,CACf,aAAa,CAAC,YAAY,EAAE,QAAQ,EAAE,kBAAkB,CAAC,EACzD,WAAW,CACZ,CAAC;CACH,CAkmDA"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"isNameInFieldArray.d.ts","sourceRoot":"","sources":["../../src/logic/isNameInFieldArray.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,UAAU,CAAC;
|
|
1
|
+
{"version":3,"file":"isNameInFieldArray.d.ts","sourceRoot":"","sources":["../../src/logic/isNameInFieldArray.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,UAAU,CAAC;yBAElC,OAAO,GAAG,CAAC,iBAAiB,CAAC,EAAE,MAAM,iBAAiB;AAAtE,wBAMM"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"updateFieldArrayRootError.d.ts","sourceRoot":"","sources":["../../src/logic/updateFieldArrayRootError.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"updateFieldArrayRootError.d.ts","sourceRoot":"","sources":["../../src/logic/updateFieldArrayRootError.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,UAAU,EACV,WAAW,EACX,WAAW,EACX,iBAAiB,EAClB,MAAM,UAAU,CAAC;yBAKF,CAAC,SAAS,WAAW,GAAG,WAAW,EACjD,QAAQ,WAAW,CAAC,CAAC,CAAC,EACtB,OAAO,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,UAAU,CAAC,CAAC,EAC1C,MAAM,iBAAiB,KACtB,WAAW,CAAC,CAAC,CAAC;AAJjB,wBASE"}
|
|
@@ -10,7 +10,11 @@ var appendErrors = (name, validateAllFieldCriteria, errors, type, message) => va
|
|
|
10
10
|
|
|
11
11
|
const EVENTS = {
|
|
12
12
|
BLUR: 'blur',
|
|
13
|
-
FOCUS_OUT: 'focusout'
|
|
13
|
+
FOCUS_OUT: 'focusout',
|
|
14
|
+
SUBMIT: 'submit',
|
|
15
|
+
TRIGGER: 'trigger',
|
|
16
|
+
VALID: 'valid',
|
|
17
|
+
};
|
|
14
18
|
const VALIDATION_MODE = {
|
|
15
19
|
onBlur: 'onBlur',
|
|
16
20
|
onChange: 'onChange',
|
|
@@ -27,6 +31,8 @@ const INPUT_VALIDATION_RULES = {
|
|
|
27
31
|
required: 'required',
|
|
28
32
|
validate: 'validate',
|
|
29
33
|
};
|
|
34
|
+
const FORM_ERROR_TYPE = 'form';
|
|
35
|
+
const ROOT_ERROR_TYPE = 'root';
|
|
30
36
|
|
|
31
37
|
var isDateObject = (value) => value instanceof Date;
|
|
32
38
|
|
|
@@ -127,8 +133,8 @@ function deepEqual(object1, object2, _internal_visited = new WeakSet()) {
|
|
|
127
133
|
if (key !== 'ref') {
|
|
128
134
|
const val2 = object2[key];
|
|
129
135
|
if ((isDateObject(val1) && isDateObject(val2)) ||
|
|
130
|
-
(isObject(val1)
|
|
131
|
-
|
|
136
|
+
((isObject(val1) || Array.isArray(val1)) &&
|
|
137
|
+
(isObject(val2) || Array.isArray(val2)))
|
|
132
138
|
? !deepEqual(val1, val2, _internal_visited)
|
|
133
139
|
: !Object.is(val1, val2)) {
|
|
134
140
|
return false;
|
|
@@ -401,6 +407,8 @@ function getFieldValue(_f) {
|
|
|
401
407
|
return getFieldValueAs(isUndefined(ref.value) ? _f.ref.value : ref.value, _f);
|
|
402
408
|
}
|
|
403
409
|
|
|
410
|
+
var getNodeParentName = (name) => name.substring(0, name.search(/\.\d+(\.|$)/)) || name;
|
|
411
|
+
|
|
404
412
|
var getResolverOptions = (fieldsNames, _fields, criteriaMode, shouldUseNativeValidation) => {
|
|
405
413
|
const fields = {};
|
|
406
414
|
for (const name of fieldsNames) {
|
|
@@ -452,9 +460,9 @@ var hasValidation = (options) => options.mount &&
|
|
|
452
460
|
options.pattern ||
|
|
453
461
|
options.validate);
|
|
454
462
|
|
|
455
|
-
var
|
|
456
|
-
|
|
457
|
-
|
|
463
|
+
var isNameInFieldArray = (names, name) => name
|
|
464
|
+
.split('.')
|
|
465
|
+
.some((part, index, arr) => !isNaN(Number(part)) && names.has(arr.slice(0, index).join('.')));
|
|
458
466
|
|
|
459
467
|
var isWatched = (name, _names, isBlurEvent) => !isBlurEvent &&
|
|
460
468
|
(_names.watchAll ||
|
|
@@ -563,7 +571,7 @@ var unsetEmptyArray = (ref, name) => !compact(get(ref, name)).length && unset(re
|
|
|
563
571
|
|
|
564
572
|
var updateFieldArrayRootError = (errors, error, name) => {
|
|
565
573
|
const fieldArrayErrors = convertToArrayPayload(get(errors, name));
|
|
566
|
-
set(fieldArrayErrors,
|
|
574
|
+
set(fieldArrayErrors, ROOT_ERROR_TYPE, error[name]);
|
|
567
575
|
set(errors, name, fieldArrayErrors);
|
|
568
576
|
return errors;
|
|
569
577
|
};
|
|
@@ -811,6 +819,7 @@ function createFormControl(props = {}) {
|
|
|
811
819
|
unMount: new Set(),
|
|
812
820
|
array: new Set(),
|
|
813
821
|
watch: new Set(),
|
|
822
|
+
registerName: new Set(),
|
|
814
823
|
};
|
|
815
824
|
let delayErrorCallback;
|
|
816
825
|
let timer = 0;
|
|
@@ -852,7 +861,11 @@ function createFormControl(props = {}) {
|
|
|
852
861
|
_updateIsValidating();
|
|
853
862
|
}
|
|
854
863
|
else {
|
|
855
|
-
isValid = await executeBuiltInValidation(
|
|
864
|
+
isValid = await executeBuiltInValidation({
|
|
865
|
+
fields: _fields,
|
|
866
|
+
onlyCheckValid: true,
|
|
867
|
+
eventType: EVENTS.VALID,
|
|
868
|
+
});
|
|
856
869
|
}
|
|
857
870
|
if (isValid !== _formState.isValid) {
|
|
858
871
|
_subjects.state.next({
|
|
@@ -880,6 +893,11 @@ function createFormControl(props = {}) {
|
|
|
880
893
|
});
|
|
881
894
|
}
|
|
882
895
|
};
|
|
896
|
+
const _updateDirtyFields = (name) => {
|
|
897
|
+
const fullDirtyFields = getDirtyFields(_defaultValues, _formValues);
|
|
898
|
+
const rootName = getNodeParentName(name);
|
|
899
|
+
set(_formState.dirtyFields, rootName, get(fullDirtyFields, rootName));
|
|
900
|
+
};
|
|
883
901
|
const _setFieldArray = (name, values = [], method, args, shouldSetValues = true, shouldUpdateFieldsAndState = true) => {
|
|
884
902
|
if (args && method && !_options.disabled) {
|
|
885
903
|
_state.action = true;
|
|
@@ -901,7 +919,7 @@ function createFormControl(props = {}) {
|
|
|
901
919
|
shouldSetValues && set(_formState.touchedFields, name, touchedFields);
|
|
902
920
|
}
|
|
903
921
|
if (_proxyFormState.dirtyFields || _proxySubscribeFormState.dirtyFields) {
|
|
904
|
-
|
|
922
|
+
_updateDirtyFields(name);
|
|
905
923
|
}
|
|
906
924
|
_subjects.state.next({
|
|
907
925
|
name,
|
|
@@ -1015,8 +1033,7 @@ function createFormControl(props = {}) {
|
|
|
1015
1033
|
};
|
|
1016
1034
|
const _runSchema = async (name) => {
|
|
1017
1035
|
_updateIsValidating(name, true);
|
|
1018
|
-
|
|
1019
|
-
return result;
|
|
1036
|
+
return await _options.resolver(_formValues, _options.context, getResolverOptions(name || _names.mount, _fields, _options.criteriaMode, _options.shouldUseNativeValidation));
|
|
1020
1037
|
};
|
|
1021
1038
|
const executeSchemaAndUpdateState = async (names) => {
|
|
1022
1039
|
const { errors } = await _runSchema(names);
|
|
@@ -1034,9 +1051,55 @@ function createFormControl(props = {}) {
|
|
|
1034
1051
|
}
|
|
1035
1052
|
return errors;
|
|
1036
1053
|
};
|
|
1037
|
-
const
|
|
1054
|
+
const validateForm = async ({ name, eventType, }) => {
|
|
1055
|
+
if (props.validate) {
|
|
1056
|
+
const result = await props.validate({
|
|
1057
|
+
formValues: _formValues,
|
|
1058
|
+
formState: _formState,
|
|
1059
|
+
name,
|
|
1060
|
+
eventType,
|
|
1061
|
+
});
|
|
1062
|
+
if (isObject(result)) {
|
|
1063
|
+
for (const key in result) {
|
|
1064
|
+
const error = result[key];
|
|
1065
|
+
if (error) {
|
|
1066
|
+
setError(`${FORM_ERROR_TYPE}.${key}`, {
|
|
1067
|
+
message: isString(result.message) ? result.message : '',
|
|
1068
|
+
type: INPUT_VALIDATION_RULES.validate,
|
|
1069
|
+
});
|
|
1070
|
+
}
|
|
1071
|
+
}
|
|
1072
|
+
}
|
|
1073
|
+
else if (isString(result) || !result) {
|
|
1074
|
+
setError(FORM_ERROR_TYPE, {
|
|
1075
|
+
message: result || '',
|
|
1076
|
+
type: INPUT_VALIDATION_RULES.validate,
|
|
1077
|
+
});
|
|
1078
|
+
}
|
|
1079
|
+
else {
|
|
1080
|
+
clearErrors(FORM_ERROR_TYPE);
|
|
1081
|
+
}
|
|
1082
|
+
return result;
|
|
1083
|
+
}
|
|
1084
|
+
return true;
|
|
1085
|
+
};
|
|
1086
|
+
const executeBuiltInValidation = async ({ fields, onlyCheckValid, name, eventType, context = {
|
|
1038
1087
|
valid: true,
|
|
1039
|
-
|
|
1088
|
+
runRootValidation: false,
|
|
1089
|
+
}, }) => {
|
|
1090
|
+
if (props.validate) {
|
|
1091
|
+
context.runRootValidation = true;
|
|
1092
|
+
const result = await validateForm({
|
|
1093
|
+
name,
|
|
1094
|
+
eventType,
|
|
1095
|
+
});
|
|
1096
|
+
if (!result) {
|
|
1097
|
+
context.valid = false;
|
|
1098
|
+
if (onlyCheckValid) {
|
|
1099
|
+
return context.valid;
|
|
1100
|
+
}
|
|
1101
|
+
}
|
|
1102
|
+
}
|
|
1040
1103
|
for (const name in fields) {
|
|
1041
1104
|
const field = fields[name];
|
|
1042
1105
|
if (field) {
|
|
@@ -1047,25 +1110,34 @@ function createFormControl(props = {}) {
|
|
|
1047
1110
|
if (isPromiseFunction && _proxyFormState.validatingFields) {
|
|
1048
1111
|
_updateIsValidating([_f.name], true);
|
|
1049
1112
|
}
|
|
1050
|
-
const fieldError = await validateField(field, _names.disabled, _formValues, shouldDisplayAllAssociatedErrors, _options.shouldUseNativeValidation && !
|
|
1113
|
+
const fieldError = await validateField(field, _names.disabled, _formValues, shouldDisplayAllAssociatedErrors, _options.shouldUseNativeValidation && !onlyCheckValid, isFieldArrayRoot);
|
|
1051
1114
|
if (isPromiseFunction && _proxyFormState.validatingFields) {
|
|
1052
1115
|
_updateIsValidating([_f.name]);
|
|
1053
1116
|
}
|
|
1054
1117
|
if (fieldError[_f.name]) {
|
|
1055
1118
|
context.valid = false;
|
|
1056
|
-
if (
|
|
1119
|
+
if (onlyCheckValid) {
|
|
1057
1120
|
break;
|
|
1058
1121
|
}
|
|
1059
1122
|
}
|
|
1060
|
-
!
|
|
1123
|
+
!onlyCheckValid &&
|
|
1061
1124
|
(get(fieldError, _f.name)
|
|
1062
1125
|
? isFieldArrayRoot
|
|
1063
1126
|
? updateFieldArrayRootError(_formState.errors, fieldError, _f.name)
|
|
1064
1127
|
: set(_formState.errors, _f.name, fieldError[_f.name])
|
|
1065
1128
|
: unset(_formState.errors, _f.name));
|
|
1129
|
+
if (props.shouldUseNativeValidation && fieldError[_f.name]) {
|
|
1130
|
+
break;
|
|
1131
|
+
}
|
|
1066
1132
|
}
|
|
1067
1133
|
!isEmptyObject(fieldValue) &&
|
|
1068
|
-
(await executeBuiltInValidation(
|
|
1134
|
+
(await executeBuiltInValidation({
|
|
1135
|
+
context,
|
|
1136
|
+
onlyCheckValid,
|
|
1137
|
+
fields: fieldValue,
|
|
1138
|
+
name: name,
|
|
1139
|
+
eventType,
|
|
1140
|
+
}));
|
|
1069
1141
|
}
|
|
1070
1142
|
}
|
|
1071
1143
|
return context.valid;
|
|
@@ -1176,9 +1248,10 @@ function createFormControl(props = {}) {
|
|
|
1176
1248
|
_proxySubscribeFormState.isDirty ||
|
|
1177
1249
|
_proxySubscribeFormState.dirtyFields) &&
|
|
1178
1250
|
options.shouldDirty) {
|
|
1251
|
+
_updateDirtyFields(name);
|
|
1179
1252
|
_subjects.state.next({
|
|
1180
1253
|
name,
|
|
1181
|
-
dirtyFields:
|
|
1254
|
+
dirtyFields: _formState.dirtyFields,
|
|
1182
1255
|
isDirty: _getDirty(name, cloneValue),
|
|
1183
1256
|
});
|
|
1184
1257
|
}
|
|
@@ -1224,6 +1297,7 @@ function createFormControl(props = {}) {
|
|
|
1224
1297
|
: getEventValue(event);
|
|
1225
1298
|
const isBlurEvent = event.type === EVENTS.BLUR || event.type === EVENTS.FOCUS_OUT;
|
|
1226
1299
|
const shouldSkipValidation = (!hasValidation(field._f) &&
|
|
1300
|
+
!props.validate &&
|
|
1227
1301
|
!_options.resolver &&
|
|
1228
1302
|
!get(_formState.errors, name) &&
|
|
1229
1303
|
!field._f.deps) ||
|
|
@@ -1261,6 +1335,12 @@ function createFormControl(props = {}) {
|
|
|
1261
1335
|
return (shouldRender &&
|
|
1262
1336
|
_subjects.state.next({ name, ...(watched ? {} : fieldState) }));
|
|
1263
1337
|
}
|
|
1338
|
+
if (!_options.resolver && props.validate) {
|
|
1339
|
+
await validateForm({
|
|
1340
|
+
name: name,
|
|
1341
|
+
eventType: event.type,
|
|
1342
|
+
});
|
|
1343
|
+
}
|
|
1264
1344
|
!isBlurEvent && watched && _subjects.state.next({ ..._formState });
|
|
1265
1345
|
if (_options.resolver) {
|
|
1266
1346
|
const { errors } = await _runSchema([name]);
|
|
@@ -1285,7 +1365,12 @@ function createFormControl(props = {}) {
|
|
|
1285
1365
|
}
|
|
1286
1366
|
else if (_proxyFormState.isValid ||
|
|
1287
1367
|
_proxySubscribeFormState.isValid) {
|
|
1288
|
-
isValid = await executeBuiltInValidation(
|
|
1368
|
+
isValid = await executeBuiltInValidation({
|
|
1369
|
+
fields: _fields,
|
|
1370
|
+
onlyCheckValid: true,
|
|
1371
|
+
name: name,
|
|
1372
|
+
eventType: event.type,
|
|
1373
|
+
});
|
|
1289
1374
|
}
|
|
1290
1375
|
}
|
|
1291
1376
|
}
|
|
@@ -1318,12 +1403,19 @@ function createFormControl(props = {}) {
|
|
|
1318
1403
|
else if (name) {
|
|
1319
1404
|
validationResult = (await Promise.all(fieldNames.map(async (fieldName) => {
|
|
1320
1405
|
const field = get(_fields, fieldName);
|
|
1321
|
-
return await executeBuiltInValidation(
|
|
1406
|
+
return await executeBuiltInValidation({
|
|
1407
|
+
fields: field && field._f ? { [fieldName]: field } : field,
|
|
1408
|
+
eventType: EVENTS.TRIGGER,
|
|
1409
|
+
});
|
|
1322
1410
|
}))).every(Boolean);
|
|
1323
1411
|
!(!validationResult && !_formState.isValid) && _setValid();
|
|
1324
1412
|
}
|
|
1325
1413
|
else {
|
|
1326
|
-
validationResult = isValid = await executeBuiltInValidation(
|
|
1414
|
+
validationResult = isValid = await executeBuiltInValidation({
|
|
1415
|
+
fields: _fields,
|
|
1416
|
+
name,
|
|
1417
|
+
eventType: EVENTS.TRIGGER,
|
|
1418
|
+
});
|
|
1327
1419
|
}
|
|
1328
1420
|
_subjects.state.next({
|
|
1329
1421
|
...(!isString(name) ||
|
|
@@ -1469,6 +1561,7 @@ function createFormControl(props = {}) {
|
|
|
1469
1561
|
const register = (name, options = {}) => {
|
|
1470
1562
|
let field = get(_fields, name);
|
|
1471
1563
|
const disabledIsDefined = isBoolean(options.disabled) || isBoolean(_options.disabled);
|
|
1564
|
+
const shouldRevalidateRemount = !_names.registerName.has(name) && field && !field._f.mount;
|
|
1472
1565
|
set(_fields, name, {
|
|
1473
1566
|
...(field || {}),
|
|
1474
1567
|
_f: {
|
|
@@ -1479,7 +1572,7 @@ function createFormControl(props = {}) {
|
|
|
1479
1572
|
},
|
|
1480
1573
|
});
|
|
1481
1574
|
_names.mount.add(name);
|
|
1482
|
-
if (field) {
|
|
1575
|
+
if (field && !shouldRevalidateRemount) {
|
|
1483
1576
|
_setDisabledField({
|
|
1484
1577
|
disabled: isBoolean(options.disabled)
|
|
1485
1578
|
? options.disabled
|
|
@@ -1509,7 +1602,9 @@ function createFormControl(props = {}) {
|
|
|
1509
1602
|
onBlur: onChange,
|
|
1510
1603
|
ref: (ref) => {
|
|
1511
1604
|
if (ref) {
|
|
1605
|
+
_names.registerName.add(name);
|
|
1512
1606
|
register(name, options);
|
|
1607
|
+
_names.registerName.delete(name);
|
|
1513
1608
|
field = get(_fields, name);
|
|
1514
1609
|
const fieldRef = isUndefined(ref.value)
|
|
1515
1610
|
? ref.querySelectorAll
|
|
@@ -1588,14 +1683,17 @@ function createFormControl(props = {}) {
|
|
|
1588
1683
|
fieldValues = cloneObject(values);
|
|
1589
1684
|
}
|
|
1590
1685
|
else {
|
|
1591
|
-
await executeBuiltInValidation(
|
|
1686
|
+
await executeBuiltInValidation({
|
|
1687
|
+
fields: _fields,
|
|
1688
|
+
eventType: EVENTS.SUBMIT,
|
|
1689
|
+
});
|
|
1592
1690
|
}
|
|
1593
1691
|
if (_names.disabled.size) {
|
|
1594
1692
|
for (const name of _names.disabled) {
|
|
1595
1693
|
unset(fieldValues, name);
|
|
1596
1694
|
}
|
|
1597
1695
|
}
|
|
1598
|
-
unset(_formState.errors,
|
|
1696
|
+
unset(_formState.errors, ROOT_ERROR_TYPE);
|
|
1599
1697
|
if (isEmptyObject(_formState.errors)) {
|
|
1600
1698
|
_subjects.state.next({
|
|
1601
1699
|
errors: {},
|
|
@@ -1719,6 +1817,7 @@ function createFormControl(props = {}) {
|
|
|
1719
1817
|
mount: keepStateOptions.keepDirtyValues ? _names.mount : new Set(),
|
|
1720
1818
|
unMount: new Set(),
|
|
1721
1819
|
array: new Set(),
|
|
1820
|
+
registerName: new Set(),
|
|
1722
1821
|
disabled: new Set(),
|
|
1723
1822
|
watch: new Set(),
|
|
1724
1823
|
watchAll: false,
|