npm 5 was released today,其中一项新功能包括通过创建 package-lock.json
文件进行确定性安装。
这个文件应该保存在源代码管理中吗?
我假设它类似于 yarn.lock
和 composer.lock
,两者都应该保存在源代码管理中。
git log
更容易处理。
package-lock.json found. Your project contains lock files generated by tools other than Yarn. It is advised not to mix package managers in order to avoid resolution inconsistencies caused by unsynchronized lock files. To clear this warning, remove package-lock.json
,我认为这里应该有一些答案来澄清人们何时应该不提交 package-lock.json
。
是的,package-lock.json
旨在检查到源代码管理中。如果您使用的是 npm 5+,您可能会在命令行上看到此通知:created a lockfile as package-lock.json. You should commit this file.
根据 npm help package-lock.json
:
package-lock.json 会为 npm 修改 node_modules 树或 package.json 的任何操作自动生成。它描述了生成的确切树,以便后续安装能够生成相同的树,而不管中间依赖项更新如何。该文件旨在提交到源存储库中,并用于多种用途: 描述依赖关系树的单一表示,以便保证团队成员、部署和持续集成安装完全相同的依赖关系。为用户提供“时间旅行”到 node_modules 先前状态的工具,而无需提交目录本身。通过可读的源代码控制差异来促进对树更改的更大可见性。并通过允许 npm 跳过以前安装的包的重复元数据解析来优化安装过程。关于 package-lock.json 的一个关键细节是它无法发布,如果在顶级包以外的任何地方找到它,它将被忽略。它与 npm-shrinkwrap.json 共享格式,本质上是相同的文件,但允许发布。除非部署 CLI 工具或以其他方式使用发布过程来生成生产包,否则不建议这样做。如果 package-lock.json 和 npm-shrinkwrap.json 都存在于包的根目录中,则 package-lock.json 将被完全忽略。
是的你应该:
提交 package-lock.json。在 CI 和本地开发机器上构建应用程序时,使用 npm ci 而不是 npm install
npm ci
工作流程要求存在 package-lock.json
。
npm install
命令的一大缺点是它可能会改变 package-lock.json
的意外行为,而 npm ci
仅使用锁定文件中指定的版本并产生错误
如果 package-lock.json 和 package.json 不同步
如果 package-lock.json 丢失。
因此,在本地运行 npm install
,尤其是。在具有多个开发人员的大型团队中,可能会导致 package-lock.json
内部发生大量冲突,并且开发人员决定完全删除 package-lock.json
。
然而,有一个强大的用例可以相信项目的依赖关系在不同机器上以可靠的方式可重复地解决。
从 package-lock.json
中,您可以得到确切的信息:已知工作状态。
过去,我有没有 package-lock.json
/ npm-shrinkwrap.json
/ yarn.lock
文件的项目,它们的构建有一天会失败,因为随机依赖项得到了破坏性更新。
这些问题很难解决,因为您有时不得不猜测最后一个工作版本是什么。
如果您想添加新的依赖项,您仍然运行 npm install {dependency}
。如果要升级,请使用 npm update {dependency}
或 npm install ${dependendency}@{version}
并提交更改的 package-lock.json
。
如果升级失败,您可以恢复到最后一个已知的工作 package-lock.json
。
强烈建议您将生成的包锁定提交到源代码控制:这将允许您团队中的其他任何人、您的部署、您的 CI/持续集成以及在您的包源中运行 npm install 的任何其他人获得完全相同的依赖关系树你正在开发的。此外,这些更改的差异是人类可读的,并且会通知您 npm 对您的 node_modules 所做的任何更改,因此您可以注意到是否有任何传递依赖项被更新、提升等。
关于 difference between npm ci
vs npm install
:
该项目必须具有现有的 package-lock.json 或 npm-shrinkwrap.json。如果包锁中的依赖项与 package.json 中的依赖项不匹配,npm ci 将退出并报错,而不是更新包锁。 npm ci 一次只能安装整个项目:无法使用此命令添加单个依赖项。如果 node_modules 已经存在,它将在 npm ci 开始安装之前自动删除。它永远不会写入 package.json 或任何包锁:安装基本上是冻结的。
注意:我发布了一个类似的答案 here
whose build would fail one day because a random dependency got a breaking update
类问题。虽然它留下了孩子依赖的可能性,导致同样的问题。
是的,它打算被签入。我想建议它有自己独特的提交。我们发现它给我们的差异增加了很多噪音。
package-lock.json
文件有什么建议吗?我正在对需要合并到主干的分支进行一些更改...我现在是否必须(以某种方式)解决两个 package-lock.json
文件之间的冲突?这感觉很痛苦。
是的,最佳做法是办理登机手续(YES,CHECK-IN)
我同意在看到差异时会引起很多噪音或冲突。但好处是:
保证每个包的版本完全相同。这部分是在不同时间在不同环境中构建时最重要的部分。您可以在 package.json 中使用 ^1.2.3,但是如何确保每次 npm install 在您的开发机器和构建服务器中获取相同的版本,尤其是那些间接依赖包?好吧,package-lock.json 将确保这一点。 (借助基于锁定文件安装软件包的 npm ci)它改进了安装过程。它有助于新的审计功能 npm 审计修复(我认为审计功能来自 npm 版本 6)。
npm ci
。人们经常提到 package-lock.json
允许确定性安装软件包,但几乎从未提及促进这种行为的命令!许多人可能错误地认为 npm install
安装的正是锁定文件中的内容...
npm ci
时提交 package-lock.json 才有意义。您的团队/首席开发人员可以决定何时更新。如果每个人都只是随意提交它,那就没有意义了,它只会在你的回购中制造噪音。 NPM documentation 应该更清楚地说明这一点。我认为大多数开发人员只是对这个功能感到困惑。
我不在我的项目中提交这个文件。重点是什么 ?
它是生成的 这是在 gitlab 中使用 gitlab-ci.yml 构建的 SHA1 代码完整性错误的原因
虽然我确实从未在我的 package.json 中使用 ^ 作为库,因为我对它有不好的体验。
package-lock.json
而导致的具体损失会很有用。一些 repos 可能不需要拥有它所带来的好处,并且可能更喜欢在源代码中没有自动生成的内容。
^
或 *
(example) 创建包,因为它会给最终消费者带来很多问题。
对于在执行 git diff 时抱怨噪音的人:
git diff -- . ':(exclude)*package-lock.json' -- . ':(exclude)*yarn.lock'
我所做的是使用别名:
alias gd="git diff --ignore-all-space --ignore-space-at-eol --ignore-space-change --ignore-blank-lines -- . ':(exclude)*package-lock.json' -- . ':(exclude)*yarn.lock'"
要在整个存储库(每个使用它的人)的差异中忽略 package-lock.json,您可以将其添加到 .gitattributes
:
package-lock.json binary
yarn.lock binary
这将导致差异显示“无论何时更改包锁定文件,二进制文件 a/package-lock.json 和 b/package-lock.json 都会有所不同。此外,一些 Git 服务(尤其是 GitLab,但不是 GitHub)也将排除执行此操作时在线查看这些文件(不再更改 10k 行!)。
gd() { git diff --color-words $1 $2 -- :!/yarn.lock :!/package-lock.json; }
而不是别名。
是的,您可以提交此文件。从 npm's official docs:
package-lock.json 会为 npm 修改 node_modules 树或 package.json 的任何操作自动生成。它描述了生成的确切树,以便后续安装能够生成相同的树,而不管中间依赖项更新如何。该文件旨在提交到源存储库[.]
npm ci
从 package-lock.json 安装
是的,提交 package-lock.json
是一种标准做法。
提交 package-lock.json
的主要原因是项目中的每个人都使用相同的包版本。
优点:
如果您遵循严格的版本控制并且不允许自动更新到主要版本以使您免受第三方包中向后不兼容的更改的影响,那么提交 package-lock 会有很大帮助。
如果你更新一个特定的包,它会在 package-lock.json 中更新,并且每个使用存储库的人都会在他们提取你的更改时更新到该特定版本。
缺点:
它可以让你的拉取请求看起来很丑:)
npm install
不会确保项目中的每个人都使用相同的软件包版本。 npm ci
将对此有所帮助。
npm ci
而不是 npm install
,那么缺点就会消失。
全局禁用 package-lock.json
在终端中输入以下内容:
npm config set package-lock false
这真的像魔术一样对我有用
package-lock=false
的 ~/.npmrc
(至少在我的 macos 上),并且可以在 node_modules/
旁边的任何特定项目中完成相同的操作(例如 echo 'package-lock=false' >> .npmrc
所有答案都说“是”,但这也取决于项目,文档说:
关于 package-lock.json 的一个关键细节是它无法发布,如果在顶级包以外的任何地方找到它,它将被忽略。
这意味着您不需要在 npm 上发布您的 package-lock.json
以获取依赖项,但您需要在您的存储库中使用 package-lock.json
来锁定您的测试依赖项的版本,构建依赖项......
但是,如果您使用 lerna 管理具有多个包的项目,则应仅将 package.json
放在存储库的根目录中,而不是在使用 npm init
创建的每个子包中。你会得到类似的东西:
.git
lerna.json
package.json
package-lock.json <--- here
packages/a/package.json
packages/a/lib/index.js
packages/b/package.json
packages/b/lib/index.js
我对 npm 的使用是生成缩小/丑化 css/js 并生成 django 应用程序提供的页面中所需的 javascript。在我的应用程序中,Javascript 在页面上运行以创建动画,有时执行 ajax 调用,在 VUE 框架内工作和/或使用 css。如果 package-lock.json 对 package.json 中的内容有一些压倒一切的控制,那么可能需要此文件的一个版本。根据我的经验,它要么不会影响 npm install 安装的内容,要么如果确实如此,据我所知,它迄今为止还没有对我部署的应用程序产生不利影响。我不使用传统上是瘦客户端的 mongodb 或其他此类应用程序。
我从 repo 中删除了 package-lock.json,因为 npm install 会生成这个文件,并且 npm install 是运行应用程序的每台服务器上部署过程的一部分。 node 和 npm 的版本控制是在每台服务器上手动完成的,但我注意它们是相同的。
当 npm install
在服务器上运行时,它会更改 package-lock.json,如果服务器上的存储库记录的文件发生更改,下一次部署不会允许您从源中提取新更改。那就是您无法部署,因为拉取将覆盖对 package-lock.json 所做的更改。
您甚至不能用 repo 上的内容覆盖本地生成的 package-lock.json(重置硬源主控),因为如果 package-lock.json 不反映其中的内容,那么当您发出命令时 npm 会抱怨node_modules 由于 npm install,从而破坏了部署。现在,如果这表明 node_modules 中安装了稍微不同的版本,那么这又一次没有给我带来问题。
如果 node_modules 不在你的 repo 上(它不应该在),那么 package-lock.json 应该被忽略。
如果我遗漏了什么,请在评论中纠正我,但是从这个文件中获取版本控制这一点是没有意义的。文件 package.json 中有版本号,我假设这个文件是在 npm install 发生时用于构建包的文件,当我删除它时,npm install 抱怨如下:
jason@localhost:introcart_wagtail$ rm package.json
jason@localhost:introcart_wagtail$ npm install
npm WARN saveError ENOENT: no such file or directory, open '/home/jason/webapps/introcart_devtools/introcart_wagtail/package.json'
并且构建失败,但是在安装 node_modules 或应用 npm 构建 js/css 时,如果我删除 package-lock.json 则不会产生任何投诉
jason@localhost:introcart_wagtail$ rm package-lock.json
jason@localhost:introcart_wagtail$ npm run dev
> introcart@1.0.0 dev /home/jason/webapps/introcart_devtools/introcart_wagtail
> NODE_ENV=development webpack --progress --colors --watch --mode=development
10% building 0/1 modules 1 active ...
将 package-lock.json 提交到源代码版本控制意味着项目将使用特定版本的依赖项,这些依赖项可能与 package.json 中定义的那些相匹配,也可能不匹配。虽然依赖项有一个特定版本,但没有任何插入符号 (^) 和波浪号 (~),如您所见,这意味着依赖项不会更新到最新版本。并且 npm install 将选择相同的版本,以及我们当前版本的 Angular 所需要的版本。
注意:如果我在 CI 期间将任何插入符号 (^) 和波浪号 (~) 添加到要更新的依赖项中,强烈建议将 package-lock.json 提交。
package-lock.json
添加到我的.gitignore
...这给我带来的问题远远多于解决问题。当我们合并或变基时,它总是会发生冲突,当合并导致 CI 服务器上的package-lock.json
损坏时,必须继续修复它只是一种痛苦。