Why You Should Commit Your Lock File

One small file that is often ignored in a JavaScript project is the lock file.

package-lock.json for npm.
pnpm-lock.yaml for pnpm.
yarn.lock for Yarn.

Commit it.

Why?

Your package.json usually doesn’t define the exact version of every dependency.

For example:

"react": "^19.0.0"

The ^ means npm can install a newer compatible version.

Today you might get:

react 19.0.0

Next month, another developer might get:

react 19.1.0

And one day, your CI/CD pipeline could install yet another version.

That’s where the lock file helps.

It records the exact dependency versions that were resolved, including transitive dependencies.

So instead of:

package.json - "Give me a compatible version"

you get:

package.json - lock file ↓ "Install exactly what we tested"

This is especially important in teams and production systems.

A developer’s machine, CI server and production environment should ideally be using the same dependency tree.

With npm, that’s one reason npm ci exists.

With pnpm:

pnpm install --frozen-lockfile

can ensure the lock file isn’t silently changed during installation.

The lock file also makes debugging easier.

If an application suddenly breaks after a dependency update, you can see exactly which versions changed.

Without a lock file, dependency resolution can become unpredictable.

So my simple rule is:

package.json says what you want.The lock file says exactly what you installed.

If you’re building a serious application, commit the lock file.

Don’t add it to `.gitignore.

Your future self – and your CI/CD pipeline – will thank you.