Description
React version: 18.3.1, 18.0.0
Does not occur in React 19, but we can't use React 19.
Summary
I am fully expecting this to be programmer error, but this behavior deeply puzzles me and I can't find any documented reason for it. If this isn't a bug in React, I would definitely consider it a bug in React documentation :)
As far as I can tell, this code follows all of the rules of hooks and documented invariants:
function App() {
const _id = useId() // If commented out, no warning.
const [prevValue, setPrevValue] = useState(false)
if (prevValue === false) setPrevValue(true) // If commented out, no warning.
return <Inner />
}
// If this component's body is copied into `App`, no warning.
function Inner() {
const id = useId() // <---- NOT STABLE!
return <div id={id} />
}
However, it fails with a hydration mismatch error:
client.js:2427 Warning: Prop `id` did not match. Server: ":R6:" Client: ":R2:" Error Component Stack
at div (<anonymous>)
at Inner (client.js:23592:40)
at App (client.js:23596:41)
at body (<anonymous>)
at html (<anonymous>)
at Html (<anonymous>)
Steps To Reproduce
I created a GitHub repo with a minimal reproduction. Steps to run are in the README: https://github.com/kognise/react-reproduction
Alternately, you should be able to see the same behavior by copying the top code sample into any server-rendered (and hydrated) React app.
The current behavior
React prints the warning Prop `id` did not match. Server: ":R6:" Client: ":R2:"
.
The expected behavior
I would expect this to just work with no issues.
Modifying the snippet as commented makes the warning go away.
Thanks!