1. 首页

你想知道关于package-lock.json的一切,但是太害怕了问了?

简介

如果你已经将节点包管理(npm)更新到版本5.x.x,看起来一切似乎都很顺利。等等,这是什么?用 npm 初始化项目的会自动创建了一个新文件 package-lock.json。如果打开它,它看起来有点像 package.json 的依赖项,但更冗长。我们决定忽略它,继续开发项目。最终,我们有时会遇到依赖项的问题,找不到,或者安装了错误的版本。大多数人最终都会删package-lock.json和运行“npm install”。那么,为什么要有它呢? 它应该做什么? 它实际上是做什么的?

总结

  • 如果你使用的 npm 版本 为 ^5.x.x , package-lock.json 会默认自动生成
  • 你应该使用 package-lock 来确保一致的安装和兼容的依赖关系
  • 你应该将 package-lock 提交到源代码控制
  • 从npm ^ 5.1.x开始,package.json能够胜过 package-lock.json,所以你遇到较少让人头痛的问题
  • 不再删除 package-lock 只是为了运行npm install并重新生成它

背景

语义版本控制

在你了解 package-lock 甚至 package.jso n之前,你必须了解语义版本控制(semver)。 这是npm背后的天才,是什么使它更成功。 你可以在 此处 阅读有关npm如何使用它的更多信息。简而言之,如果你正在构建与其他应用程序接口的应用程序,你应该告知你所做的更改将如何影响第三方与你的应用程序交互的能力。这是通过语义版本控制完成的,版本由三部分组成:X,Y,Z,分别是主要版本,次要版本和补丁版本。

例如:1.2.3,主要版本1,次要版本2,补丁3。

补丁中的更改表示不会破坏任何内容的错误修复。 次要版本的更改表示不会破坏任何内容的新功能。 主要版本的更改代表了一个破坏兼容性的大变化。 如果用户不适应主要版本更改,则内容将无法正常工作。

管理包

npm 存在使管理包变得容易。你的项目可能有数百个依赖项,每个依赖项都有一百个,为了让你的注意力远离依赖地狱,通过 npm 管理,使用一些简单的命令,你可以安装和管理这些依赖关系,几乎不必考虑它们。

当您使用npm安装包(并保存它)时,会在 package.json 中添加一个包含包名称和应该使用的 semver的条目。默认情况下,npm 安装最新版本,并预先插入版本号,例如 “^1.2.12”,这表示至少应该使用版本 1.2.12,但任何高于此版本的版本都可以,只要它具有相同的主要版本,由于次要版本和补丁编号仅代表错误修正和非破坏性添加, 你可以安全地使用任何更高版本的同一主要版本。阅读更多关于semver通配符的信息,请看 这里

共享项目

在 package.json 中定义这样的依赖项的真正好处是,任何有权访问 package.json 的人都可以创建一个包含运行应用程序所需模块的依赖项文件夹,但是让我们来看看事情可能出错的具体方式。

假设我们创建了一个将使用 express 的新项目。 运行npm init后,我们安装express:npm install express - save。在编写代码时,最新的版本是4.15.4,所以 “express”:“^ 4.15.4”作为我的package.json中的依赖项添加,并且我的电脑安装了确切的版本。

现在也许明天,express 的维护者会发布 bug 修复,因此最新版本变为4.15.5。 然后,如果有人想要为我的项目做贡献,他们会克隆它,然后运行`npm install。’因为4.15.5是具有相同主要版本的更高版本,所以为它们安装。 我们都安装 express ,但我们却是不同的版本。

从理论上讲,它们应该仍然是兼容的,但也许bugfix会影响我们正在使用的功能,而且当使用Express版本4.15.4和4.15.5运行时,我们的应用程序会产生不同的结果。

Package-lock

目的

package-lock.json 的目的是避免上述情况,其中从同一 package.json 安装模块会导致两种不同的安装。 在 npm 版本 5.x.x 中添加了 package-lock.json,因此如果你使用的是主要版本 5 或更高版本,除非您禁用它,否则它会自动生成。

内容结构

package-lock 是 package.json 中列出的每个依赖项的大型列表,应安装的特定版本,模块的位置(URI),验证模块完整性的哈希,它需要的包列表 ,以及依赖项列表。 让我们来看看 express 的列表是什么:


"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" } },

可以在“requires”部分中列出的每个包中找到等效条目。

npm(^5.x.x.x)后的做法,npm 使用package-lock.json,而不是使用 package.json 来解析和安装模块。因为 package-lock 为每个模块及其每个依赖项指定了版本,位置和完整性哈希,所以它每次创建的安装都是相同的。 无论你使用什么设备,或者将来安装它都无关紧要,每次都应该给你相同的结果,这非常有用。

争议

因此,如果引用 package-lock 是希望解决一个常见问题,为什么它的顶级搜索结果(除了npm文档)都是关于禁用它或质疑它扮演的角色?

在npm 5.x.x之前,package.json 是项目的真实来源,npm 用户喜欢这个模型,并且非常习惯于维护他们的包文件。 但是,当首次引入 package-lock 时,它的行为与有多少人预期的相反。 给定一个预先存在的包和package-lock,对package.json的更改(许多用户认为是真实的来源)没有同步到package-lock 中。

示例:包A,版本 1.0.0 在 package.json 和 package.lock.json 中。 在package.json中,A被手动编辑为1.1.0版。 如果认为 package.json 是真实来源的用户运行 npm install,他们会期望安装 1.1.0版。 但是,安装了1.0.0版,即使列出的 v1.1.0 是 package.json, 他们也希望安装是 1.0.0版。

示例: package-lock.json 中不存在模块,但它存在于 package.json 中,作为一个将package.json 视为真实来源的用户,我希望能够安装我的模块。 但是,由于 package-lock.json 不存在该模块,因此未安装该模块,并且我的代码因无法找到模块而失败。

大部分时间,因为我们无法弄清楚为什么我们的依赖关系没有被正确安装,要么删除了package-lock.json 并重新安装,要么完全禁用 package-lock.json 来解决问题。

期望与真实行为之间的这种冲突在 npm repo中引发了一个非常有趣的问题线索。 有些人认为package.json 应该是事实的来源,有些人认为,因为 package-lock 是 npm 用来创建安装的东西,所以应该被认为是事实的来源。 这场争议的解决方案在于 PR#17508。 如果 package.json 已更新,Npm 维护者添加了一个更改,导致package.json 覆盖 package-lock。 现在,在上述两种情况下,都会正确安装用户期望安装的软件包。 此更改是作为npm v5.1.0的一部分发布的,该版本于2017年7月5日上线。

链接:http://blog.npmjs.org/post/115305091285/introducing-the-npm-semantic-version-calculator

看完两件小事

如果你觉得这篇文章对你挺有启发,我想请你帮我两个小忙:

  1. 关注我们的 GitHub 博客,让我们成为长期关系
  2. 把这篇文章分享给你的朋友 / 交流群,让更多的人看到,一起进步,一起成长!
  3. 关注公众号 「画漫画的程序员」,公众号后台回复「资源」 免费领取我精心整理的前端进阶资源教程

JS中文网是中国领先的新一代开发者社区和专业的技术媒体,一个帮助开发者成长的社区,目前已经覆盖和服务了超过 300 万开发者,你每天都可以在这里找到技术世界的头条内容。欢迎热爱技术的你一起加入交流与学习,JS中文网的使命是帮助开发者用代码改变世界

本文著作权归作者所有,如若转载,请注明出处

转载请注明:文章转载自「 Js中文网 · 前端进阶资源教程 」https://www.javascriptc.com

标题:你想知道关于package-lock.json的一切,但是太害怕了问了?

链接:https://www.javascriptc.com/3451.html

« JavaScript常用正则表达式备忘录
前端框架中路由的实现原理»
Flutter 中文教程资源

相关推荐

QR code