Pebellslearn by building
0%
RoadmapsMatrixCoursesSandboxSign in
Package Managers  ›  Lesson

Versions and Lockfiles

npm 15 minPackages use MAJOR.MINOR.PATCH versions, package.json accepts ranges such as caret and tilde, and the committed lockfile pins exact versions so every install matches.

Versions and Lockfiles

The site builds perfectly on your laptop. On your teammate's laptop, cloned the same afternoon, the date picker looks different and one button is broken. Same package.json, different code. The cause is version ranges, and the cure is a file most beginners ignore: the lockfile.

The rule

package.json allows a range; the lockfile pins the exact versions.

Semantic versioning. Package versions are written MAJOR.MINOR.PATCH, like 4.6.13:

  • PATCH (4.6.13): bug fixes only.
  • MINOR (4.6.13): new features that should not break existing code.
  • MAJOR (4.6.13): breaking changes; your code may need updating.

Ranges. package.json usually holds a range, not one exact version:

Written Accepts Example matches
4.6.13 exactly that version 4.6.13 only
~4.6.13 patch updates 4.6.14, 4.6.20, but not 4.7.0
^4.6.13 minor and patch updates 4.7.0, 4.9.2, but not 5.0.0

^ is npm's default. It trusts package authors to follow the rules, which they usually, but not always, do. (For versions starting with 0., npm treats ^ more cautiously, since anything can change before 1.0.)

The lockfile. When npm installs, it writes package-lock.json, recording the exact version of every package in the tree, including the packages your packages depend on. The next npm install follows the lockfile instead of picking the newest matching version. Commit it to Git, so everyone, and every deployment, gets identical code.

Two install commands.

  • npm install installs and may update the lockfile if package.json changed.
  • npm ci ("clean install") deletes node_modules and installs exactly what the lockfile says. If the lockfile and package.json disagree, it stops with an error rather than guessing. Build servers use it for exactly that strictness.

Updating on purpose. npm outdated lists packages with newer versions; npm update moves them within their ranges. Crossing a major version is a deliberate step: read the package's changelog, then install the new major and test.

The shortcut

To check a version against a range, look at the symbol and freeze the digits to its left: ^ freezes the first number, ~ freezes the first two. Anything to the right may rise.

Does 4.7.1 satisfy each range?Step 1 of 4
  1. Range ^4.6.13

    ^ freezes the major, 4. The candidate keeps 4 and is at least 4.6.13, so it matches.

The trap is adding package-lock.json to .gitignore because it looks like generated noise. That is exactly how two laptops end up with different code.

Drills

Answer fast — trust the rule.

quick drill

A package goes from 2.3.1 to 3.0.0. What does that signal?

quick drill

Which version does ^2.3.1 NOT accept?

quick drill

Which version does ~2.3.1 accept?

quick drill

Should package-lock.json be committed to Git?

quick drill

A build server should install exactly what the lockfile says and fail if it is out of date. Which command?

Remember

  • package.json allows a range; the lockfile pins the exact versions.
  • Freeze the digits left of the symbol: ^ freezes one, ~ freezes two.
  • Trap: ignoring the lockfile lets every laptop drift to different code.

Practice — level up

0/1 solved

Write your answer, then compare it with a rubric and a model answer.

ExplainSame code on every laptop

Two teammates cloned the bakery project on the same day but get different versions of the date picker, which is listed as ^4.6.13. Explain semantic versioning, what the caret allows, and how a lockfile and npm ci prevent this.