I am catching errors from api and showing them in form, and that is working fine. But the problem is when I change one field in form all errors disappear. For form I am using Formik and for validation Yup.
const handleSubmit = (values, {setSubmitting, setFieldError, setStatus}) => {
someApiCall(values)
.then(
() => {
},
(error) => {
// example of setting error
setFieldError('email', 'email is already used');
})
.finally(() => {
setSubmitting(false)
});
};
I tried with adding third parametar false to setFieldError, but nothing changed.
Here's my working example: https://codesandbox.io/s/formik-example-dynamic-server-rendered-values-1uv4l
There's a callback validate
available in Formik: https://jaredpalmer.com/formik/docs/api/formik#validate-values-values-formikerrors-values-promise-any using which you can probably try to do something like below.
I initiated emailsAlreadyInUse
with empty array and then in your API call once error gets returned then add that user to the array and once user uses the same email again and tried to validate, although it will pass Yup validation but it will be caught in validate
callback which I believe runs after Yup validation (though I could be wrong but in your case doesn't matter).
const emailsAlreadyInUse= [];
const handleSubmit = (values, {
setSubmitting,
setFieldError,
setStatus
}) => {
someApiCall(values)
.then(
() => {
// Do something
// possibly reset emailsAlreadyInUse if needed unless component is going to be unmounted.
},
(error) => {
// example of setting error
setFieldError('email', 'email is already used');
// Assuming error object you receive has data object that has email property
emailsAlreadyInUse.push(error.data.email);
})
.finally(() => {
setSubmitting(false)
});
};
<Formik
...
...
validate = {
values => {
let errors = {};
if (emailsAlreadyInUse.includes(values.email)) {
errors.email = 'email is already used';
}
return errors;
}
}
/>