VNX-NODE-001 – Missing npm Lock File
Overview
This rule detects Node.js projects that have a package.json but no corresponding lock file (package-lock.json, yarn.lock, or pnpm-lock.yaml). Without a lock file, every npm install re-resolves floating version ranges from the registry, meaning a different — potentially malicious — package version may be installed on each run. This falls under CWE-829 (Inclusion of Functionality from Untrusted Control Sphere) and directly enables dependency confusion and supply chain attacks.
Severity: High | CWE: CWE-829 – Inclusion of Functionality from Untrusted Control Sphere | OWASP ASVS: V10.3.2
Lock files are not generated automatically by Node.js or npm. You must run npm install, yarn install, or pnpm install explicitly to create one, and then commit it to version control. Without this step, your dependency tree is non-deterministic across environments.
Why This Matters
In a dependency confusion attack, an adversary publishes a public package with the same name as one of your internal packages but a higher version number. Without a lock file pinning exact resolved versions, npm install may silently pull the malicious public package instead of your internal one. The 2021 dependency confusion attack by security researcher Alex Birsan demonstrated this against Apple, Microsoft, and dozens of other companies — every affected project lacked pinned dependencies.
Beyond malicious substitution, floating ranges mean that a legitimate upstream package can introduce a breaking change or a newly discovered vulnerability between your CI run and your production deploy. A lock file makes builds reproducible and auditable: you can review exactly what changed between two lock file commits rather than discovering version drift at runtime.
OWASP ASVS v4 requirement V10.3.2 states: “Verify that the application only uses software components without known vulnerabilities.” Pinning dependencies via a lock file is a prerequisite for this — you cannot audit what you cannot enumerate.
What Gets Flagged
The rule fires when a directory is identified as a Node.js project (it appears in dirs_by_language["node"]) but none of the three standard lock files exist alongside package.json.
my-service/
package.json ← project root detected
src/
...
# FLAGGED: no package-lock.json, yarn.lock, or pnpm-lock.yaml present
Remediation
Generate a lock file immediately. Run the package manager you already use:
# npm (creates package-lock.json) npm install # yarn (creates yarn.lock) yarn install # pnpm (creates pnpm-lock.yaml) pnpm installCommit the lock file to version control. The lock file must live in the repository root (or the relevant workspace root) and be committed alongside
package.json. Never add lock files to.gitignore.Use
npm ciinstead ofnpm installin CI/CD.npm ciinstalls exactly what is inpackage-lock.json, fails if the lock file is absent or out of sync withpackage.json, and never modifies the lock file. This guarantees reproducible builds across environments.# SAFE: reproducible CI install npm ci # In a Dockerfile: COPY package.json package-lock.json ./ RUN npm ci --omit=devPin to lock file version 2 or higher.
package-lock.jsonversion 2+ (npm 7+) includes anintegrityfield with SRI hashes for every resolved package. Verify the npm version in your pipeline:node -e "console.log(JSON.parse(require('fs').readFileSync('package-lock.json')).lockfileVersion)" # Should print 2 or 3Enable
npm auditin CI. Runningnpm audit --audit-level=highafternpm cicatches newly disclosed vulnerabilities in your pinned dependency tree before they reach production.npm ci npm audit --audit-level=highConsider private registry mirroring. For high-security environments, mirror required packages to a private Artifact Registry or Nexus instance and configure npm to resolve only from that registry, eliminating the public-registry attack surface entirely.
# .npmrc — scope private packages to internal registry @myorg:registry=https://npm.internal.example.com
References
- CWE-829: Inclusion of Functionality from Untrusted Control Sphere
- CAPEC-185: Malicious Software Download
- OWASP ASVS v4 – V10.3.2 Software Integrity
- OWASP Node.js Security Cheat Sheet
- npm ci documentation
- npm package-lock.json specification
- Alex Birsan – Dependency Confusion attack writeup
- MITRE ATT&CK T1195.001 – Compromise Software Dependencies and Development Tools