Skip to content
Back to Maintenance & LTS

Dependency Deduplication

Collapse duplicate versions of the same package so you ship one copy, not five, of lodash.

Why

When five different versions of the same package end up in your tree, you pay five costs: install time, bundle size, memory, security surface, and the bug where two copies have different identity (instanceof breaks because each copy has its own prototype). Deduplication collapses these to one. Modern package managers dedupe by default (npm's hoisting, pnpm's symlinks), but conflicts arise when two deps demand incompatible major versions — then you get a legitimate duplicate, which you should either resolve by upgrading one consumer or accept and audit. The goal isn't zero duplicates (sometimes they're unavoidable) but zero accidental duplicates caused by floating ranges.

When

When npm ls shows the same package at multiple versions, or when bundle size bloats unexpectedly.

How

1. Find duplicates: npm ls lodash (or npm ls --all | grep -A2 lodash) — shows every copy and who pulls it
2. Use npm explain <path> to see why each version is there
3. If versions are close (same major): npm dedupe collapses them automatically
4. If versions span majors: upgrade the consumer demanding the old major, or accept the split
5. For bundle size: import from the root, not a nested path; use bundle analyzer (webpack-bundle-analyzer / source-map-explorer)
6. For pnpm: it dedupes by design (single store, symlinks) — prefer it for monorepos
7. Verify: after dedupe, re-run tests (instanceof identity can change) and check bundle size delta

Example

# Find all copies of lodash in the tree
npm ls lodash
# [email protected]
# ├─┬ [email protected]
# │ └── [email protected]  # old!
# └── [email protected]    # the one you installed

# Why is 4.17.20 there?
npm explain node_modules/foo/node_modules/lodash
# -> [email protected] depends on lodash@^4.17.15

# Dedupe (collapses 4.17.20 + 4.17.21 -> 4.17.21)
npm dedupe
npm test  # verify instanceof still works

# Bundle analyzer to see duplicate cost
npx webpack-bundle-analyzer dist/stats.json
# If lodash shows up twice in the tree view, you have a duplicate
# in the BUNDLE even after npm dedupe — fix by upgrading foo to a
# version that uses [email protected].

Common Problems

  • ⚠Two copies of the same lib break instanceof checks — each copy has its own prototype, so x instanceof Foo is false across the boundary.
  • ⚠Deduping across majors (forcing one major) — breaks the consumer that needs the old API; dedupe only within a major.
  • ⚠Ignoring bundle duplicates — npm dedupe fixes node_modules but webpack may still bundle two copies if imports differ.

Best Practices

  • ✓Run npm dedupe as part of every dependency update PR — it's safe within majors and shrinks install + bundle.
  • ✓Use pnpm for monorepos — its single-store + symlink design dedupes by construction, not as an afterthought.
  • ✓Add a bundle-analyzer CI check that fails if the same package appears at two versions in the bundle output.