版本号
semver 约定一个包的版本号必须包含3个数字,格式必须为 MAJOR.MINOR.PATCH
, 意为 主版本号.次版本号.修订版本号
.
MAJOR 主版本号,对应大的版本号迭代,做了不兼容旧版的修改时要更新 MAJOR 版本号
MINOR 次版本号,对应小版本迭代,发生兼容旧版API的修改或功能更新时,更新MINOR版本号
PATCH 修订号,对应修订版本号,一般针对修复 BUG 的版本号
~,^
~,^ 的表述需要结合具体的包管理工具和版本号规则来确定,但是对于一般使用记住如下原则:
^ 是确保版本兼容性时,默认对次版本号的限定约束
~ 是确保版本兼容性时,默认对补丁号的约束
npm install流程
- 检查
.npmrc
文件:优先级为:项目级的.npmrc
文件 > 用户级的.npmrc
文件> 全局级的.npmrc
文件 > npm 内置的.npmrc
文件 - 检查项目中有无
lock
文件。 - 无
lock
文件:- 从
npm
远程仓库获取包信息 - 根据
package.json
构建依赖树,构建过程:- 构建依赖树时,不管其是直接依赖还是子依赖的依赖,优先将其放置在
node_modules
根目录。 - 当遇到相同模块时,判断已放置在依赖树的模块版本是否符合新模块的版本范围,如果符合则跳过,不符合则在当前模块的
node_modules
下放置该模块。 - 注意这一步只是确定逻辑上的依赖树,并非真正的安装,后面会根据这个依赖结构去下载或拿到缓存中的依赖包
- 构建依赖树时,不管其是直接依赖还是子依赖的依赖,优先将其放置在
- 在缓存中依次查找依赖树中的每个包
- 不存在缓存:
- 从
npm
远程仓库下载包 - 校验包的完整性
- 校验不通过:
- 重新下载
- 校验通过:
- 将下载的包复制到
npm
缓存目录 - 将下载的包按照依赖结构解压到
node_modules
- 将下载的包复制到
- 从
- 存在缓存:将缓存按照依赖结构解压到
node_modules
- 不存在缓存:
- 将包解压到
node_modules
- 生成
lock
文件
- 从
- 有
lock
文件:- 检查
package.json
中的依赖版本是否和package-lock.json
中的依赖有冲突。 - 如果没有冲突,直接跳过获取包信息、构建依赖树过程,开始在缓存中查找包信息,后续过程相同
- 检查
package.json
npm脚本
npm 脚本的原理非常简单。每当执行npm run
,就会自动新建一个 Shell,在这个 Shell 里面执行指定的脚本命令。因此,只要是 Shell(一般是 Bash)可以运行的命令,就可以写在 npm 脚本里面。
比较特别的是,npm run
新建的这个 Shell,会将当前目录的node_modules/.bin
子目录加入PATH
变量,执行结束后,再将PATH
变量恢复原样。
这意味着,当前目录的node_modules/.bin
子目录里面的所有脚本,都可以直接用脚本名调用,而不必加上路径。
运行多个 npm script
`&&` npm script 串行
`&` npm script 并行
npm script 传递参数
向 npm 脚本传入参数,要使用--
标明。
"lint:js:fix": "npm run lint:js -- --fix"
npm script 钩子
为了方便开发者自定义,
npm script
的设计者为命令的执行增加了类似生命周期的机制,具体来说就是pre
和post
钩子脚本。这种特性在某些操作前需要做检查、某些操作后需要做清理的情况下非常有用。
举例来说,运行 npm run test 的时候,分 3 个阶段:
- 检查
scripts
对象中是否存在pretest
命令,如果有,先执行该命令; - 检查是否有
test
命令,有的话运行test
命令,没有的话报错; - 检查是否存在
posttest
命令,如果有,执行posttest
命令;