package.json基础
认识 package.json
在 WebStrom
中创建 Node.js 项目后,会默认生成一个 package.json
文件,如图3.3所示。
package.json
文件是项目的清单文件,其中可以做很多完全互不相关的事情。例如,图3.3中的 package.json
文件主要用来对项目进行配置,而在 npm
安装目录中,同样有一个 package.json
文件,存储了所有已安装软件包的名称和版本等信息。

对于 Node.js 程序,package.json
文件中的内容没有固定要求,唯一的要求是必须遵守 JSON
格式,否则,尝试以编程的方式访问其属性的程序会无法读取它。
创建 Node.js 项目时默认生成的 package.json
文件如下:
{
"name": "nodepro",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"keywords": [],
"author": "",
"license": "ISC"
}
上面的代码中包含很多属性,具体说明如下。
-
name
:应用程序或软件包的名称。名称必须少于 214 个字符,且不能包含空格,只能包含小写字母、连字符(-)或下画线(_)。 -
version
:当前的版本,该属性的值遵循语义版本控制法,这意味着版本始终以 3 个数字表示—x.x.x,其中,第一个数字是主版本号,第二个数字是次版本号,第三个数字是补丁版本号。 -
description
:应用程序/软件包的简短描述。如果要将软件包发布到 npm,则这个属性特别有用,使用者可以知道该软件包的具体作用。 -
main
:设置应用程序的入口点。 -
scripts
:定义一组可以运行的 Node.js 脚本,这些脚本是命令行应用程序。可以通过调用npm run XXXX
或yarn XXXX
来运行它们,其中的XXXX
是命令的名称。例如npm run dev
。 -
keywords
:包含与软件包功能相关的关键字数组。 -
author
:列出软件包的作者名称。 -
license
:指定软件包的许可证。
除了上面列出的属性,package.json
文件中还支持其他的很多属性,常用的如下。
-
contributors
:除作者外,该项目可以有一个或多个贡献者,此属性是列出他们的数组。 -
bugs
:链接到软件包的问题跟踪器,最常用的是 GitHub 的 issues 页面。 -
homepage
:设置软件包的主页。 -
repository
:指定程序包仓库所在的位置。例如:"repository": "github:nodejscn/node-api-cn",
上面的 github 前缀表示 github 仓库,其他流行的仓库还包括:
"repository": "gitlab:nodejscn/node-api-cn", "repository": "bitbucket:nodejscn/node-api-cn",
开发人员可以显式地通过该属性设置版本控制系统,例如:
"repository": { "type": "git", "url": "https://github.com/nodejscn/node-api-cn.git" }
也可以使用其他的版本控制系统:
"repository": { "type": "svn", "url": "..." }
-
private
:如果设置为true
,则可以防止应用程序/软件包被意外发布到 npm 上。 -
dependencies
:设置作为依赖安装的npm
软件包的列表。当使用npm
或yarn
安装软件包时,该软件包会被自动插入此列表中。 -
devDependencies
:设置作为开发依赖安装的npm
软件包的列表。它们不同于dependencies
,因为它们只需安装在开发机器上,而无须在生产环境中运行代码。当使用npm
或yarn
安装软件包时,该软件包会被自动地插入此列表中。 -
engines
:设置软件包/应用程序要运行的 Node.js 或其他命令的版本。 -
browserslist
:用于告知要支持哪些浏览器(及其版本)。
npm 中的 package-lock.json 文件
在 npm5
以上的版本中,引入了 package-lock.json
文件,该文件旨在跟踪被安装的每个软件包的确切版本,以便产品可以以相同的方式被 100% 复制(即使软件包的维护者更新了软件包)。
package-lock.json
文件的出现解决了 package.json
一直存在的特殊问题,在 package.json
中,可以使用 semver
(语义化版本)表示法设置要升级到的版本(补丁版本或次版本),例如:
-
如果写入的是 ~0.13.0,则只更新补丁版本:即 0.13.1 可以,但 0.14.0 不可以。
-
如果写入的是 ^0.13.0,则要更新补丁版本和次版本:即 0.13.1、0.14.0……以此类推。
-
如果写入的是 0.13.0,则始终使用确切的版本。
无须将 node_modules
文件夹(该文件夹通常很大)提交到 Git,当尝试使用 npm install
命令在另一台机器上复制项目时,如果指定了 ~
语法并且软件包发布了补丁版本,则该补丁版本会被安装,^
语法中的次版本也一样。
如果指定确切的版本,例如示例中的 0.13.0,则不会受到此问题的影响。
这时如果多个人在不同时间获取同一个项目,使用 npm install
安装时,有可能安装的依赖包版本不同,这样可能会给程序带来不可预知的错误。而通过使用 package-lock.json
文件,可以固化当前安装的每个软件包的版本,当运行 npm install
时,npm
会使用这些确切的版本,确保每个人在任何时间安装的版本都是一致的,从而避免使用 package.json
文件时可能出现的版本不同问题。
例如,在 package.json
文件中有如下属性:
"express": "^4.15.4"
在只有 package.json
文件时,如果后续出现了 4.15.5 版本、4.15.6 版本等,则有可能每个人安装的依赖包就会不同,从而导致一些未知的兼容性问题。这时如果使用 package-lock.json
文件,则文件中的内容可以设置如下:
"express": {
"version": "4.15.4",
"resolved": "https://registry.npmjs.org/express/-/express-4.15.4.tgz",
"integrity": "sha1-Ay4iU0ic+PzgJma+yj0R7XotrtE=",
"requires": {
"accepts": "1.3.3",
"array-flatten": "1.1.1",
"content-disposition": "0.5.2",
"content-type": "1.0.2",
"cookie": "0.3.1",
"cookie-signature": "1.0.6",
"debug": "2.6.8",
"depd": "1.1.1",
"encodeurl": "1.0.1",
"escape-html": "1.0.3",
"etag": "1.8.0",
"finalhandler": "1.0.4",
"fresh": "0.5.0",
"merge-descriptors": "1.0.1",
"methods": "1.1.2",
"on-finished": "2.3.0",
"parseurl": "1.3.1",
"path-to-regexp": "0.1.7",
"proxy-addr": "1.1.5",
"qs": "6.5.0",
"range-parser": "1.2.0",
"send": "0.15.4",
"serve-static": "1.12.4",
"setprototypeof": "1.0.3",
"statuses": "1.3.1",
"type-is": "1.6.15",
"utils-merge": "1.0.0",
"vary": "1.1.1"
}
},
上面的代码中,由于在 package-lock.json
文件中使用了校验软件包的 integrity
散列值,这样就可以保证所有人在任何时间安装的依赖包的版本都是一致的。
在使用 |