🔧 Error Fixes
· 5 min read
Last updated on

npm Peer Dependency Error — What It Means and How to Fix It


npm ERR! ERESOLVE unable to resolve dependency tree
npm ERR! Could not resolve dependency:
npm ERR! peer react@"^17.0.0 || ^18.0.0" from some-package@2.0.0
npm ERR! node_modules/some-package
npm ERR!   some-package@"^2.0.0" from the root project

This error means a package you’re installing requires a specific version of another package (a “peer dependency”), and your project has an incompatible version.

What peer dependencies are

A peer dependency is a package saying: “I don’t install this myself, but I need it to be present in the project, and it needs to be a compatible version.”

Example: A React component library declares "peerDependencies": { "react": "^17.0.0 || ^18.0.0" }. This means:

  • It won’t install React itself
  • It expects React 17 or 18 to already be in your project
  • If your project uses React 19, npm throws ERESOLVE

Why this changed: npm v6 and earlier silently ignored peer dependency conflicts. npm v7+ (2021) made them errors by default. This is why old tutorials don’t mention this issue — it didn’t exist before npm 7.

Fix 1: —legacy-peer-deps (quick fix)

npm install --legacy-peer-deps

This tells npm to use the old npm v6 behavior — ignore peer dependency conflicts and install anyway.

When to use: When you just want it to work and the package is probably compatible (most React/TypeScript libraries work fine across minor version mismatches).

Make it permanent so you don’t have to type it every time:

# Set globally
npm config set legacy-peer-deps true

# Or add to .npmrc in your project
echo "legacy-peer-deps=true" >> .npmrc

Risk: Low. The package might have minor issues with your version, but for most libraries (especially React ecosystem), it works fine.

Fix 2: —force

npm install --force

More aggressive than --legacy-peer-deps. Forces installation, overwrites conflicts, and rebuilds the entire dependency tree.

When to use: When --legacy-peer-deps doesn’t resolve the conflict.

Risk: Medium. Can cause duplicate packages in node_modules and potential runtime issues. Always test after using --force.

Fix 3: Install the required version (proper fix)

The correct solution — align your dependency versions with what the package expects.

# 1. Check what version is required
npm ls react
# Shows the dependency tree and which version each package wants

# 2. Check the peer dependency directly
npm info some-package peerDependencies
# { react: "^17.0.0 || ^18.0.0" }

# 3. Install a compatible version
npm install react@18 react-dom@18

When to use: When you can afford to change the dependency version and want a clean dependency tree.

Risk: Changing a major dependency version might break other packages. Run your tests after upgrading.

Fix 4: Use overrides (npm 8.3+)

Tell npm to use a specific version everywhere, regardless of what packages request:

{
  "name": "my-project",
  "dependencies": {
    "react": "^19.0.0",
    "some-library": "^2.0.0"
  },
  "overrides": {
    "react": "$react"
  }
}

The "$react" syntax means “use whatever version is in my dependencies.” This silences the peer dependency error permanently.

For nested overrides:

{
  "overrides": {
    "some-library": {
      "react": "$react"
    }
  }
}

After adding overrides, delete node_modules and package-lock.json, then reinstall:

rm -rf node_modules package-lock.json
npm install

Fix 5: Switch to pnpm or yarn

Both handle peer dependencies more gracefully than npm:

# pnpm — strict but clear about what's wrong
pnpm install
# Shows warnings but doesn't block installation by default

# yarn — also more lenient
yarn install

pnpm uses a different node_modules structure (content-addressable storage) that avoids many peer dependency conflicts entirely. If you’re starting a new project, consider pnpm.

Fix 6: Update the conflicting package

Often the peer dependency error exists because the library hasn’t updated its peerDependencies to include your version yet. Check if a newer version exists:

# Check for updates
npm outdated some-package

# Install the latest version
npm install some-package@latest

# Or check if there's a beta/next version with updated peer deps
npm info some-package versions
npm install some-package@next

Understanding the error message

npm ERR! ERESOLVE unable to resolve dependency tree
npm ERR!
npm ERR! While resolving: my-project@1.0.0
npm ERR! Found: react@19.0.0                    ← Your version
npm ERR! node_modules/react
npm ERR!   react@"^19.0.0" from the root project
npm ERR!
npm ERR! Could not resolve dependency:
npm ERR! peer react@"^17.0.0 || ^18.0.0"       ← What the package wants
npm ERR! from some-library@2.0.0
npm ERR! node_modules/some-library

Reading this: some-library@2.0.0 wants React 17 or 18, but your project has React 19. The versions don’t overlap.

Common scenarios

React version mismatch — The most common case. A library hasn’t added React 19 to its peer deps yet. Almost always safe to use --legacy-peer-deps — React maintains backward compatibility.

TypeScript version mismatch — Some packages pin specific TypeScript versions. --legacy-peer-deps almost always works because TypeScript is a dev dependency that doesn’t affect runtime.

ESLint plugin conflicts — ESLint plugins often have strict peer deps on the ESLint version. Either update ESLint or use --legacy-peer-deps.

Multiple React versions — If you see “duplicate react” warnings after forcing, your bundle might include React twice. Check with npm ls react — you should see only one version.

Decision flowchart

  1. Is the version mismatch minor? (e.g., React 18 vs 19, TypeScript 5.3 vs 5.5) → Use --legacy-peer-deps
  2. Is the version mismatch major? (e.g., React 16 vs 19) → Upgrade the conflicting package or downgrade your dependency
  3. Is it a one-time install? → Use --legacy-peer-deps
  4. Is it a team project? → Add legacy-peer-deps=true to .npmrc or use overrides in package.json

FAQ

Is —legacy-peer-deps safe to use in production?

Yes, for most cases. It just means npm won’t block installation when peer deps don’t match. The packages still work the same way at runtime. The risk is theoretical incompatibility, not a security issue.

Why did npm change this behavior?

npm v7 made peer dependency conflicts errors to catch real incompatibilities earlier. The problem is that many packages have overly strict peer dependency ranges (e.g., "react": "^18.0.0" when the package actually works fine with React 19). The ecosystem hasn’t fully adapted.

How do I fix this in CI/CD?

Add --legacy-peer-deps to your CI install command, or add a .npmrc file to your repo:

# .npmrc (commit this to your repo)
legacy-peer-deps=true

What’s the difference between —legacy-peer-deps and —force?

--legacy-peer-deps skips peer dependency resolution (npm v6 behavior). --force goes further — it removes existing node_modules, ignores all conflicts, and rebuilds everything. Use --legacy-peer-deps first; only use --force if that doesn’t work.