一、pnpm 是什么?
pnpm(Performant NPM)是由 Zoltan Kochan 开发的高性能 Node.js 包管理器,核心定位是解决 npm/yarn 存在的磁盘空间占用高、安装速度慢、依赖嵌套过深等问题,同时兼容 npm 的大部分功能和生态。
简单来说:pnpm = 极致的磁盘利用率 + 超快的安装速度 + 严格的依赖管理。
二、核心优势(对比 npm/yarn)
1. 极致的磁盘空间利用率
-
硬链接 + 符号链接(Symlink)机制 :pnpm 会在全局目录(默认
~/.pnpm-store)中存储所有安装过的包的单一副本 ,后续项目安装相同版本的包时,不会重复下载,而是通过「硬链接」复用全局存储的文件,通过「符号链接」构建项目的node_modules结构。- 对比:npm/yarn 会在每个项目的
node_modules中完整复制依赖包,多项目场景下磁盘占用呈倍数增长。 - 举例:10 个项目都依赖
lodash@4.17.21,pnpm 仅存储 1 份 lodash 文件,而 npm/yarn 会存储 10 份。
- 对比:npm/yarn 会在每个项目的
2. 超快的安装速度
- 复用全局缓存减少下载次数;
- 并行安装依赖(比 npm 更早优化并行逻辑);
- 扁平化依赖结构但避免「幽灵依赖」(下文解释),减少文件 IO 开销。
- 实测:安装大型项目依赖时,pnpm 速度通常是 npm 的 2-5 倍,比 yarn classic 快 1.5-3 倍。
3. 严格的依赖管理(避免幽灵依赖)
- npm/yarn classic 的
node_modules是嵌套 + 扁平化混合结构,可能导致项目引用未在package.json中声明的依赖(幽灵依赖); - pnpm 的
node_modules是严格的符号链接结构 :只有在package.json中声明的依赖才会出现在项目的node_modules根目录,间接依赖无法被直接引用,从根源避免幽灵依赖,提升项目可维护性。
4. 其他优势
- 兼容 npm 命令:
pnpm install/pnpm add/pnpm run等命令与 npm 基本一致,学习成本低; - 内置工作区(monorepo)支持:无需额外配置,即可高效管理多包项目;
- 可配置的存储路径:支持自定义全局包存储目录,适配不同环境;
- 零安装(optional):支持
pnpm fetch预下载依赖,离线环境也能安装。
三、核心原理:pnpm 的 node_modules 结构
pnpm 的 node_modules 分为两层:
-
全局存储层 :
~/.pnpm-store存储所有包的原始文件(每个版本仅一份); -
项目链接层:
- 项目根目录的
node_modules中,只有package.json声明的依赖(如react),且是指向node_modules/.pnpm/react@18.2.0/node_modules/react的符号链接; node_modules/.pnpm目录中,存储所有依赖的硬链接副本,且每个依赖的node_modules仅包含自身的直接依赖,形成严格的依赖树。
- 项目根目录的
这种结构既保证了磁盘复用,又保证了依赖的严格隔离。
四、安装 pnpm
1. 通用安装方式(推荐)
bash
运行
bash
# 使用 npm 安装(全局)
npm install -g pnpm
# 或使用官方脚本(跨平台)
curl -fsSL https://get.pnpm.io/install.sh | sh -
# 或(Windows PowerShell)
iwr https://get.pnpm.io/install.ps1 -useb | iex
2. 其他方式
- Homebrew(macOS/Linux) :
brew install pnpm; - Scoop(Windows) :
scoop install pnpm; - Docker :
docker run --rm -it pnpm/pnpm:latest。
3. 验证安装
bash
运行
bash
pnpm -v # 输出版本号即安装成功(当前稳定版为 v9.x)
五、常用命令(与 npm 对比)
| 功能 | npm 命令 | pnpm 命令 |
|---|---|---|
| 安装所有依赖 | npm install |
pnpm install |
| 添加生产依赖 | npm install react |
pnpm add react |
| 添加开发依赖 | npm install -D typescript |
pnpm add -D typescript |
| 全局安装包 | npm install -g ts-node |
pnpm add -g ts-node |
| 卸载依赖 | npm uninstall react |
pnpm remove react |
| 运行脚本 | npm run dev |
pnpm run dev |
| 查看全局包存储路径 | npm root -g |
pnpm store path |
| 清理缓存 | npm cache clean --force |
pnpm store prune |
特有 / 增强命令
bash
运行
python
# 查看依赖树(比 npm ls 更清晰)
pnpm list
# 预下载依赖(离线安装用)
pnpm fetch
# 构建 monorepo 项目(工作区)
pnpm -r build # 递归执行所有子包的 build 脚本
pnpm --filter pkg-name dev # 仅执行指定子包的 dev 脚本
# 更新依赖
pnpm update # 更新所有依赖
pnpm update react # 更新 react 到最新兼容版本
六、pnpm 配置(可选)
pnpm 的配置文件为 .npmrc 或 .pnpmrc,常用配置:
ini
ini
# 自定义全局存储路径
store-dir=/path/to/pnpm-store
# 启用严格模式(默认开启,禁止引用未声明的依赖)
strict-peer-dependencies=true
# 国内镜像(加速下载)
registry=https://registry.npmmirror.com/
七、适用场景
- 多项目开发:多个项目依赖相同包版本时,大幅节省磁盘空间;
- 大型项目 / 团队协作:严格的依赖管理避免幽灵依赖,减少线上问题;
- Monorepo 项目:内置工作区支持,无需额外配置 lerna/yarn workspace;
- 追求安装速度:替代 npm/yarn 提升开发效率。
八、注意事项
- 兼容性 :pnpm 生成的
node_modules结构与 npm 不同,极少数老包可能因路径问题兼容异常(可通过pnpm config set node-linker hoisted切换为扁平化结构临时解决); - 全局包 :pnpm 全局安装的包路径与 npm 不同,需确保
pnpm bin -g路径加入系统环境变量; - lockfile :pnpm 生成
pnpm-lock.yaml,与 npm 的package-lock.json、yarn 的yarn.lock不兼容,团队需统一包管理器。
总结
pnpm 是 npm/yarn 的高性能替代方案,核心优势是「省空间、快安装、严依赖」,完全兼容 npm 生态,且对 monorepo 支持友好。无论是个人项目还是企业级项目,都能显著提升依赖管理效率,目前已被 Vite、Nuxt、Turborepo 等主流工具推荐使用。