Dependency Audit
Security auditing npm dependencies for vulnerabilities, license compliance, and supply chain risks
You are an expert in auditing npm dependencies for security vulnerabilities, license compliance, and supply chain risks, using built-in tools, third-party scanners, and CI integration. ## Key Points - **GitHub Advisory Database**: The primary source for npm audit. Community-reviewed advisories. - **NIST NVD (National Vulnerability Database)**: CVE-based vulnerability records. - **OSV (Open Source Vulnerabilities)**: Google's aggregated vulnerability database. - **Snyk Vulnerability DB**: Snyk's proprietary database with additional triage data. - **Direct**: In a package you explicitly depend on. You can update it. - **Transitive**: In a dependency of a dependency. You may need to wait for the intermediate package to update, or use overrides. - **Typosquatting**: `lodas` instead of `lodash`. - **Dependency confusion**: Public package with same name as internal package. - **Maintainer account compromise**: Legitimate package updated with malicious code. - **Malicious postinstall scripts**: Code that runs during `npm install`. - **Protestware**: Maintainer intentionally adds destructive or political code. - name: Audit dependencies ## Quick Example ```bash npm install -D audit-ci ``` ```yaml # GitHub Actions - name: Audit dependencies run: npx audit-ci --moderate ```
skilldb get package-management-skills/Dependency AuditFull skill: 362 linesDependency Audit — Package Management
You are an expert in auditing npm dependencies for security vulnerabilities, license compliance, and supply chain risks, using built-in tools, third-party scanners, and CI integration.
Core Philosophy
Overview
Every npm dependency is a trust decision. Auditing dependencies means systematically checking for known vulnerabilities, license incompatibilities, malicious packages, and supply chain risks. Modern tooling makes this automated, but understanding what the tools check — and what they miss — is critical for maintaining secure applications.
Core Concepts
Vulnerability Databases
- GitHub Advisory Database: The primary source for npm audit. Community-reviewed advisories.
- NIST NVD (National Vulnerability Database): CVE-based vulnerability records.
- OSV (Open Source Vulnerabilities): Google's aggregated vulnerability database.
- Snyk Vulnerability DB: Snyk's proprietary database with additional triage data.
Severity Levels
| Level | CVSS Score | Meaning |
|---|---|---|
| critical | 9.0-10.0 | Actively exploitable, severe impact |
| high | 7.0-8.9 | Exploitable with significant impact |
| moderate | 4.0-6.9 | Requires specific conditions to exploit |
| low | 0.1-3.9 | Limited impact or hard to exploit |
| info | 0.0 | Informational, no direct security impact |
Direct vs. Transitive Vulnerabilities
- Direct: In a package you explicitly depend on. You can update it.
- Transitive: In a dependency of a dependency. You may need to wait for the intermediate package to update, or use overrides.
Supply Chain Attack Vectors
- Typosquatting:
lodasinstead oflodash. - Dependency confusion: Public package with same name as internal package.
- Maintainer account compromise: Legitimate package updated with malicious code.
- Malicious postinstall scripts: Code that runs during
npm install. - Protestware: Maintainer intentionally adds destructive or political code.
Implementation Patterns
Built-in npm Audit
# Run audit
npm audit
# JSON output for CI parsing
npm audit --json
# Only production dependencies
npm audit --omit=dev
# Automatically fix with compatible updates
npm audit fix
# Fix with major version updates (may break)
npm audit fix --force
# Just see what fix would do
npm audit fix --dry-run
pnpm Audit
pnpm audit
# Production only
pnpm audit --prod
# JSON output
pnpm audit --json
# Fix vulnerabilities
pnpm audit --fix
Yarn Berry Audit
yarn npm audit
# Production only
yarn npm audit --environment production
# All severities
yarn npm audit --all
Ignoring Advisories
Some advisories are false positives or not exploitable in your context. Document why:
# npm: no built-in ignore, use .nsprc or audit-ci
# Create .audit-ci.jsonc
{
"allowlist": [
"GHSA-xxxx-xxxx-xxxx" // Not exploitable: only affects server-side usage, we use client-side only
]
}
audit-ci (CI Integration)
npm install -D audit-ci
// .audit-ci.jsonc
{
"moderate": true,
"allowlist": [
"GHSA-xxxx-xxxx-xxxx"
],
"report-type": "full"
}
# GitHub Actions
- name: Audit dependencies
run: npx audit-ci --moderate
Socket.dev (Supply Chain Analysis)
Socket goes beyond known vulnerabilities to detect suspicious behavior:
npx socket:optimize # Analyze for supply chain risks
# Or use the GitHub App for automatic PR comments
# https://github.com/apps/socket-security
Socket checks for:
- Install scripts that execute code
- Network access during install
- Obfuscated code
- Filesystem access patterns
- New maintainers on critical packages
Snyk
# Install
npm install -g snyk
# Authenticate
snyk auth
# Test for vulnerabilities
snyk test
# Monitor continuously
snyk monitor
# Test a specific package
snyk test lodash
# Infrastructure as code scanning
snyk iac test
# GitHub Actions
- uses: snyk/actions/node@master
env:
SNYK_TOKEN: ${{ secrets.SNYK_TOKEN }}
License Compliance
# List all dependency licenses
npx license-checker --summary
# Fail on specific licenses
npx license-checker --failOn 'GPL-3.0;AGPL-3.0'
# Production only
npx license-checker --production
# JSON output
npx license-checker --json --out licenses.json
# pnpm
pnpm licenses list
# More detailed analysis
npx license-compliance --production --allow 'MIT;Apache-2.0;BSD-2-Clause;BSD-3-Clause;ISC'
Automated Dependency Updates
Keep dependencies current to get security patches:
Dependabot (.github/dependabot.yml):
version: 2
updates:
- package-ecosystem: npm
directory: "/"
schedule:
interval: weekly
open-pull-requests-limit: 10
groups:
production:
dependency-type: production
development:
dependency-type: development
ignore:
- dependency-name: "aws-sdk"
update-types: ["version-update:semver-major"]
Renovate (renovate.json):
{
"$schema": "https://docs.renovatebot.com/renovate-schema.json",
"extends": [
"config:recommended",
"group:allNonMajor",
":semanticCommits"
],
"packageRules": [
{
"matchPackagePatterns": ["eslint"],
"groupName": "eslint",
"automerge": true
},
{
"matchUpdateTypes": ["major"],
"labels": ["major-update"]
}
]
}
Analyzing Package Health Before Installing
# Check download trends, maintenance, quality
npx packagephobia lodash # Install size
# npm provenance: verify package origin
npm audit signatures
# Check package metadata
npm info lodash
# View all maintainers
npm owner ls lodash
# Check when last published
npm view lodash time
Creating a Security Policy
For a comprehensive audit strategy, automate in CI:
# .github/workflows/security.yml
name: Security Audit
on:
schedule:
- cron: '0 9 * * 1' # Weekly Monday 9am
pull_request:
paths:
- 'package.json'
- 'package-lock.json'
jobs:
audit:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: 20
- run: npm ci
- run: npx audit-ci --moderate
- run: npx license-checker --failOn 'GPL-3.0;AGPL-3.0' --production
Handling Vulnerabilities in Transitive Dependencies
When a vulnerability is in a transitive dependency and no update is available:
// npm overrides (package.json)
{
"overrides": {
"vulnerable-pkg": ">=2.0.1"
}
}
// pnpm overrides
{
"pnpm": {
"overrides": {
"vulnerable-pkg": ">=2.0.1"
}
}
}
# Yarn Berry resolutions (.yarnrc.yml or package.json)
resolutions:
vulnerable-pkg: ">=2.0.1"
Best Practices
- Run
npm auditon every CI build and fail on high/critical vulnerabilities. - Use
audit-cifor configurable CI integration with allowlists for acknowledged false positives. - Automate dependency updates with Dependabot or Renovate. Group minor/patch updates for less noise.
- Check licenses in CI. Know which licenses your organization permits.
- Use Socket.dev or similar tools to detect supply chain attacks that vulnerability databases miss.
- Pin exact versions in applications (via lock files) and review lock file changes in PRs.
- Audit
postinstallscripts: runnpm lsand review packages that execute scripts during install. - Before adding a new dependency, check its maintenance status, download count, contributor count, and known issues.
- Use npm provenance (
npm audit signatures) to verify published packages were built in trusted CI environments. - Maintain an allowlist of acknowledged vulnerabilities with documented justification and review dates.
Common Pitfalls
- Ignoring audit output: Many teams treat
npm auditwarnings as noise. Set a threshold and enforce it. npm audit fix --force: This installs major version updates that may break your application. Always review changes before running with--force.- Dev dependency false positives: A vulnerability in a dev dependency (e.g., a test framework) rarely affects production. Use
--omit=devto focus on production risk. - Transitive vulnerability paralysis: Waiting indefinitely for a transitive dependency fix. Use overrides to patch immediately while waiting for the proper fix upstream.
- License surprise: Installing a dependency under GPL-3.0 in a proprietary project can have legal consequences. Check licenses before installation.
- Stale Dependabot PRs: Opening PRs without merging them provides no security benefit. Configure automerge for patch updates with passing tests.
- Only checking at install time: Vulnerabilities are discovered continuously. Run scheduled audits, not just at install.
- Trusting download count alone: Popular packages can be compromised. Use multiple signals (provenance, maintainers, Socket analysis) to assess trust.
Anti-Patterns
Over-engineering for hypothetical scale. Building for millions of users when you have hundreds adds complexity without value. Solve today's problems first.
Ignoring the existing ecosystem. Reinventing functionality that mature libraries already provide well wastes time and introduces unnecessary risk.
Premature abstraction. Creating elaborate frameworks and utilities before you have enough concrete cases to know what the abstraction should look like produces the wrong abstraction.
Neglecting error handling at boundaries. Internal code can trust its inputs, but system boundaries (user input, APIs, file I/O) require defensive validation.
Skipping documentation for obvious code. What is obvious to you today will not be obvious to your colleague next month or to you next year.
Install this skill directly: skilldb add package-management-skills
Related Skills
Bundling Libraries
Bundling JavaScript/TypeScript libraries for distribution using tsup, unbuild, and Rollup
Lockfile Management
Lock file strategies for deterministic installs across npm, pnpm, and Yarn
Npm Publishing
Publishing packages to the npm registry with proper configuration, access control, and release automation
Pnpm
pnpm workspace management for monorepos with content-addressable storage and strict dependency isolation
Private Registries
Setting up and using private npm registries with Verdaccio, GitHub Packages, and GitLab Package Registry
Semantic Versioning
Semantic versioning (SemVer) conventions, version ranges, and strategies for managing breaking changes