线上BUG引起思考:package.json 中的 ^~ 该保留吗?

一、写在前面
一次线上项目 bug,引发了关于 package.json 中的 ^~ 是否该保留?保留可能引发的后果?以及如何在版本更新便利和版本更稳定中取舍的思考?这个 bug 是由于线上部署打包时,自己下载了最新依赖,于是线上依赖版本和研发本地依赖版本不同,不巧的是最新依赖有 bug 而本地早先下载的没有, 导致了定位 bug 浪费了大量时间。

最后是发现 lock 的版本有差异,根据这个方向进一步定位到了 bug。

而会导致这种版安装的依赖版本差异的决定性原因则是 package.json 没有写死版本号,而是使用允许根据市场版本更新的指令符号 ^~。

那么如果希望避免上诉 bug,锁定依赖版本,可行的方案是什么?

本文将以上诉 bug 为引,尝试简单讨论和认识:

①package.json 中的 ^ ~
②依赖版本锁定:yarn 和 npm 等的 lock 锁定
③依赖版本锁定:package.json 的锁定
④让Git记下 lock 的变更记录的意义
⑤小结:前端工程项目依赖版本锁定的小结
二、package.json 中的 ^ ~
在这里插入图片描述

  1. ^ 意思是要更新【次版本】,当市场有更新的版本时,例如:package.json 中是"^2.1.0",库可能会更新到2.2.0的最新版本,但不会更新到3.0.0版本。 ~
  2. 意思是要更新【补丁版本】,当市场有更新的版本时,例如:package.json 中是"~2.1.0",库可能会更新到2.1.1的最新版本,但不会更新到2.2.0版本。
  3. 版本号前面啥也没有,表示写死了版本号,无论何时何地安装的依赖版本只会是这个。

三、怎么锁定工程依赖的版本
在实践中,工程依赖的版本锁定,可能会有两方面的考虑,一是通过包管理工具的 lock 进行版本依赖锁定, 二则是通过在 package.json 中写死版本号来“绝对锁定”依赖版本。依赖版本的锁定,是必须要考虑, 否则一个差异和不幸可能需要浪费大量时间去定位由此导致的 bug,那将是痛苦而不值得的,尽管发生的机会比较小。

3.1 package.json 的锁定
毫无疑问,package.json 具有依赖版本的决定权。是否在安装依赖时,下载新版本,是否修改 lock 版本,是由 package.json 中附带 ~ ^等命令符号结合市场最新版本决定的, 在决定性因素上,与使用的包管理工具并无多大关系,无论是 npm、yarn 或 pnpm。

只要,package.json 写死版本号,版本号前不携带那些 ~ ^等符号,那么无论何时何地何人安装依赖,依赖版本都会是一致的。

因此,在功能已经开发完毕,进入运维阶段的前端工程项目,如果希望减少由于依赖版本差异带来的莫名其面的 bug,那么写死 package.json 中版本号是可行可靠的。如果确有需要升级依赖版本,再单独手动去升级。项目上线转运维阶段后,需要批量更新依赖,从而使用新依赖的新功能的可能性较小, 而运维中项目保证项目的稳定才是更重要工作,毕竟“还能跑就行”。

3.2 yarn 和 npm 等的 lock 锁定
矛盾是总是存在的,总有不希望一个一个手动更新依赖的需求,总有希望“一键更新全部依赖”的场景。这种时候,package.json 中写死版本号,则不是期望的。那么某种程度上的依赖本锁定则出现了,这就是通过包管理工具的 lock 来锁定,例如 yarn 的 yarn.lock,npm 的 package-lock.json, 以及 pnpm 的 pnpm-lock.yaml。

据我观测一些知名的开源项目,通常也不会全部一锤将版本号都写死中 package.json,并且通常让Git记下 lock 的变更记录。例如:
在这里插入图片描述
在这里插入图片描述
3.3 yarn.lock 和 package-lock.json 下载新依赖上的区别
包管理工具的 lock 也具有某种程度上的“依赖版本锁定”功能,尽管不同的工具的 lock 表现具有差异。例如当 package-lock.json 存在时,即使市场上有比 package-lock.json 中锁定版本更新,且 package-lock.json 中存在 ^ ~ 允许更新, 安装的版本也只会是 package-lock.json 中锁定的版本,不会自动下载更新的版本。当然当 package.json 中版本被手动更新,会触发的 package-lock.json 连带变更。

而 yarn 的 yarn.lock 的“版本锁定”的则表现不同,当市场有比 yarn.lock 中更新的版本,且 package-lock.json 中存在 ^ ~ 允许更新, 那么 yarn 会自动安装比 yarn.lock 更新的版本并且主动修改 yarn.lock。

从这个差异角度看,package-lock.json 的“版本锁定”更可靠,可以起到依赖版本保持一致的作用,而 yarn.lock 则不具备。

3.4 让Git记下 lock 的变更记录
既然 yarn.lock 无法帮助我们“锁定”版本,那么 yarn.lock 的意思而在?我并不清楚 yarn.lock 设计全部意义,但我可以确定的一个价值是: 让Git记下 lock 的变更记录,有助于追踪使用的依赖版本记录,有时会很有作用,例如定位某类bug时。

即使 lock 会被修改,它的存在也会很有价值,例如:证明此前被 lock 的版本在本工程是可用的。因为会存在某个新下的最新版本存在缺陷或不符合本工程的需求的情形。这个新版本缺陷可能会导致工程无法运行或运行异常。

一个例子是,新同事安装工程出现工程运行异常,而旧同事正常,且通过 git 证明业务代码无差异,package.json 也无差异,此时差异会体现在 lock 的版本。此时要想使用最新且能确保本工程正常运行的依赖版本,那么旧同事 lock 的依赖版本就是答案。

而 package.json 中的版本虽然可用,但由于具有时间跨度的不确定性,可能会比 lock 的要旧很多。

知名的例子是 vue-router 的 issues #2881 中提到的,在升级了 Vue-Router 版本到3.1.0及以上之后,页面在跳转路由控制台会报Uncaught (in promise)的问题,从而导致某些场景的跳转异常。

3.5 关于依赖地狱( Dependency Hell)和依赖分身(Doppelgangers)
package.json 的依赖版本设置作用仅有效于当前工程,实践中依赖锁定往往会涉及嵌套依赖等问题,因为依赖也可能会有 package.json,依赖的依赖也可能会有 package.json。

但本文暂不讨论,关于依赖地域( Dependency Hell)和依赖分身(Doppelgangers)的问题。

四、小结

总结上述简单的分析和讨论,小结如下:

①package.json 具有锁定依赖版本的决定权,包管理工具不具有。 ②package.json ^ 意思是要更新【次版本】,~
意思是要更新【补丁版本】。 ③yarn 的 yarn.lock 和 npm 的 package-lock.json
对“锁定依赖版本”表现不同,package-lock.json 的“锁定效果”更可靠。 ④让Git记下 lock
的变更记录是有意义的。一些知名开源项目都让Git记下 lock 的变更记录。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/235688.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

硬件基础-电感

电感 目录 1.原理 2.作用 3.高频等效模型 4. 直流偏置特性 5.器件选型 6.电感损耗 7.功率电感 8.贴片电感 9.共模电感 10.差模电感 1.原理 电感是阻碍电流的变化,储能 电感的磁芯决定了电感的饱和电流,也决定了电感值与电流的变化曲线,磁滞损…

P1 H264码流结构分析 (上)

目录 前言 01 什么是码流结构 02 H264帧类型的区别 03 片slice 前言 从本章开始我们将要学习嵌入式音视频的学习了 ,使用的瑞芯微的开发板 🎬 个人主页:ChenPi 🐻推荐专栏1: 《C_ChenPi的博客-CSDN博客》✨✨✨ &#x1f525…

石器时代H5小游戏架设教程

本文讲解石器时代 H5 之恐龙宝贝架设教程,想研究 H5 游戏如何实现,那请跟着此次教程学习在拥有小游戏源码的情况下该如何搭建起来 开始架设 1. 架设条件 石器时代架设需要准备: 一台linux 服务器,建议 CentOs 7.6 版本&#xf…

ros2 学习08 topic 话题定义及示例

topic 在ros 中的作用 节点实现了机器人各种各样的功能,但这些功能并不是独立的,之间会有千丝万缕的联系,其中最重要的一种联系方式就是话题,它是节点间传递数据的桥梁。 大家可以想一下,这两个节点是不是必然存在某种…

作业--day34

使用select完成TCP并发服务器和客户端 server.c #include <myhead.h>#define PORT 8888 #define IP "192.168.125.137"int main(int argc, const char *argv[]) {int sfd socket(AF_INET, SOCK_STREAM, 0);if(sfd -1){perror("socket error");re…

Docker 网络模式 -day05

docker 启动时候还会有&#xff0c;名为docker0的虚拟网桥&#xff0c;注意网址为 127.0.0.1 [rootiZuf6hxabqikytnrumsi4gZ ~]# ifconfig docker0: flags4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500inet 172.17.0.1 netmask 255.255.0.0 broadcast 172.17.255.2…

基于k6和python进行自动化性能测试

摘要&#xff1a;在性能测试中&#xff0c;达到相应的性能指标对于一个软件来说十分重要&#xff0c;在本文中&#xff0c;将介绍一种现代化性能测试工具k6。 import http from k6/http; import { sleep } from k6; export default function () {http.get(https://test-api.co…

Backend - Django 项目创建 运行

目录 一、配置环境 二、创建 Django 项目 &#xff08;一&#xff09;新建文件夹 &#xff08;二&#xff09;打开文件夹 &#xff08;三&#xff09;打开运行终端 &#xff08;四&#xff09;创建基础项目 &#xff08;五&#xff09;创建app 1. 安装Django &#xf…

note-1

一个“逆向思维”的小例子&#xff1a;“一男生晚上到某银行ATM机存款&#xff0c;碰ATM机出现故障&#xff0c;5000元被吞。当即联系银行&#xff0c;被告知要等到天亮才能维修。其绞尽脑汁的想突然灵机一动&#xff0c;使用公用电话致电客服称&#xff1a;ATM机多吐出3000元&…

VR智慧酒店:提升人气入住率,助力酒店开辟新赛道

随着智能科技的不断进步&#xff0c;智能感、科技感也体现在我们的住宿体验上&#xff0c;VR智慧酒店可以让用户沉浸式体验高质量的酒店服务&#xff0c;这种全新的体验方式助力开启智能化酒店获客新模式&#xff0c;引爆超人气入住率。 传统的酒店行业推广成本高、效果差&…

map|动态规划|单调栈|LeetCode975:奇偶跳

作者推荐 【贪心算法】【中位贪心】.执行操作使频率分数最大 涉及知识点 单调栈 动态规划 map 题目 给定一个整数数组 A&#xff0c;你可以从某一起始索引出发&#xff0c;跳跃一定次数。在你跳跃的过程中&#xff0c;第 1、3、5… 次跳跃称为奇数跳跃&#xff0c;而第 2、…

linux 驱动——私有数据

文章目录 linux 驱动中的私有数据container_of驱动程序应用程序模块使用 linux 驱动中的私有数据 container_of 参考&#xff1a;linux——宏 list_entry/container_of 驱动程序 #include "linux/device/class.h" #include "linux/export.h" #include…

Python人脸识别

实现效果 代码 import cv2# 加载人脸识别分类器 face_cascade cv2.CascadeClassifier(haarcascade_frontalface_default.xml)# 打开摄像头 cap cv2.VideoCapture(0)while True:# 读取摄像头捕获的帧ret, frame cap.read()# 将帧转换为灰度图像gray cv2.cvtColor(frame, c…

迪文屏开发保姆级教程——页面键盘

迪文屏页面键盘保姆级教程。 本篇文章主要介绍了在DGBUS平台上使用页面键盘的步骤。 迪文屏官方开发指南PDF&#xff1a;&#xff08;不方便下载的私聊我发给你&#xff09; https://download.csdn.net/download/qq_21370051/88647174?spm1001.2014.3001.5503https://downloa…

vivado 关于时钟

关于时钟 在数字设计中&#xff0c;时钟代表了从寄存器可靠传输数据的时间基准注册。AMD Vivado™集成设计环境&#xff08;IDE&#xff09;计时引擎使用时钟计算时序路径要求并通过以下方式报告设计时序裕度的特性松弛计算的方法有关更多信息&#xff0c;请参阅Vivado Design…

AI百模大战:引领行业变革与开启人才黄金时代

&#x1f34e;个人博客&#xff1a;个人主页 &#x1f3c6;个人专栏&#xff1a;Linux学习 ⛳️ 功不唐捐&#xff0c;玉汝于成 目录 前言 技术进步&#xff1a;AI的飞速发展 1. 深度学习的多领域应用 2. 自然语言处理的语境理解提升 3. 计算机视觉的实时处理能力提高 4…

Python学习笔记(六):函数的多返回值、函数的多种参数使用形式、匿名函数、文件的读取操作、文件的写入 、文件的追加

目录 一、函数的多返回值 二、函数的多种参数使用形式 2.1位置参数 2.2关键字参数 2.3缺省参数 2.4不定长参数 三、匿名函数 3.1 函数作为参数传递 3.2 函数的定义 3.3 匿名函数定义语法&#xff1a; 四、文件的读取操作 4.1 open&#xff08;&#xff09;打开函数…

图卷积神经网络发展

1. 图神经网络&#xff08;GNN&#xff09; 图神经网络的概念最早在2005年提出。2009年Franco博士在其论文 [2]中定义了图神经网络的理论基础。 本文中所提到的图均指图论中的图(Graph)。它是一种由若干个结点(Node)及连接两个结点的边(Edge)所构成的图形&#xff0c;用于刻画…

【模式识别】解锁降维奥秘:深度剖析PCA人脸识别技术

​&#x1f308;个人主页&#xff1a;Sarapines Programmer&#x1f525; 系列专栏&#xff1a;《模式之谜 | 数据奇迹解码》⏰诗赋清音&#xff1a;云生高巅梦远游&#xff0c; 星光点缀碧海愁。 山川深邃情难晤&#xff0c; 剑气凌云志自修。 目录 &#x1f30c;1 初识模式识…

智能化物联网(IoT):发展、问题与未来前景

导言 智能化物联网&#xff08;IoT&#xff09;作为信息技术领域的一项核心技术&#xff0c;正在深刻改变人们的生活和工作方式。本文将深入研究IoT的发展过程、遇到的问题及解决过程、未来的可用范围&#xff0c;以及在各国的应用和未来的研究趋势。探讨在哪些方面能够取得胜利…