Major Changes
Store
-
Runtime dependencies are always linked from the global virtual store #10233.
-
Optimized index file format to store the hash algorithm once per file instead of repeating it for every file entry. Each file entry now stores only the hex digest instead of the full integrity string (
<algo>-<digest>). Using hex format improves performance since file paths in the content-addressable store use hex representation, eliminating base64-to-hex conversion during path lookups. -
Store version bumped to v11.
-
Switched internal store and cache files from JSON to MessagePack format for improved performance.
This change migrates all internal index files and metadata cache files to use MessagePack serialization instead of JSON. MessagePack provides faster serialization/deserialization and more compact file sizes, resulting in improved installation performance.
Related PR: #10500
-
Store the bundled manifest (name, version, bin, engines, scripts, etc.) directly in the package index file, eliminating the need to read
package.jsonfrom the content-addressable store during resolution and installation. This reduces I/O and speeds up repeat installs #10473.
Global Packages
-
Global installs (
pnpm add -g pkg) andpnpm dlxnow use the global virtual store by default. Packages are stored at{storeDir}/linksinstead of per-project.pnpmdirectories. This can be disabled by settingenableGlobalVirtualStore: false#10694. -
Isolated global packages. Each globally installed package (or group of packages installed together) now gets its own isolated installation directory with its own
package.json,node_modules/, and lockfile. This prevents global packages from interfering with each other through peer dependency conflicts, hoisting changes, or version resolution shifts.Key changes:
pnpm add -g <pkg>creates an isolated installation in{pnpmHomeDir}/global/v11/{hash}/pnpm remove -g <pkg>removes the entire installation group containing the packagepnpm update -g [pkg]re-installs packages in new isolated directoriespnpm list -gscans isolated directories to show all installed global packagespnpm install -g(no args) is no longer supported; usepnpm add -g <pkg>instead
Configuration
-
pnpm config get(without--json) no longer print INI formatted text.
Instead, it would print JSON for both objects and arrays and raw string for
strings, numbers, booleans, and nulls.
pnpm config get --jsonwould still print all types of values as JSON like before. -
pnpm config get <array>now prints a JSON array. -
pnpm config listnow prints a JSON object instead of INI formatted text. -
pnpm config listandpnpm config get(without argument) now hide auth-related settings. -
pnpm config listandpnpm config get(without argument) now show top-level keys as camelCase.
Exception: Keys that start with@or//would be preserved (their cases don't change). -
pnpm config getandpnpm config listno longer load non camelCase options from the workspace manifest (pnpm-workspace.yaml). -
pnpm no longer loads non-auth and non-registry settings from rc files. Other settings must be defined in
pnpm-workspace.yaml. -
Replace workspace project specific
.npmrcwithpackageConfigsinpnpm-workspace.yaml.A workspace manifest with
packageConfigswould look something like this:# File: pnpm-workspace.yaml packages: - "packages/project-1" - "packages/project-2" packageConfigs: "project-1": saveExact: true "project-2": savePrefix: "~"
Or this:
# File: pnpm-workspace.yaml packages: - "packages/project-1" - "packages/project-2" packageConfigs: - match: ["project-1", "project-2"] modulesDir: "node_modules" saveExact: true
Other
-
This package is now pure ESM.
-
Node.js v18, 19, 20, and 21 support discontinued.
-
The standalone exe version of pnpm requires at least glibc 2.27.
-
strictDepBuildsistrueby default. -
blockExoticSubdepsistrueby default. -
Remove deprecated build dependency settings:
onlyBuiltDependencies,onlyBuiltDependenciesFile,neverBuiltDependencies, andignoredBuiltDependencies.Use the
allowBuildssetting instead. It is a map where keys are package name patterns and values are booleans:truemeans the package is allowed to run build scriptsfalsemeans the package is explicitly denied from running build scripts
Same as before, by default, none of the packages in the dependencies are allowed to run scripts. If a package has postinstall scripts and it isn't declared in
allowBuilds, an error is printed.Before:
onlyBuiltDependencies: - electron onlyBuiltDependenciesFile: "allowed-builds.json" neverBuiltDependencies: - core-js ignoredBuiltDependencies: - esbuild
After:
allowBuilds: electron: true core-js: false esbuild: false
-
Removed the deprecated
allowNonAppliedPatchescompletely in favor ofallowUnusedPatches.
RemoveignorePatchFailuresso all patch application failures should throw an error. -
Removed the
pnpm servercommand #10463. -
Removed support for the
useNodeVersionandexecutionEnv.nodeVersionfields.devEngines.runtimeandengines.runtimeshould be used instead #10373. -
Removed support for
hooks.fetchers. We now have a new API for custom fetchers and resolvers via thefetchersfield ofpnpmfile. -
The default value of the
typefield in thepackage.jsonfile of the project initialized bypnpm initcommand has been changed tomodule. -
Support lowercase options in
pnpm add:-d,-p,-o,-e#9197.When using
pnpm addcommand only:-pis now an alias for--save-prodinstead of--parseable-dis now an alias for--save-devinstead of--loglevel=info
-
pnpm publishnow works without thenpmCLI.The One-time Password feature now reads from
PNPM_CONFIG_OTPinstead ofNPM_CONFIG_OTP:export PNPM_CONFIG_OTP='<your OTP here>' pnpm publish --no-git-checks
Since the new
pnpm publishno longer callsnpm publish, some undocumented features may have been unknowingly dropped. If you rely on a feature that is now gone, please open an issue at https://github.com/pnpm/pnpm/issues. In the meantime, you can usepnpm pack && npm publish *.tgzas a workaround. -
Breaking changes to
pnpm link:pnpm link <pkg-name>no longer resolves packages from the global store. Only relative or absolute paths are accepted. For example, usepnpm link ./fooinstead ofpnpm link foo.pnpm link --globalis removed. Usepnpm add -g .to register a local package's bins globally.pnpm link(no arguments) is removed. Usepnpm link <dir>with an explicit path instead.
-
Do not exclude the root workspace project, when it is explicitly selected via a filter #10465.
Minor Changes
-
7fab2a2: Load environment variables whose names start with
pnpm_config_into config. These environment variables override settings frompnpm-workspace.yamlbut not the CLI arguments. -
cb367b9: Support reading
allowBuildsfrompnpm-workspace.yamlin the global package directory for global installs. -
075aa99: Add support for a global YAML config file named
config.yaml.Now configurations are divided into 2 categories:
- Registry and auth settings which can be stored in INI files such as global
rcand local.npmrc. - pnpm-specific settings which can only be loaded from YAML files such as global
config.yamland localpnpm-workspace.yaml.
- Registry and auth settings which can be stored in INI files such as global
-
e146e98: Added support for pnpmfiles written in ESM. They should have the
.mjsextension:.pnpmfile.mjs#9730. -
7d5ada0:
pnpm whynow shows a reverse dependency tree. The searched package appears at the root with its dependents as branches, walking back to workspace roots. This replaces the previous forward-tree output which was noisy and hard to read for deeply nested dependencies. -
5bf7768: A new
--yesflag can be passed to pnpm to automatically confirm prompts. This is useful when running pnpm in non-interactive script. -
2b14c74: When pnpm updates the
pnpm-workspace.yaml, comments, string formatting, and whitespace will be preserved. -
Added
pnpm sbomcommand for generating Software Bill of Materials in CycloneDX 1.7 and SPDX 2.3 JSON formats #9088. -
Allow loading certificates from
cert,ca, andkeyfor specific registry URLs. E.g.,//registry.example.com/:ca=-----BEGIN CERTIFICATE-----.... Previously this was only working viacertfile,cafile, andkeyfile#10230. -
Added
--allflag topnpm approve-buildsthat approves all pending builds without interactive prompts #10136. -
Added a new setting
blockExoticSubdepsthat prevents the resolution of exotic protocols in transitive dependencies #10265. -
Added
trustPolicyIgnoreAfter, which allows you to ignore trust policy checks for packages published more than a specified time ago #10352. -
Added a new flag called
--baretopnpm initfor creating a package.json with the bare minimum of required fields #10226. -
Added support for
allowBuilds, which is a new field that can be used instead ofonlyBuiltDependenciesandignoredBuiltDependencies#10311. -
Added support for object type in
configDependencieswhen the tarball URL returned from package metadata differs from the computed URL #10431. -
The
pnpm dlx/pnpxcommand now supports thecatalog:protocol. Example:pnpm dlx shx@catalog:. -
Add support for a hook called
beforePackingthat can be used to customize thepackage.jsoncontents at publish time #3816. -
On systems using the musl C library (e.g. Alpine Linux),
pnpm env usenow automatically downloads the musl variant of Node.js.pnpm env addandpnpm env removesubcommands have been removed.pnpm env listnow only lists remote Node.js versions. -
Added support for
--dry-runto thepackcommand #10301. -
Added mark-and-sweep garbage collection for global virtual store.
pnpm store prunenow removes unused packages from the global virtual store'slinks/directory. -
Semi-breaking. Changed the location of unscoped packages in the virtual global store. They will now be stored under a directory named
@to maintain a uniform 4-level directory depth. -
Support configuring
auditLevelin thepnpm-workspace.yamlfile #10540. -
Support bare
workspace:protocol without version specifier. It is now treated asworkspace:*and resolves to the concrete version during publish #10436. -
Added support for
pnpm config get globalconfigto retrieve the global config file path #9977. -
Added a new command
pnpm runtime set <runtime name> <runtime version spec> [-g]for installing runtimes. Deprecatedpnpm env usein favor of the new command. -
Added
pnpm cleancommand that safely removesnode_modulesdirectories from all workspace projects #10707. Use--lockfileto also removepnpm-lock.yamlfiles. -
Increase the network concurrency on machines with many CPU cores #10068.
-
Added support for
trustPolicyExclude#10164. -
Compute integrity hash for HTTP tarball dependencies when fetching, storing it in the lockfile to prevent servers from serving altered content on subsequent installs #10287.
-
Added support for automatic Node.js runtime installation for dependencies. pnpm will now install the Node.js version required by a dependency if that dependency declares a Node.js runtime in the
enginesfield #10141. -
Allow overriding the
enginesfield on publish by thepublishConfig.enginesfield. -
Changed default values:
optimisticRepeatInstallis nowtrueandverifyDepsBeforeRunis nowinstall. -
Added a new setting:
trustPolicy. When set tono-downgrade, pnpm will fail installation if a package's trust level has decreased compared to previous releases #8889. -
Support
.pnpmfile.mjsas the default pnpmfile. When.pnpmfile.mjsexists, it takes priority over.pnpmfile.cjsand only one is loaded. -
Added
-Fas a short alias for the--filteroption.
Patch Changes
-
Check if a package is installable for non npm-hosted packages (e.g., git or tarball dependencies) after the manifest has been fetched.
-
Explicitly tell
npmthe path to the globalrcconfig file. -
Fix YAML formatting preservation in
pnpm-workspace.yamlwhen running commands likepnpm update. Previously, quotes and other formatting were lost even when catalog values didn't change.Closes #10425
-
The parameter set by the
--allow-buildflag is written toallowBuilds. -
Fix a bug in which specifying
filteronpnpm-workspace.yamlwould cause pnpm to not detect any projects. -
Defer patch errors until all patches in a group are applied, so that one failed patch does not prevent other patches from being attempted.
Platinum Sponsors
|
|
Gold Sponsors
|
|
|
|
|
|
|
|
|
|
|