Tested with zsh, bash and fish shells on macOS. May work with others as well. WSL may work but is not yet tested.
Project inspired by nvm, although implementation details are different. For pvm the focus is primarily performance and an easy-to-script integration in project repositories. Because pvm adds entries to the path, there is no startup cost for opening a new terminal, and package.json scripts or scripts running in any execution context can leverage pnpm and pvm commands without worrying about undefined aliases.
Additionally, each distinct function of pvm is implemented as a separate script. This allows quicker execution for individual commands, with the downside that some code may need to be repeated between scripts. This tradeoff is acceptable because the main focus is on runtime performance. If you are used to using sluggish version managers, you will be pleasantly surprised by the speed of pvm.
First, remove any currently-installed pnpm versions. You can detect versions with which pnpm and then rm the file. You may need to do this more than once.
Next, install pvm:
curl -H 'Cache-Control: no-cache' -o- https://raw.githubusercontent.com/pkg-mgr/pvm/main/setup.sh | bashAlternately, to auto-remove any existing pnpm installation before installing:
curl -H 'Cache-Control: no-cache' -o- https://raw.githubusercontent.com/pkg-mgr/pvm/main/setup.sh | NUKE_PNPM=1 bashrm -rf ~/.pvm /usr/local/bin/pnpm /usr/local/bin/pnpx /usr/local/bin/pvm
# or simply:
pvm nukeNote: this will not remove globally-installed packages. To do that, rm -rf ~/.pnpm-store
Once pvm is installed, you need to install at least one version of pnpm (ex: pvm install 8.9.2). You are now ready to use pnpm. You can then install additional versions the same way and switch between them with pvm use <version>.
You can also specify a default version (ex: pvm default 8.9.5) for any new shell session where you have not run the pvm use <version> command yet.
In addition, if you create a .pvmrc file with a version in the same folder as a package.json file, any pnpm command run in that folder will automatically use the specified version.
Example:
echo "8.9.2" > .pvmrc
pnpm --version(The .pvmrc must be in the same directory as your project's package.json file.)
Install a package globally, as normal. Ex: pnpm add -g cowsay
You can then run the global package with pnpx. Ex: pnpx cowsay HI or pnpm exec cowsay HI.
- Individual command scripts are installed to
~/.pvm/cmdsfolder - pnpm binaries are installed to
~/.pvm/versionfolders (ex:~/.pvm/8.9.2). Global installs are added to this folder as well. - The
run.shscript is copied to/usr/local/bin/pnpm. This allows us to intercept and run pnpm commands with the correct version of pnpm. - The
cmd.shscript is copied to/usr/local/bin/pvmand/usr/local/bin/pvm. This allows us to run the pvm commands which collectively allow pnpm version management.
Note: after running setup, you can run pvm help to see the list of available commands.
pvm defaultaka~/.pvm/cmds/default.sh- lists the default version. (Initially set to the latest at time of original setup.)pvm default <version>aka~/.pvm/cmds/default.sh- sets the default pnpm versionpvm helpaka~/.pvm/cmds/help.sh- lists all available commandspvm installaka~/.pvm/cmds/install.sh- installs the latest version of pnpmpvm install <version>aka~/.pvm/cmds/install.sh- installs specified pnpm version.pvm listaka~/.pvm/cmds/list.sh- lists all currently installed versions of pnpmpvm list --remoteaka~/.pvm/cmds/list.sh- lists all versions available to installpvm nukeaka~/.pvm/cmds/nuke.sh- removes pvm and all pnpm binaries completelypvm runaka~/.pvm/cmds/run.sh- runs a pnpm command using automatic pnpm version detection. (The pnpm command will also do this directly.)pvm uninstall <version>aka~/.pvm/cmds/uninstall.sh- uninstalls specified pnpm versionpvm unuseaka~/.pvm/cmds/unuse.sh- un-sets the pnpm version for the current terminal sessionpvm updateaka~/.pvm/cmds/- updates all pvm scriptspvm useaka~/.pvm/cmds/use.sh- sets the pnpm version for the current terminal session
You can debug (produce additional command output) by setting the PVM_DEBUG environment variable to true before running any command. Ex: PVM_DEBUG=true pvm default
- VS Code
- Code Spell Checker
- shellcheck via the VS Code Extension for script linting
- shell-format for auto-formatting
Make code changes, then run ./setup.sh which will perform setup using your local code. You can now test your local changes with using the pvm command.
Before preparing a PR, run ./extract-versions.js to update the versions.txt versions list and default-version.txt default default version.
Once you've tested the commands locally, raise a PR. The changes are live once they are merged to master.