新版 pnpm 自己也能读取 package.jsonpackageManager 字段,不一定需要 Corepack 才能切换项目使用的 pnpm 版本。

{
  "packageManager": "pnpm@11.0.0"
}

假设系统入口是 pnpm 11.21.0,进入这个项目运行 pnpm --version 时,它可以自动下载并执行 11.0.0:

全局 pnpm 11.21.0
  → 读取 packageManager
  → 下载 pnpm 11.0.0
  → 用 11.0.0 执行当前命令

从哪个版本开始支持

  • pnpm 9.7.0:首次加入版本管理,但需要设置 manage-package-manager-versions=true
  • pnpm 10.0.0:该功能默认开启;
  • pnpm 11:移除 managePackageManagerVersions 等旧设置,统一由 pmOnFail 控制;默认值为 download,仍会自动下载。

所以实际使用时,可以安装一个较新的 pnpm 作为启动入口,再让各项目通过 packageManager 固定自己的版本。

下载到了哪里

pnpm 自管理的版本放在 pnpm store,而不是项目 node_modules。不要假设固定目录,直接查询当前配置:

pnpm store path

Corepack 使用另一套缓存;默认由 COREPACK_HOME 决定,未覆盖时在 macOS/Linux 通常位于:

~/.cache/node/corepack/

排查时不要只看 pnpm --version,还应确认入口和缓存:

command -v pnpm
npm list --global --depth=0
corepack pnpm --version
pnpm store path

command -v pnpm 指向 npm 全局安装目录,说明入口是全局 pnpm;指向 Corepack shim,说明入口由 Corepack 提供。两种方式都可能读取同一个 packageManager 字段,但下载位置和代理链路不同。

参考:pnpm 9.7 发布说明pnpm 10 发布说明pnpm 11 发布说明pnpm Settings