当一个npm包被删除时会发生什么?

3
我正在阅读一篇关于流行的npm包(left-pad)作者删除自己的包后导致应用程序崩溃的文章。
这怎么可能呢?不是在执行`npm install --save`时会本地下载npm包的代码吗?我想唯一可能出现问题的情况是那些通过CDN使用该项目的人。我的假设正确吗?
原文链接:https://www.theregister.co.uk/2016/03/23/npm_left_pad_chaos/

当你执行npm install {anything}时,它会将包下载到本地的node_modules文件夹中,并继续运行。--save选项确保您的package.json文件反映了您在项目中使用的确切版本。这在某人安装您的模块时很重要,他们将获得相同的版本而不是最新版本。如果该软件包被删除并且您的软件包依赖于它,则当某人尝试从头安装您的软件包时,这将导致问题(因为他们需要下载现在已删除的软件包)。 - Nick Dima
如果源代码安装在node_modules文件夹中,会有什么问题? - lightspeed
1
@lightspeed 因为在构建过程中通常会执行 npm install。好吧,想一想。它将尝试下载已删除的软件包并失败,因为它不存在。 - Isaac Vidrine
这是否意味着每个构建过程都需要网络连接?我记得曾经离线进行构建? - lightspeed
2
在自动化部署中,@lightspeed,你当然可以通过ssh登录到机器上手动更新和启动应用程序。但是CI/CD环境的整个意义在于,您可以将代码推送到源代码控制并自动进行构建/部署过程。您只需要执行git push命令即可。正如Nik Kyriakides所说,这一点非常美妙。 - Isaac Vidrine
显示剩余9条评论
1个回答

7

大多数项目不会将实际模块提交到源代码控制中

node_modules文件夹通常不会上传到Git或SVN等源代码控制中。它往往是一个庞大的文件夹,每次推送/拉取都会很麻烦。

此外,一些模块包含C++代码,并在安装时编译为用户的操作系统。我可能与安装它的用户有不同的操作系统,因此如果我盲目地从源代码控制下载他的已编译版本的该模块,则该模块将无法工作。

相反,会包含一个小的配置文件,例如package.json,其中描述了项目所需的模块。当您运行$ npm install时,包管理器(npmyarn)会读取该文件并开始下载它引用的模块。

每次部署或克隆项目时,计算机会从其存储库下载源代码,但不包括模块(因为它们不在源代码控制中),然后人或机器运行$ npm install以获取相关/必需的模块。

项目一直在部署和构建

现在,项目会在远程服务器上一直部署;即将项目部署到生产服务器或在远程CI服务器上运行测试,甚至由其他开发人员在其本地机器上克隆。我工作的项目每天至少在远程CI服务器上部署和测试5次;每当我们向远程存储库推送提交时。

由于该用户删除了很多依赖模块,全球范围内许多$ npm install都开始失败。许多人无法将更新推送到其生产服务器上的项目,其他开发人员无法在其机器上获取该项目以进行工作等...

为防止这些问题,npm引入了一个政策,禁止取消发布超过72小时的模块:

来自npm

注册表数据是不可变的,这意味着一旦发布,包就不能更改。出于安全和依赖于这些软件包的用户的稳定性的原因,我们这样做。因此,如果您曾经发布过名为“bob”的版本1.1.0的软件包,则其他软件包永远无法以该名称和版本发布。即使取消发布该软件包也是如此。但是,由于意外情况的发生,我们允许用户在72小时内取消发布他们刚创建的软件包。


有道理。每次构建时都会进行新的 npm install 吗?我可以想象出一些不修改依赖项的项目更新。 - lightspeed
我不确定,所以无法回答。我只知道如果我(或我的部署/CI服务器)运行 $ npm install,安装的模块将与 package.json 描述的相符。 - nicholaswmin
在某些情况下,也有可能取消发布 早于 72 小时 的版本,因此这种保护措施并不总是能够保护您。 - Guy Rotem
这太棒了,我一直在苦苦寻找像jfrog或nexus这样的解决方案,以便拥有我们团队正在使用的库的存储库。有了npm的保障,我不确定我是否仍然会使用那些工具。 - TalesMGodois

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接