node应用线上部署时锁定包的依赖版本

简介:

npm shrinkwrap

我们使用node开发时,经常需要依赖一些模块来完成功能需求,而我们所依赖的模块也必然会依赖其他模块,就这样一级一级的依赖,而且这些依赖模块并不为我们所控制。一个产品或项目的开发周期,少则几个周,多则几个月几年。开发人员往往在一开始时下载了依赖包发现能够正常工作后,便一直在依赖包的当前版本上工作,然而在线上服务器布属时往往是根据依赖配置文件,重新下载依赖包。可这个时候依赖链中的包的开发者很可能已经将某个模块升级了,而且并不能保证这些新的依赖包没有bug。一旦依赖链上的某个包出现bug,可能对产品造成严重影响,而且这个时候往往无法找回开发时所用的正确依赖,以及依赖的依赖的版本。
我们来看一个经典的例子:
假设有包A依赖包B,包B依赖包C:

//包A
{
  "name": "A",
  "version": "0.1.0",
  "dependencies": {
    "B": "<0.1.0"
  }
}
//包B
{
  "name": "B",
  "version": "0.0.1",
  "dependencies": {
    "C": "<0.1.0"
  }
}
//包C
{
  "name": "C",
  "version": "0.0.1"
}

假设在开发时,我们运行npm install A得到以下的依赖链:

A@0.1.0
`-- B@0.0.1
    `-- C@0.0.1

而在项目需要部署上线时,我们不可能把所有node_modules放到线上服务器中,所以将项目代码放到服务器时,我们便会运行npm install A,而恰恰这阶段,包B的版本更新到了0.0.8,所以我们在服务器上得到的依赖链就是:

A@0.1.0
`-- B@0.0.8
    `-- C@0.0.1

如果B的新版本有问题,这时就会对产品造成难以预估的损失。
所以我们推荐当开发环境中,所有依赖模块都能正常工作时,便在部署到服务器之前将依赖包的版本锁住,这时候就运行这个命令:

npm shrinkwrap

我们会得到一个npm-shrinkwrap.json的文件,这个文件保存了所有当前使用的依赖模块的版本:

{
  "name": "A",
  "version": "0.1.0",
  "dependencies": {
    "B": {
      "version": "0.0.1",
      "from": "B@^0.0.1",
      "resolved": "https://registry.npmjs.org/B/-/B-0.0.1.tgz",
      "dependencies": {
        "C": {
          "version": "0.0.1",
          "from": "org/C#v0.0.1",
          "resolved": "git://github.com/org/C.git#5c380ae319fc4efe9e7f2d9c78b0faa588fd99b4"
        }
      }
    }
  }
}

将这个文件连同项目源码一同部署到服务器上,然后运行npm install这时候,npm会首先检查有没有npm-shrinkwrap.json文件,有的话会根据该文件中依赖包的版本以及resolve字段下载依赖包,这样就能够保证线上环境与开发环境一致。

from 与 resolve

这个文件时根据我们当前项目中的node_modules中的模块的当前版本生成的。version代表当前模块版本,from表示的是package.json中对该依赖模块的版本描述,resolve代表当前模块的实际来源。
比如当你的package.json中对于某个依赖模块有如下描述:

"dependencies": {
    "acorn": "^3.0.0",
....................................
  }

acorn模块安装后,它的package.json文件中会出现如下字段:

  "_from": "acorn@>=3.0.0 <4.0.0",
  "_resolved": "https://registry.npmjs.org/acorn/-/acorn-3.2.0.tgz",

这时候运行npm shrinkwrap便会出现:

  "dependencies": {
    "acorn": {
      "version": "3.2.0",
      "from": "acorn@>=3.0.0 <4.0.0",
      "resolved": "https://registry.npmjs.org/acorn/-/acorn-3.2.0.tgz"
    },

对于npm-shrinkwrap.json来说,这其中最重要的就是resolve字段。

使用npm shrinkwrap的注意事项

  • 如果要安装新的依赖模块,一定要使用npm install --save 模块,这样保证package.json与npm-shrinkwrap.json文件同步更新。
  • node_modules中的模块必须能够包含package.json中的依赖模块,如果node_modules中不存在package.json中指定的依赖模块,运行npm shrinkwrap会报错;如果node_modules中包含有package.json中未指定的模块,根据官方说法是也会报错,但根据我的实验(windows7系统)并没有报错,npm-shrinkwrap.json会包含所有在node_modules中的模块。
  • npm-shrinkwrap.json中并不会包含devDependencies字段中的模块。

参考文章:

npm-shrinkwrap-Lock down dependency versions

目录
相关文章
|
9月前
|
JavaScript 前端开发
如何减少Node.js应用中的全局变量?
如何减少Node.js应用中的全局变量?
473 133
|
9月前
|
监控 负载均衡 JavaScript
有哪些有效的方法可以优化Node.js应用的性能?
有哪些有效的方法可以优化Node.js应用的性能?
442 69
|
6月前
|
存储 监控 JavaScript
基于布隆过滤器的 Node.js 算法在局域网电脑桌面监控设备快速校验中的应用研究
本文探讨了布隆过滤器在局域网电脑桌面监控中的应用,分析其高效空间利用率、快速查询性能及动态扩容优势,并设计了基于MAC地址的校验模型,提供Node.js实现代码,适用于设备准入控制与重复数据过滤场景。
249 0
|
JSON JavaScript Linux
【MCP教程系列】Node.js+TypeScript搭建NPX MCP服务并自定义部署至阿里云百炼
本文介绍如何将阿里云百炼的工作流封装成MCP服务并部署,随后引入到智能体中使用。主要步骤包括:1) 封装MCP服务;2) 发布到npm官方平台;3) 在阿里云百炼平台创建自定义MCP服务;4) 在智能体中添加自定义MCP服务。通过这些步骤,用户可以轻松将工作流转化为MCP服务,并在智能体中调用。
3438 0
|
5月前
|
运维 监控 JavaScript
基于 Node.js 图结构的局域网设备拓扑分析算法在局域网内监控软件中的应用研究
本文探讨图结构在局域网监控系统中的应用,通过Node.js实现设备拓扑建模、路径分析与故障定位,提升网络可视化、可追溯性与运维效率,结合模拟实验验证其高效性与准确性。
314 3
|
9月前
|
监控 算法 JavaScript
公司局域网管理视域下 Node.js 图算法的深度应用研究:拓扑结构建模与流量优化策略探析
本文探讨了图论算法在公司局域网管理中的应用,针对设备互联复杂、流量调度低效及安全监控困难等问题,提出基于图论的解决方案。通过节点与边建模局域网拓扑结构,利用DFS/BFS实现设备快速发现,Dijkstra算法优化流量路径,社区检测算法识别安全风险。结合WorkWin软件实例,展示了算法在设备管理、流量调度与安全监控中的价值,为智能化局域网管理提供了理论与实践指导。
235 3
|
12月前
|
弹性计算 JavaScript 前端开发
一键安装!阿里云新功能部署Nodejs环境到ECS竟然如此简单!
Node.js 是一种高效的 JavaScript 运行环境,基于 Chrome V8 引擎,支持在服务器端运行 JavaScript 代码。本文介绍如何在阿里云上一键部署 Node.js 环境,无需繁琐配置,轻松上手。前提条件包括 ECS 实例运行中且操作系统为 CentOS、Ubuntu 等。功能特点为一键安装和稳定性好,支持常用 LTS 版本。安装步骤简单:登录阿里云控制台,选择扩展程序管理页面,安装 Node.js 扩展,选择实例和版本,等待创建完成并验证安装成功。通过阿里云的公共扩展,初学者和经验丰富的开发者都能快速进入开发状态,开启高效开发之旅。
|
10月前
|
存储 JavaScript 前端开发
在NodeJS中使用npm包进行JS代码的混淆加密
总的来说,使用“javascript-obfuscator”包可以帮助我们在Node.js中轻松地混淆JavaScript代码。通过合理的配置,我们可以使混淆后的代码更难以理解,从而提高代码的保密性。
987 9
|
10月前
|
JavaScript 算法 前端开发
nodejs18版本 npm run dev失败
在使用若依框架运行 `npm run dev` 时,若卡在 95% 并报错,通常是 Node.js 17+ 与 Webpack 的兼容性问题。原因是 OpenSSL 3 的加密算法变化导致依赖冲突。解决方法:Windows 下运行 `set NODE_OPTIONS=--openssl-legacy-provider`,macOS/Linux 使用 `export NODE_OPTIONS=--openssl-legacy-provider`,然后重新启动开发服务即可。此设置让 Node.js 启用旧版加密支持,恢复正常构建流程。
975 0