nvm
这里推荐使用nvm进行node的版本管理,进行多版本切换比较方便。
What | 是什么
node version manager – node版本管理工具,可以同时切换node的多个版本在本地运行。
How | 如何使用
1.安装nvm
以curl为例,打开终端,复制粘贴如下命令后,按回车键等待安装完成即可。1
curl -o- https://raw.githubusercontent.com/creationix/nvm/v0.31.3/install.sh | bash
2.安装node.js
使用nvm install <version> [<arch>]
命令下载需要的版本。arch
参数表示系统位数,默认是64位,如果是32位操作系统,需要执行命令:nvm install 10.0.1 32
1
$ nvm install 10.0.1
3.使用nvm管理node版本
使用特定node版本
执行nvm use <version> [<arch>]
命令开始使用特定版本。比如:nvm use 6.9.0
或者nvm use 6.9.0 32
1
$ nvm use 6.9.0
切换node使用版本
刚刚下载了node 6.9.0版本并且成功使用,现在我们下载一个6.10.3版本,然后切换并使用。1
2
3$ nvm use 6.9.0
$ nvm install 6.10.3
$ nvm use 6.10.3
参考:
nvm官网
nvm的介绍及使用
Install nvm on Mac OSX
npm
What | 是什么
npm有几重含义,npm是世界最大的软件仓库,仓库地址为:https://www.npmjs.com,同时,npm是node的模块管理器,全称node version manager。
作为软件仓库,它由三部分构成:
- 网站:发现包、访问和管理软件包
- CLI:开发者与npm交互的方式
- 注册表:JavaScript代码公共数据库和元信息
How | 如何使用
下载和安装Node.js和npm
为了可以发布和安装包,我们需要一个Node版本管理器,官方建议使用Node version manager去安装Node.js和npm。
使用nvm安装Node.js和npm
nvm可以在系统安装和切换多个Node.js和npm版本,来确保它们可以在不同的版本中使用。
前面我们已经介绍过nvm的安装和使用。
下载最新版本的npm1
$ [sudo] npm install npm -g
检查npm和Node.js的版本1
2$ node -v
$ npm -v
npm CLI 版本
npm有两个版本:
稳定版lastest release
和预发布版 next release
安装Node.js的时候npm会被自动安装,然而npm比Node.js的发布要频繁,安装最新稳定版:1
$ npm install npm@lastest -g
安装预发布版本:1
$ npm install npm@next -g
不一定安装成功,取决于开发周期,所以可能仍然安装的是稳定版。
使用npm安装模块
因为有了npm,只需要一条命令,就能安装别人写好的模块。1
$ npm install
安装package.json
文件内的依赖模块到node_modules
目录。
如果想要安装某个特定的模块,使用:1
$ npm install <packageName>
安装前,npm install
会检查node_modules
目录之中是否已经存在指定模块。如果存在,就不再重新安装了,即使远程仓库有一个新版本,也是如此。
如果你希望,一个模块不管是否安装过,npm都强制重新安装,可以使用-f
或--force
参数。1
$ npm install <packageName> --force
包和模块介绍
软件包和他们的元信息存放在npm的注册表里,
模块是node_modules
目录中可以由Node.js require()函数加载的任何文件或目录。
关于贡献包到注册表的语意版本控制
语义化版本规格是一套规范,来帮助其他开发者理解你代码的变动程度。
它以1.0.0
作为新版的开始。
阶段 | 代码状态 | 规则 | 版本样例 |
---|---|---|---|
新品 | 第一次发布 | 1.0.0开始 | 1.0.0 |
补丁发布 | 向后兼容bug修复 | 增加第三个数字 | 1.0.1 |
小版本 | 向后兼容新功能 | 增长中间的数字并重置最后一个数字为0 | 1.1.0 |
主要发布 | 改变破坏了向后兼容 | 增长第一个数字并且将中间和最后一个数字重置为0 | 2.0.0 |
你可以使用语义版本去指定你包能接受的更新类型
你可以从依赖你包的package.json
文件里指定你的包的更新类型。
比如,为了指定可以接受的版本范围上限是1.0.4,使用如下语法:
- 补丁发布: 1.0 或1.0.x 或 ~1.0.4
- 小版本:1 或 1.x 或 ^1.0.4
- 主要发布: * 或 x
例如:1
2
3
4"dependencies": {
"my_dep": "^1.0.0",
"another_dep": "~2.2.0"
}
对于语意版本语法的更多信息,看npm 语意化版本计算
从注册表获取包
包的搜索和下载
打开npm官网搜索框搜索对应包的名称即可,搜索完对应的包名后,左边有四个筛选条件:
Popularity
:流行度,表示该包多少次被下载,代表多少人受益了。Quality
:品质,包含了一些注意事项如果存在README文件,如稳定性,测试、最新依赖、自定义网站,代码复杂性Maintenance
:维护性,从开发人员对包的关注度来排名,例如:经常维护可能会更好。Optimal
:理想的,可以理解为前三项的综合评估,一般用这个标准就可以,这也是默认排序
安装一个没有作用域的包
这类包总是公共的,可以被任何人下载、安装。1
$ npm install <pageage_name>
在当前目录创建node_modules(如果没有)并且下载该包到当前目录。就是在自己的项目里依赖自己的包,这也是npm install的默认行为。
注意:
如果没有本地没有package.json文件,会安装最新版本,否则,安装package.json文件中声明的满足语意规则的最新版。
安装一个作用域公共包
作用域包的下载需要引用一下作用域的名字1
npm install @scope/package-name
测试包的安装
在你的安装目录下检查是否有node_modules包存在,这里包含了你安装包的目录1
ls node_moudules
使用dist-tags安装包
默认是安装包的最新版,可以使用npm install <package_name>@example-package
被标记为beta
的版本。1
npm install example-package@beta
下载安装全局包
顾名思义,全局包的作用域是整个电脑系统级别的。即可以在各个项目中使用它。1
npm install -g <package_name>
注意
如果npm的版本大于等于5.2,建议使用npx来安装全局包
关于npx,看这篇文章npx介绍
如果全局安装出现了EACCES权限错误,推荐重新安装npm,或手动改变npm的默认目录,具体查看解决全局安装包EACCES权限错误
下载包的更新
更新本地安装包
找到项目根目录确保包含package.json文件:
1
$ cd /path/to/project
运行更新命令
1
$ npm update
它会先到远程仓库查询最新版本,然后查询本地版本。如果本地版本不存在,或者远程版本较新,就会安装。
单独更新某一个包,使用:1
$ npm update <packageName>
- 测试更新,不应该有任何输出
1
$ npm outdated
更新全局安装包
决定哪个全局包需要更新1
$ npm outdated -g --depth=0
更新某一个全局包1
$ npm update -g <package_name>
更新所有全局包1
$ npm update -g
注册表
npm update
命令怎么知道每个模块的最新版本呢?
答案是npm模块仓库提供了一个查询服务,叫做registry
。以npmjs.com为例,它的查询服务地址是https://registry.npmjs.org/
。
这个网址后面跟上模块名,就会得到一个JSON对象,里面是该模块的所有版本信息。比如,访问https://registry.npmjs.org/react
,就会看到react模块所有版本的信息。
它跟下面命令的效果是一样的。1
2
3
4
5
6$ npm view react
// npm view 的别名
$ npm info react
$ npm show react
$ npm v react
registry
网址的模块名后面,还可以跟上版本号或者标签,用来查询某个具体版本的信息。比如,访问 https://registry.npmjs.org/react/v0.14.6
,就可以看到React的0.14.6版。
返回的JSON对象里面,有一个dist.tarball
属性,是该版本的压缩包的网址。
1 | dist |
到这个网址下载压缩包,在本地解压,就得到了模块的代码。npm install
和npm update
命令,都是通过这种方式安装模块的。
包和依赖的卸载
卸载本地包
从node_modules目录删除本地包1
2
3
4// 没有作用域的包
npm uninstall <package_name>
// 包含作用域的包
npm uninstall <@scope/package_name>
例如:1
npm uninstall lodash
从package.json依赖删除本地包
从package.json的依赖里删除包,使用 –save标志。1
2
3
4// 非作用域包
npm uninstall --save <package_name>
// 作用域包
npm uninstall --save <@scope/package_name>
例如1
npm uninstall --save lodash
注意
如果安装包作为一个“devDependency”(i.e. 用 –save-dev),使用 –save-dev 去卸载它: npm uninstall –save-dev package_name
删除确认
查看包是否已删除
- (OS X):
ls node_modules
卸载全局包
需要加一个g标志1
2
3
4// 非作用域包
npm uninstall -g <package_name>
// 作用域包
npm uninstall -g <@scope/package_name>
其他
问题排查
我们可以在安装包的使用生成一个debug.log文件,该文件会在安装失败的时候生成,帮我们排查错误,如果需要生成这个文件,安装包时,使用如下命令:1
$ npm install --timing
debug.log文件位于.npm目录。可以使用npm config get cache
发现这个目录。
npm 设置淘宝镜像
因为npm服务器在国外,如果觉得慢,可以换成淘宝NPM镜像
将npm的registry设置为淘宝的镜像源,以下为几种常用方法:
临时使用
1
npm --registry https://registry.npm.taobao.org install express
持久使用
1
npm config set registry https://registry.npm.taobao.org
回复原地址使用:1
npm config set registry https://registry.npmjs.org/
配置成功后验证:
npm config get registry 或 npm info express
- 通过cnpm使用
1
npm install -g cnpm --registry=https://registry.npm.taobao.org
使用样例1
cnpm install express
缓存目录
npm install
或npm update
命令,从registry下载压缩包之后,都存放在本地缓存目录。
这个缓存目录,在Linux或Mac默认是用户主目录下的.npm
目录,在Windows默认是%AppData%/npm-cache
。通过配置命令,可以查看这个目录的具体位置。
1 | $ npm config get cache |
你最好浏览一下这个目录。1
$ ls ~/.npm
可以使用如下命令查看该目录下内存大小:1
du -sh *
.npm目录存放着大量文件,清空它的命令。1
2
3$ rm -rf ~/.npm/*
# 或者
$ npm cache clean
模块的安装过程
总结一下,Node模块的安装过程是这样的:
- 发出npm install命令
- npm向registry查询压缩包的网址
- 下载压缩包,存放在~/.npm目录
- 解压压缩包到当前目录的node_modules目录
注意,一个模块安装以后,本地其实保存了两份。一份是 ~/.npm
目录下的压缩包,另一份是node_modules
目录下解压后的代码。
但是,运行npm insall的时候,只会检查node_modules目录,而不会检查~/.npm
目录。也就是说,如果该模块在~/.npm下有压缩包,但是没有安装在node_modules
目录中,npm依然会从远程仓库下载一次新的压缩包。
这种行为固然可以保证总是取得最新的代码,但有时并不是我们想要的。最大的问题是,它会极大的影响安装速度。即使某个模块的压缩包就在缓存目录中,也要去远程仓库下载,这怎么可能不慢呢?
另外,有些场合没有网络(比如飞机上),但是你想安装的模块,明明就在缓存目录之中,这时也无法安装。
–cache-min参数
为了解决这些问题,npm提供了一个 --cache-min
参数,用于从缓存目录安装模块。
--cache-min
参数指定一个时间(单位为分钟),只有超过这个时间的模块,才会从registry
下载。1
$ npm install --cache-min 99999 <package-name>
上面命令指定,只有超过99999分钟的模块,才从registry下载。实际上就是指定,所有模块从缓存安装,这样就大大加快了下载速度。
它还有另一种写法。
1 | $ npm install --cache-min Infinity <package-name> |
但是,这并不等于离线模式,这是仍然需要网络连接。因为现在的--cache-min
实现有一些问题。
(1) 如果指定模块不在缓存目录,那么npm会连接registry,下载最新版。这没有问题,但是如果指定模块在缓存目录之中,npm也会连接registry,发出指定模块的etag,服务器返回状态码304,表示不需要重新下载压缩包。
(2) 如果某个模块已经在缓存之中,但是版本低于要求,npm会直接报错,而不是去registry下载最新版本。
npm团队知道存在这些问题,正在重写cache。并且,将来也会提供一个--offline
参数,使用npm可以在离线情况下使用。
不过,这些改进没有日程表。所以,当前使用 --cache-min
改进安装速度,是有问题的。