DEV Community

Alex Chen
Alex Chen

Posted on

npm Scripts and package.json Mastery (2026)

npm Scripts and package.json Mastery (2026)

Your package.json is more than a dependency list. It is a powerful automation tool. Here is how to master npm scripts.

package.json Essentials

{
  "name": "my-awesome-project",
  "version": "1.0.0",
  "description": "A well-configured project",
  "type": "module",           // Use ES modules (import/export) instead of CommonJS
  "main": "./dist/index.js", // Entry point for require()
  "exports": {               // Control what external code can import (Node.js 12.7+)
    ".": {
      "import": "./dist/index.js",
      "require": "./dist/index.cjs"
    },
    "./utils": "./dist/utils.js"
  },
  "bin": {                   // CLI commands
    "my-tool": "./cli.js"
  },
  "files": [                 // Files to include when publishing
    "dist",
    "README.md"
  ],
  "engines": {                // Required Node.js version
    "node": ">=18.0.0"
  },
  "scripts": {                // THE POWERFUL PART (see below)
    ...
  }
}
Enter fullscreen mode Exit fullscreen mode

Script Basics

{
  "scripts": {
    "start": "node server.js",
    "dev": "nodemon server.js",
    "build": "tsc",
    "test": "jest",
    "lint": "eslint src/",
    "format": "prettier --write 'src/**/*.{js,ts}'"
  }
}
Enter fullscreen mode Exit fullscreen mode

Run with: npm run dev or shorthand npm test / npm start

Pre/post hooks run automatically:

{
  "scripts": {
    "prebuild": "npm run lint && npm run clean",
    "build": "tsc",
    "postbuild": "npm run test"
  }
}
// Running `npm run build` automatically executes:
// prebuild  build  postbuild (in order)
Enter fullscreen mode Exit fullscreen mode

Environment Variables in Scripts

{
  "scripts": {
    "dev": "NODE_ENV=development nodemon server.js",
    "prod": "NODE_ENV=production node server.js",
    "test": "NODE_ENV=test jest --coverage"
  }
}
// Cross-platform solution (Windows compatible):
// Install cross-env: npm install -D cross-env
{
  "scripts": {
    "dev": "cross-env NODE_ENV=development nodemon server.js"
  }
}
Enter fullscreen mode Exit fullscreen mode

Advanced Script Patterns

{
  "scripts": {
    // Chaining with && (run sequentially, stop on failure)
    "validate": "npm run lint && npm run typecheck && npm run test",

    // Chaining with & (run in parallel)
    "dev:all": "npm run dev:client & npm run dev:server",

    // Using npm variables
    "show-pkg": "echo %npm_package_name% v%npm_package_version%",
    // On Unix: echo $npm_package_name v$npm_package_version

    // Conditional scripts (using tiny CLI tools)
    "deploy:staging": "[ \"$NODE_ENV\" = \"production\" ] && echo 'Cannot deploy from production!' || npm run deploy:staging:real",

    // Script composition (call other scripts)
    "ci": "npm run lint && npm run typecheck && npm run test:cov && npm run build",

    // Watch mode for development
    "watch": "tsc -w && nodemon dist/server.js",

    // Database operations
    "db:migrate": "knex migrate:latest",
    "db:rollback": "knex migrate:rollback",
    "db:seed": "knex seed:run",
    "db:reset": "npm run db:migrate:undo:all && npm run db:migrate && npm run db:seed",

    // Git hooks integration
    "prepare": "husky install",
    "precommit": "lint-staged"
  }
}
Enter fullscreen mode Exit fullscreen mode

Useful Dev Dependencies

# Development tooling (devDependencies only):
npm install -D nodemon        # Auto-restart on file changes
npm install -D concurrently   # Run multiple scripts in parallel properly
npm install -D cross-env      # Cross-platform env vars
npm install -D husky          # Git hooks
npm install -D lint-staged    # Run linters on staged files
npm install -D prettier       # Code formatter
npm install -D eslint         # Code linter
npm install -D jest           # Testing framework
npm install -D @types/node    # TypeScript types for Node.js
npm install -D ts-node        # Run TypeScript directly
npm install -D rimraf         # Cross-platform rm -rf
npm install -D cpx            # Cross-platform copy
npm install -D dotenv         # Load .env files
Enter fullscreen mode Exit fullscreen mode

Lifecycle Scripts (Special npm Hooks)

{
  "scripts": {
    // These run automatically at specific times:

    "prepare": "husky install",
    // Runs BEFORE npm install (and after)
    // Good for: installing git hooks, building native deps

    "prepublishOnly": "npm run build && npm run test",
    // Runs before npm publish
    // CRITICAL: ensures you publish built+tested code

    "postinstall": "node setup.js || exit 0",
    // Runs after npm install
    // Good for: setup scripts, dependency checks
    // Always use || exit 0 so it does not break installs!

    "preversion": "npm run test",
    "version": "git add -A && git commit -m 'chore: release v%s'",
    "postversion": "git push && git push --tags",
    // Runs during npm version (bump patch/minor/major)

    "pack": "npm pack --dry-run 2>&1 | head -20",
    // Preview what would be published without actually publishing
  }
}
Enter fullscreen mode Exit fullscreen mode

Workspaces (Monorepo Management)

// Root package.json
{
  "name": "my-monorepo",
  "private": true,
  "workspaces": [
    "packages/*",
    "apps/*"
  ],
  "scripts": {
    "dev": "concurrently 'npm run dev -w apps/web' 'npm run dev -w api'",
    "build": "npm run build --workspaces-if-present",
    "test": "npm test --workspaces-if-present",
    "lint": "eslint 'packages/*/src' 'apps/*/src'"
  }
}

// Benefits:
// - Single node_modules folder (hoisted dependencies)
// - npm install from root installs everything
// - Cross-package references work naturally
// - Commands can run across all or specific workspaces: -w <name>
Enter fullscreen mode Exit fullscreen mode

What is your favorite npm script trick? What is in your package.json that you cannot live without?

Follow @armorbreak for more practical developer guides.

Top comments (0)