-
Notifications
You must be signed in to change notification settings - Fork 46.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Throw if React and React DOM versions don't match #29236
Throw if React and React DOM versions don't match #29236
Conversation
The latest updates on your projects. Learn more about Vercel for Git ↗︎
|
Comparing: 4ec6a6f...38bc3c5 Critical size changesIncludes critical production bundles, as well as any change greater than 2%:
Significant size changesIncludes any change greater than 0.2%: Expand to show |
afb7de3
to
d7c40ca
Compare
if (isomorphicReactPackageVersion !== reactDOMPackageVersion) { | ||
// TODO: Do we have a canoncical documentation page for this? | ||
throw new Error( | ||
'Incompatible React versions: The "react" and "react-dom" packages must ' + |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In a perfect world we'd also detect environment mismatches e.g. importing react-dom
with the react-server
condition while react
is being imported without the react-server
condition. Maybe we encode the environment in the version string e.g. 19.0.0-abc-123+react-server
? Though that wouldn't tell you explcitly that the environment mismatched not the version.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We could add another internal field (or check for the presence of a server-only API, and vice versa), but I'm less concerned about that one since it's only the tip of the iceberg of what you have to do to configure a Server Components set-up correctly. For a similar reason I didn't add a check to React Native because nobody really imports the React Native renderer directly; it's configured by some sort of framework.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we actually add it for React Native too? Too often the RN sync are using the wrong versions together, which caused issues when landing breaking changes
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Like, RN installs the renderer, but the template still allows using your own version of react
, and we should catch that. This will start erroring in the OSS build on land, but that needs to get fixed before the next RN npm release.
d7c40ca
to
8ad45be
Compare
export function ensureCorrectIsomorphicReactVersion() { | ||
const isomorphicReactPackageVersion = IsomorphicReactPackage.version; | ||
if (isomorphicReactPackageVersion !== reactDOMPackageVersion) { | ||
// TODO: Do we have a canoncical documentation page for this? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Closest is https://legacy.reactjs.org/warnings/invalid-hook-call-warning.html#mismatching-versions-of-react-and-react-dom and https://react.dev/warnings/invalid-hook-call-warning#mismatching-versions-of-react-and-react-dom. But these are just about a React version that's too low or duplicate React modules not explicitly about version mismatch. For example, package managers that auto-install peer dependencies will result in multiple versions of React if the specified version of react
and react-dom
don't match.
So maybe we include version mismatch in that section and link to it?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just added react.dev/warnings/version-mismatch
, @acdlite can we add that URL to the error? reactjs/react.dev#6909
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It just redirects for now, but I'll follow up with a proper warning page
8ad45be
to
e8b016c
Compare
|
Weren't we going to delete react-is entirely though? :D |
Some design system libraries need at least support for |
React has |
Another prominent use case is Jest snapshot testing, as reported in #28813 (comment). A version mismatch might break those tests because they rely on |
I think what |
*/ | ||
|
||
import reactDOMPackageVersion from 'shared/ReactVersion'; | ||
import * as IsomorphicReactPackage from 'react'; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Since we compile to CJS this doesn't matter much but it might be nice to import {version} from "react"
so that it doesn't pull in every export and disables dead export elimination.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've been doing it this way based on this comment. Not sure if it still applies:
react/packages/react-reconciler/src/Scheduler.js
Lines 10 to 15 in e8b016c
// This module only exists as an ESM wrapper around the external CommonJS | |
// Scheduler dependency. Notice that we're intentionally not using named imports | |
// because Rollup would use dynamic dispatch for CommonJS interop named imports. | |
// When we switch to ESM, we can delete this module. | |
import * as Scheduler from 'scheduler'; | |
Throw an error during module initialization if the version of the "react-dom" package does not match the version of "react". We used to be more relaxed about this, because the "react" package changed so infrequently. However, we now have many more features that rely on an internal protocol between the two packages, including Hooks, Float, and the compiler runtime. So it's important that both packages are versioned in lockstep. Before this change, a version mismatch would often result in a cryptic internal error with no indication of the root cause. Instead, we will now compare the versions during module initialization and immediately throw an error to catch mistakes as early as possible and provide a clear error message.
e8b016c
to
38bc3c5
Compare
Throw an error during module initialization if the version of the "react-dom" package does not match the version of "react". We used to be more relaxed about this, because the "react" package changed so infrequently. However, we now have many more features that rely on an internal protocol between the two packages, including Hooks, Float, and the compiler runtime. So it's important that both packages are versioned in lockstep. Before this change, a version mismatch would often result in a cryptic internal error with no indication of the root cause. Instead, we will now compare the versions during module initialization and immediately throw an error to catch mistakes as early as possible and provide a clear error message. DiffTrain build for commit 681a4aa.
Throw an error during module initialization if the version of the "react-dom" package does not match the version of "react". We used to be more relaxed about this, because the "react" package changed so infrequently. However, we now have many more features that rely on an internal protocol between the two packages, including Hooks, Float, and the compiler runtime. So it's important that both packages are versioned in lockstep. Before this change, a version mismatch would often result in a cryptic internal error with no indication of the root cause. Instead, we will now compare the versions during module initialization and immediately throw an error to catch mistakes as early as possible and provide a clear error message. DiffTrain build for [681a4aa](681a4aa)
Throw an error during module initialization if the version of the "react-dom" package does not match the version of "react". We used to be more relaxed about this, because the "react" package changed so infrequently. However, we now have many more features that rely on an internal protocol between the two packages, including Hooks, Float, and the compiler runtime. So it's important that both packages are versioned in lockstep. Before this change, a version mismatch would often result in a cryptic internal error with no indication of the root cause. Instead, we will now compare the versions during module initialization and immediately throw an error to catch mistakes as early as possible and provide a clear error message.
#29236 caused issues for internal syncs at Meta, because we were computing version numbers using file hashes (to eliminate "no-op" internal sync commits). The problem is that since version numbers may not be consistent across synced files (e.g. if some files have not changed in recent commits), the newly introduced version mismatch check fails. There's some more work that needs to be done here to restore the benefits of file-specific hashing, but for now this simply reverts the content hash changes from the following PRs: - #28633 (95319ab) - #28590 (37676ab) - #28582 (cb076b5) - #26734 (5dd90c5) - #26331 (3cad3a5)
#29236 caused issues for internal syncs at Meta, because we were computing version numbers using file hashes (to eliminate "no-op" internal sync commits). The problem is that since version numbers may not be consistent across synced files (e.g. if some files have not changed in recent commits), the newly introduced version mismatch check fails. There's some more work that needs to be done here to restore the benefits of file-specific hashing, but for now this simply reverts the content hash changes from the following PRs: - #28633 (95319ab) - #28590 (37676ab) - #28582 (cb076b5) - #26734 (5dd90c5) - #26331 (3cad3a5) DiffTrain build for [5bd4031](5bd4031)
#29236 caused issues for internal syncs at Meta, because we were computing version numbers using file hashes (to eliminate "no-op" internal sync commits). The problem is that since version numbers may not be consistent across synced files (e.g. if some files have not changed in recent commits), the newly introduced version mismatch check fails. There's some more work that needs to be done here to restore the benefits of file-specific hashing, but for now this simply reverts the content hash changes from the following PRs: - #28633 (95319ab) - #28590 (37676ab) - #28582 (cb076b5) - #26734 (5dd90c5) - #26331 (3cad3a5) DiffTrain build for commit 5bd4031.
Throw an error during module initialization if the version of the "react-dom" package does not match the version of "react".
We used to be more relaxed about this, because the "react" package changed so infrequently. However, we now have many more features that rely on an internal protocol between the two packages, including Hooks, Float, and the compiler runtime. So it's important that both packages are versioned in lockstep.
Before this change, a version mismatch would often result in a cryptic internal error with no indication of the root cause.
Instead, we will now compare the versions during module initialization and immediately throw an error to catch mistakes as early as possible and provide a clear error message.