前端进阶之旅前端进阶之旅
基础篇
进阶篇
高频篇
精选篇
手写篇
原理篇
面经篇
自检篇
每日一题
  • 综合
    • 综合题型
    • 其他问题
    • 设计模式
    • 思维导图
    • 学习路线
  • 前端基础
    • HTTP
    • 浏览器
    • 计算机基础
  • 进阶学习
    • NPM工作流
    • Docker
    • Canvas
    • Node学习指南
    • 前端综合文章
  • 其他
    • Handbook
    • 职场话题
    • CSS可视化
小程序题库
公众号动态
博客动态
开发者导航
基础篇
进阶篇
高频篇
精选篇
手写篇
原理篇
面经篇
自检篇
每日一题
  • 综合
    • 综合题型
    • 其他问题
    • 设计模式
    • 思维导图
    • 学习路线
  • 前端基础
    • HTTP
    • 浏览器
    • 计算机基础
  • 进阶学习
    • NPM工作流
    • Docker
    • Canvas
    • Node学习指南
    • 前端综合文章
  • 其他
    • Handbook
    • 职场话题
    • CSS可视化
小程序题库
公众号动态
博客动态
开发者导航

拯救磁盘空间 为什么pnpm是更好的包管理工具

首页
2023-05-26 14:40:12
Front-End
pnpmnpmyarn包管理工具前端工程化Workspace

在前端开发中,我们每天都会与各种npm包打交道,选择一个合适的包管理工具能显著提升开发体验和构建效率。近年来,pnpm作为一款新兴的包管理工具逐渐受到越来越多开发者青睐,它究竟有何魅力能让众多开源项目纷纷转投其怀抱?本文将带你深入了解pnpm的原理与优势。

# 一、为什么需要更好的包管理工具

# 1.1 npm与yarn的发展历程

在早期npm 1、npm 2时代,项目的node_modules会呈现出嵌套结构:

node_modules
└─ foo
   ├─ index.js
   ├─ package.json
   └─ node_modules
      └─ bar
         ├─ index.js
         └─ package.json
@前端进阶之旅: 代码已经复制到剪贴板

这种嵌套依赖树设计存在三个严重问题:

问题一:依赖层级太深

这会导致文件的路径过长的问题,尤其在Windows系统下文件路径默认最多支持256个字符。

问题二:包重复安装

比如foo和zoo都依赖于bar,那么bar就会在两者的node_modules中被安装两次,导致项目体积暴涨。

问题三:模块实例不能共享

比如React有一些内部变量,在两个不同包引入的React不是同一个模块实例,因此无法共享内部变量,导致一些不可预知的bug。

后来yarn横空出世解决了这些问题,npm也在3.0版本中沿用了yarn的解决方案,这个解决方案就是扁平化依赖。

# 1.2 扁平化依赖带来的新问题

所谓的扁平化依赖就是将所有依赖铺平,放到同一级目录下:

node_modules
├─ foo
│  ├─ index.js
│  └─ package.json
└─ bar
   ├─ index.js
   └─ package.json
@前端进阶之旅: 代码已经复制到剪贴板

虽然之前的问题得到了解决,但这种扁平化的处理方式自身也存在许多问题:

问题一:幽灵依赖

所谓的幽灵依赖是指我们明明没有在package.json的dependencies里声明某个依赖,但在代码里却可以import进来。因为项目依赖被铺平了,那么依赖的依赖自然也是可以被引入到项目中。

幽灵依赖带来的弊端很明显:我们显式依赖了A,A又依赖了B,这时候我们在项目中直接使用B是可以的,但如果某一天A不再依赖于B,那么我们项目中使用B的地方就会报错。

问题二:依赖结构不确定性

举例来说,如果项目同时依赖foo和bar,而它们都依赖不同版本的lodash,那么最终安装哪个版本是不确定的,完全取决于package.json中的声明顺序。

这就是为什么会产生依赖结构的不确定问题,也是lock文件诞生的原因,无论是package-lock.json还是yarn.lock,都是为了保证install之后都产生确定的node_modules结构。

问题三:非法访问依赖

由于扁平化结构,如果A依赖B,B依赖C,那么A当中是可以直接使用C的,但A并没有声明C这个依赖,这就是非法访问。

在monorepo项目中,如果A依赖X,B依赖X,还有一个C,它不依赖X,但它代码里面用到了X。由于依赖提升的存在,npm/yarn会把X放到根目录的node_modules中,这样C在本地是能够跑起来的。但试想一下,一旦C单独发包出去,用户单独安装C,那么就找不到X了,执行到引用X的代码时就直接报错了。

正是这些问题促使了pnpm的诞生。

# 二、pnpm是什么

pnpm(Performant NPM)是一个快速的、节省磁盘空间的包管理工具,同时它还对monorepo有良好的支持。

# 安装pnpm
npm i pnpm -g
@前端进阶之旅: 代码已经复制到剪贴板

它的用处与npm和yarn并没有什么本质区别,甚至连用法都十分相似,但却在性能和安全性方面有显著优势。

# 三、pnpm核心优势

# 3.1 安装速度快

根据官方文档的benchmark测试数据,pnpm在大多数场景下的安装速度都要优于npm和yarn。

可以看到,pnpm在绝多大数场景下,包安装的速度都是明显优于npm/yarn,速度会比npm/yarn快2-3倍。

对yarn比较熟悉的同学可能会说,yarn不是有<

fe
  • 一、为什么需要更好的包管理工具
    • 1.1 npm与yarn的发展历程
    • 1.2 扁平化依赖带来的新问题
  • 二、pnpm是什么
  • 三、pnpm核心优势
    • 3.1 安装速度快
    • 3.2 节省磁盘空间
    • 3.3 安全性高
    • 3.4 支持Monorepo
  • 四、pnpm依赖管理原理
    • 4.1 npm/yarn的安装原理
    • 4.2 node_modules目录结构
    • 4.3 软链接与硬链接的协作
  • 五、pnpm工作空间(Workspace)完全指南
    • 5.1 什么是Monorepo
    • 5.2 创建Workspace项目
    • 5.3 Workspace常用命令
    • 5.4 Workspace内部依赖
    • 5.5 发布配置
  • 六、pnpm基本使用
    • 6.1 安装依赖
    • 6.2 更新与卸载
    • 6.3 运行脚本
    • 6.4 其他常用命令
  • 七、三者功能对比一览
    • 核心差异解读
  • 八、总结

← 前端文件下载完全指南:10+种方案对比与实战代码Formily核心概念解析,构建复杂表单的最佳实践总结 →