Published on

Auto-loading Node.js version with zsh and nvm

Authors

If you need to juggle between multiple Node.js projects that are based on several Node versions, there is a big chance that you are going to forget to set the appropriate Node version. You might figure this out when you face the related problem, you might cause a new problem because of this, or it might have no impact on your work, but it will definitely cause you a headache from time to time.

Setup

However, if you are using Zsh (Z shell) and nvm (Node Version Manager), there is a really convenient way to prevent this situation. You can set your zsh shell to automatically install/use the Node.js version defined in the .nvmrc file once you navigate to the project folder from your terminal. In order to do this, you need to add the following code snippet to the $HOME/.zshrc config file:

# place this after nvm initialization!
autoload -U add-zsh-hook
load-nvmrc() {
local nvmrc_path="$(nvm_find_nvmrc)"

if [ -n "$nvmrc_path" ]; then
local nvmrc_node_version=$(nvm version "$(cat "${nvmrc_path}")")

    if [ "$nvmrc_node_version" = "N/A" ]; then
      nvm install
    elif [ "$nvmrc_node_version" != "$(nvm version)" ]; then
      nvm use
    fi
elif [ -n "$(PWD=$OLDPWD nvm_find_nvmrc)" ] && [ "$(nvm version)" != "$(nvm version default)" ]; then
echo "Reverting to nvm default version"
nvm use default
fi
}
add-zsh-hook chpwd load-nvmrc
load-nvmrc

Next, you should restart your terminal, and navigate to a folder with .nvmrc file. If Node.js version from the file is not found, it will be automatically installed:

cd my_node_project
Found '/Users/aleksandar/code/my_node_project/.nvmrc' with version <18.10>
Downloading and installing node v18.10.0...
Downloading https://nodejs.org/dist/v18.10.0/node-v18.10.0-darwin-x64.tar.xz...
######################################################################## 100.0%
Computing checksum with shasum -a 256
Checksums matched!
Now using node v18.10.0 (npm v8.19.2)

If Node.js version from the file is installed, it will be automatically loaded (unless the version is the same as your default Node.js version, then it won't do anything):

cd my_node_project
Found '/Users/aleksandar/code/my_node_project/.nvmrc' with version <18.10>
Now using node v18.10.0 (npm v8.19.2)

When you navigate away from that folder, the default Node.js version will be loaded again:

cd ..
Reverting to nvm default version
Now using node v18.12.1 (npm v8.19.2)

That's it, you're ready to roll!

Powerlevel10k caveat

If you are using Powerlevel10k zsh theme (https://github.com/romkatv/powerlevel10k) it is likely that you will face the following warning if you start your shell in the folder with the .nvmrc that requires immediate Node.js version change (this is often the case with the shell within IDE):

[WARNING]: Console output during zsh initialization detected.

When using Powerlevel10k with instant prompt, console output during zsh
initialization may indicate issues.

...

A full message will explain what the problem is and what are the potential solutions. The most convenient way to fix it, is to set the following parameter inside the $HOME/.p10k.zsh config file:

typeset -g POWERLEVEL9K_INSTANT_PROMPT=quiet

This should fix the warning above without additional shell performance penalties.

Links

Zsh - https://www.zsh.org
NVM - https://github.com/nvm-sh/nvm
NVM Zsh integration - https://github.com/nvm-sh/nvm#zsh
Powerlevel10k theme - https://github.com/romkatv/powerlevel10k