Do you want to request a feature or report a bug?
Report a bug
What is the current behavior?
react-dom logs an error to the console when .checkValidity() is called on a form element (from a ref) inside the render part of a function component. The error is only logged when .checkValidity() returns false. This is the error message:
Warning: unstable_flushDiscreteUpdates: Cannot flush updates when React is already rendering.
CodeSandbox: https://codesandbox.io/s/pensive-colden-ipuwi
What is the expected behavior?
Nothing should be logged to the console.
A more informative error should be logged to the console (see comment).
Which versions of React, and which browser / OS are affected by this issue? Did this work in previous versions of React?
React/ReactDOM: 6.10.0 - 6.12.0 (this worked as expected in 6.9.0)
Browser: Chrome 78, Firefox 70
OS: any
You are not supposed to touch DOM in render. Something like this might work for your case:
const [isValid, setIsValid] = useState(false);
// ...
return (
<form onSubmit={e => e.preventDefault()} ref={formRef} onChange={() => { setIsValid(formRef.current.checkValidity()) }}>
// ...
Ah that makes sense.
In that case, I'd say this error message could be improved to indicate what the developer did wrong (i.e. reading from the DOM during render).
While you should be cautious about reading from the DOM in render, that's not the reason this warning fires. It's specifically because calling checkValidity fires the invalid event. This event is caught and handled by React, which is already trying to handle the input event, so this warning fires.
React is correctly warning you about something you shouldn't do, but I agree that the error message here is not good. Maybe it can be caught earlier, or this scenario prevented in some other way.
This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contribution.
Closing this issue after a prolonged period of inactivity. If this issue is still present in the latest release, please create a new issue with up-to-date information. Thank you!
Closing this issue after a prolonged period of inactivity. If this issue is still present in the latest release, please create a new issue with up-to-date information. Thank you!
Most helpful comment
You are not supposed to touch DOM in render. Something like this might work for your case: