npm ERESOLVE Unable to Resolve Dependency Tree: How to Fix It
npm error code ERESOLVE
npm error ERESOLVE unable to resolve dependency tree
npm error
npm error While resolving: my-app@1.0.0
npm error Found: react@19.2.0
npm error node_modules/react
npm error react@"^19.0.0" from the root project
npm error
npm error Could not resolve dependency:
npm error peer react@"^16.9.0 || ^17 || ^18" from react-datepicker@6.9.0
npm error node_modules/react-datepicker
npm error react-datepicker@"6.9.0" from the root project
(Older npm versions print the same thing with npm ERR! at the start of each line.)
This is a peer dependency conflict. A peer dependency is a package saying "I don't bundle React, I use yours — and yours must be one of these versions." Since npm 7, npm installs peer dependencies automatically and refuses to build a tree that breaks one. Here, your app uses React 19 and react-datepicker@6.9.0 only promises to work with React 16.9 to 18.
Read the error
Three lines tell you everything:
- Found: what you have —
react@19.2.0, required by the root project (yourpackage.json). - Could not resolve dependency: the conflicting requirement —
peer react@"^16.9.0 || ^17 || ^18". - from: who's asking —
react-datepicker@6.9.0.
The caret ranges matter: ^18 means 18.x only, so React 19 is outside it even if the library would probably work.
Fix 1: upgrade the package that's behind (best)
Usually a newer release of the library already supports your version. Check what the latest version accepts:
npm view react-datepicker@latest peerDependencies
{ react: '^16.9.0 || ^17 || ^18 || ^19 || ^19.0.0-rc', … }
The current major accepts React 19, so upgrading fixes it (read the changelog — a major version can change the API):
npm install react-datepicker@latest
No newer release? Check the library's issue tracker — peer range bumps often sit in a pull request or a prerelease (npm view <package> dist-tags).
Fix 2: match the version it wants
If you just upgraded React (or ESLint, or TypeScript) and a key library hasn't caught up, staying one major version back for now is a legitimate choice:
npm install react@18 react-dom@18
Fix 3: override the peer range for one package
If you've checked that the library works with your version and you just need npm to accept it, use overrides (npm 8.3+) in package.json. This is targeted: it changes the rule for one package, and the reason is written down in your repository.
{
"overrides": {
"react-datepicker": {
"react": "$react",
"react-dom": "$react-dom"
}
}
}
$react means "whatever version my own dependencies ask for". Run npm install again; if the existing lockfile keeps the old resolution, delete package-lock.json and node_modules and reinstall.
Fix 4: --legacy-peer-deps
npm install --legacy-peer-deps
This brings back npm 6 behaviour: peer dependencies are ignored entirely — not installed automatically, not checked. The install succeeds, and you take responsibility for providing compatible versions. To make it stick for everyone working on the project (and your CI), put it in .npmrc:
legacy-peer-deps=true
It's a blunt tool: it silences every peer conflict, including future ones you'd want to know about. Prefer overrides when only one package is the problem.
Fix 5: --force (last resort)
npm install --force
--force overrides the conflict and installs whatever it can, with no promise the result works together — in the worst case, two copies of a package end up in the tree. For libraries that rely on a single shared instance — React, with its hooks, is the classic case — two copies cause runtime errors such as "Invalid hook call". Use it to unblock yourself, not as the permanent fix.
Which one to use
| Situation | Fix |
|---|---|
| A newer version of the library supports your version | Upgrade it |
| You just bumped a major version and a key library lags | Pin the previous major for now |
| You've confirmed the library works anyway | overrides for that package |
| Many old packages, legacy project | --legacy-peer-deps in .npmrc |
| Need an install right now, will fix properly later | --force |
Why it works in CI but not locally (or the reverse)
npm ci installs exactly what package-lock.json describes. If the lockfile was generated with --legacy-peer-deps but CI doesn't use the flag, or the reverse, one of them fails. Put the setting in .npmrc and commit it so every install behaves the same.
pnpm and Yarn report most peer conflicts as warnings rather than failing the install, which is why the same project can install cleanly with them and fail with npm. The conflict is still there either way.