Lock file is committed and current
Why it matters
Without a committed lock file, every npm install — on your machine, in CI, and at deploy time — is a fresh resolution against whatever versions are current on the registry at that moment. A transitive dependency can silently update between your local install and the production deploy, introducing a behavioral change or a newly-published vulnerability without any visible diff. SLSA L2 requires that the build process be reproducible from a pinned source; a missing lock file breaks that invariant. CWE-829 (Inclusion of Functionality from Untrusted Control Sphere) applies because the install is pulling code from a source you haven't reviewed at that exact version. Lock files are the minimum viable proof that what you shipped is what you tested.
Severity rationale
High because a missing lock file means your production environment can silently install different code than what was tested, turning any npm publish into a potential silent update to your running application.
Remediation
Generate and commit the lock file immediately. Remove it from .gitignore if present — there is no valid reason to exclude a lock file from an application repository.
npm install
git add package-lock.json
git commit -m "chore: add package lock file"
For monorepos or workspaces, commit the root lock file. For pnpm or yarn, commit pnpm-lock.yaml or yarn.lock respectively. CI should run npm ci (not npm install) to enforce the lock file on every build.
Detection
-
ID:
lockfile-committed -
Severity:
high -
What to look for: Check for the presence of a lock file (
package-lock.json,pnpm-lock.yaml,yarn.lock, orbun.lockb) in the project root. Verify the lock file is not listed in.gitignore. To check currency: compare thedependenciesanddevDependenciesentries inpackage.jsonagainst the resolved packages in the lock file. Ifpackage.jsonlists a package that has no entry in the lock file at all, the lock file is stale. Before evaluating, extract and quote the first 5 lines of the lockfile header to confirm it is a valid, non-empty lockfile for the correct package manager. Count all instances found and enumerate each. -
Detector snippet (shell-capable tools only): If the tool has shell access, check whether any supported lockfile exists in the project root. Exit 0 means a lockfile is present — proceed to prose to verify it's not gitignored and is current. Exit 1 means NO lockfile — fail. Exit >=2 or command not found — fall back to prose reasoning.
test -f package-lock.json -o -f pnpm-lock.yaml -o -f yarn.lock -o -f bun.lockb -
Pass criteria: A lock file exists, is not in
.gitignore, and all packages inpackage.jsonhave corresponding resolved entries in the lock file. At least 1 implementation must be confirmed. -
Fail criteria: No lock file exists, or the lock file is in
.gitignore, or one or more packages inpackage.jsonare absent from the lock file (indicatingnpm installhas not been run after editingpackage.json). -
Skip (N/A) when: The project has no
package.json(no npm ecosystem detected). -
Cross-reference: The
no-wildcard-versionscheck verifies that the lockfile's pinned versions are not undermined by loose ranges in the manifest. -
Detail on fail:
"No package-lock.json, pnpm-lock.yaml, or yarn.lock found in project root"or"yarn.lock is listed in .gitignore — lock file not committed"or"package.json has packages not present in lock file — run npm install to sync" -
Remediation: A committed lock file guarantees that every install — on your machine, CI, and production — uses exactly the same dependency versions. Without it, a new version of a transitive dependency could silently install on next deploy, introducing breaking changes or security vulnerabilities.
To generate and commit the lock file:
npm install # generates package-lock.json git add package-lock.json git commit -m "chore: add package lock file"Remove it from
.gitignoreif present — there is almost never a good reason to gitignore a lock file in an application project (libraries are the exception).
External references
- cwe · CWE-829 — Inclusion of Functionality from Untrusted Control Sphere
- slsa:1.0 · L2 — Hosted build platform with signed provenance
- ssdf:800-218 · PS.1 — Protect All Forms of Code from Unauthorized Access and Tampering
Taxons
History
- 2026-04-18·v1.0.0·Initial import from dependency-supply-chain·automated
- 2026-04-20·v1.1.0·Add Phase 6.0 detect-bash snippet for deterministic lockfile presence check·by cakleinman