# npm script 面试总览:执行环境、编排与依赖确定性

⚡ 30 秒速记

  • npm run name 会读取 package.json#scripts,在平台 shell 中执行命令,并把 node_modules/.bin 临时加入 PATH
  • pre<name> / post<name> 是生命周期钩子;串行用 &&,并行要用跨平台工具并正确转发失败码和退出信号
  • 参数分界用 --,脚本上下文可读取 npm_lifecycle_eventnpm_package_*,但跨平台环境变量应交给 cross-env
  • 可复现安装依赖靠 lockfile 与 npm ci;版本范围决定允许解析什么,lockfile 记录本次实际解析结果
  • 脚本应保持短小、可组合、失败即非零退出;复杂流程迁移到 JavaScript 文件或 CI 配置,别在 JSON 里堆 shell

npm run name 会读取 package.jsonscripts,把 node_modules/.bin 临时加入 PATH,再交给当前平台的 shell 执行。 串行任务用 && 保证失败即停止,并行工具还要正确处理退出码和终止信号;跨平台环境变量则可交给 cross-env。版本范围约束允许解析的版本,lockfile 记录实际依赖图,持续集成中用 npm ci 校验一致性。流程复杂时,我会把分支和文件处理移到可测试的 Node.js 脚本里。

执行 npm run build 时,npm 先找到脚本文本,再构造包含 node_modules/.binPATH 并交给当前平台的 shell。因此脚本里能直接写 eslint,无需硬编码 ./node_modules/.bin/eslint;但同一段 shell 在 Windows 与 POSIX 环境的变量语法、引号和命令可用性可能不同,这正是跨平台工具存在的原因。

串行任务用 && 可以保证前一步失败后停止,不能用 ; 假装等价。并行任务不只是“同时启动”:还要聚合退出码、把终止信号发给所有子进程,并避免一个任务失败后另一个继续占端口。规模变大后,把分支、重试和文件处理放进可测试的 Node.js 脚本,package.json 只保留稳定入口。

版本范围和 lockfile 回答的是两个不同问题:^1.2.3 描述未来重新解析时允许选哪些版本,lockfile 固定这次安装使用的精确版本及依赖图。CI 应使用 npm ci,当清单与 lockfile 不一致时直接失败,而不是悄悄重写锁文件。上面的交互演示会真实解析两组 semver 范围,展示 ^1.2.3^0.2.3 的边界差异。

{
  "scripts": {
    "lint": "eslint .",
    "test": "vitest run",
    "verify": "npm run lint && npm test",
    "build": "node scripts/build.mjs"
  }
}
webapp
公众号
开发者导航
切换夜间模式
点击侧边栏下一篇
折叠侧边栏
收起全部