咱们都很熟悉的,经过 npm run script-name 能够执行 package.json 中 scripts 对象配置的脚本。可是,你或许不知道下面这些知识。html
下文中 npm-scirpt 指 package.json scripts 中配置的脚本命令。name-scirpt 指代某一个名字为 name 的脚本命令。node
当咱们使用命令 npm start 时,npm 会尝试执行 package.json scripts 中配置的 start 脚本命令。start-script 的默认配置为 "start": "node server.js"。因此若是项目根目录下有 server.js 文件,那么经过 npm start 会直接运行 server.js 中的代码。python
除了 start-script ,当使用 npm start 命令时,npm 一样会尝试在 package.json scripts 中查找是否配置了 prestart,poststart 脚本命令。若是都配置了,npm 会按照如下顺序执行脚本。linux
相似的,npm test, npm restart, npm stop 都会按照以上的方式执行 scripts 中配置的对应脚本。同时 npm 会经过 npm_lifecycle_event 环境变量标识当前处于哪一阶段(所谓的生命周期)。好比,在 prestart-script 脚本执行阶段 npm_lifecycle_event 的值为 "prestart",start-script 阶段,值为 "start",即 package.json scripts 对象配置的脚本名字。webpack
以上是 npm 内置命令对应的脚本执行逻辑,对于咱们平时最熟悉的自定义脚本,以上逻辑一样适用。好比咱们配置了 "build": "webpack --mode=production",同时配置了 prebuild 以及 postbuild 脚本,当使用 npm run build 时,一样会依次执行 prebuild-script、build-script、postbuild-script。git
咱们配置的脚本命令,如 "start": "node server.js",node server.js 会当作一行代码传递给系统的 SHELL 去解释执行。实际使用的 SHELL 可能会根据系统平台而不一样,类 UNIX 系统里,如 macOS 或 linux 中指代的是 /bin/sh, 在 windows 中使用的是 cmd.exe。github
既然是交给 SHELL 去解释执行的,说明配置的脚本能够是任意可以在 SHELL 中运行的命令,而不单单是 node 脚本或者 js 程序。即若是你的系统里安装了 python(或者说系统变量 PATH 里能找到 python 命令),你也能够将 scripts 配置为 "myscript": "python xxx.py"web
上面提到了在使用 npm run script-name 命令时,npm 会设置一个环境变量 npm_lifecycle_event。实际上 npm 还会设置不少环境变量,经过内置命令 npm run env 能够查看 npm 为脚本运行时设置的全部环境变量。 其中 package.json 中设置的全部字段,都会被设置为 npm_package_ 开头的环境变量。若是你的 packge.json 设置以下npm
{
"name": "npm-demo",
"version": "1.0.0",
"script": {
"build": "webpack --mode=production"
},
"files": ["src"]
}
复制代码
PATH 上面提到了 npm-script 执行前会设置一些环境变量,其中很重要的一个环境变量是 PATH。npm 会将项目 node_modules/.bin 的绝对路径添加到环境变量 PATH 中。所以咱们能够在 npm-script 中使用项目本地安装的一些命令行工具。如上面设置的 build 脚本: "build": "webpack --mode=production"。json
只要咱们本地安装了 webpack,就能够在项目的 node_modules/.bin 路径下看到 webpack 可执行文件。又由于 node_modules/.bin 路径已经添加到 PATH 中,因此脚本运行时可以在 PATH 中找到 webpack 命令,从而顺利执行。
最后,为何 webpack 安装后,可以在 node_modules/.bin 路径下找到对应的可执行文件?能够查看
Reference