Re-render causes validateOnMount to run again with initialValues, producing incorrect validation results.
Video of re-render triggering validation with initialValues
This may be intended behavior, but I found it pretty unexpected, especially since the name of the prop is validatesOnMount. The docs do mention that it runs when initialValues changes, so it is behaving as documented. It's a little not-so-obvious though.
validateOnMount should only run when the component initially mounts.
https://codesandbox.io/s/formik-example-no1kc
Remove initialValues from the dependencies array for the validateOnMount useEffect.
If the current behavior is desired, perhaps add a more explicit warning about the need to memoize initialValues when using validateOnMount.
| Software | Version(s) |
| ---------------- | ---------- |
| Formik | 2.0.4
| React | 16.12.0
| TypeScript | 3.7.2
| Browser | Chrome
| npm/Yarn | Yarn
| Operating System | OS X
I have a similar problem, validateOnMount is causing a render loop.
the problem is this https://github.com/jaredpalmer/formik/blob/48dd0c7be1a4763df8217e79e72ffdef89447aaa/packages/formik/src/Formik.tsx#L358
you need to useMemo your initialValues
but even using this, it is causing rerender
This only seems to be a problem from version 2.0.4 onwards. Has anyone else found this?
I've been tearing my hair out over this today before finally figuring out what was going on. I also feel it's quite unintuitive that initialValues is used as a dependency for the initial validation useEffect.
I ended up working around it by not creating the initialValues object inside the render function, but instead creating it one level up and passing it down into my component that is using Formik.
I believe the behavior here should be the same as with enableReinitialize which uses deep object comparison under the hood.
I am running into this as well. My initialValues are being used instead of the actual Formik field values for validation leading to the form being invalid when it is really valid.
Anyone found a solution?
Hi @arianitu we've created a work around which is to "freeze" initial values so that they never change, thus never trigger this validation effect:
function useFreeze(initializer) {
const [frozenValue] = useState(initializer);
return frozenValue;
}
// wherever formik is used: (Not able to be used with `withFormik`)
const {
errors,
touched,
values,
} = useFormik({
initialValues: useFreeze({
question: defaultValues.question || "",
answer: defaultValues.answer || "",
}),
...
});
Thank you for your solution @andycarrell , but I don't really want to do that everywhere, this bug is awful, we may downgrade to 1.x.
@jaredpalmer this seems like a pretty bad bug in 2.x, shouldn't initialValues just set the values of Formik and then validation should only act on the actual values?
All our forms are affected since we want Save buttons etc to be disabled before a user can interact with them. With this bug, it breaks all our forms because we sometimes pass values of inputs up the chain and cause re-renders.
@andycarrell considering this is from November, I don't think it's going to get fixed soon, so I guess I'll use your solution. This also works:
let initialValues = useMemo(() => {
return {
name: '',
size: ''
}
}, []);
Yep @arianitu this works fine for me.
Haven't tested it yet, but this looks to me like it would fix the bug: https://github.com/jaredpalmer/formik/pull/2243
Most helpful comment
@andycarrell considering this is from November, I don't think it's going to get fixed soon, so I guess I'll use your solution. This also works: