Here we are with the first article I am releasing on the web. And today we will talk about Windows Subsystem for Linux, a feature released as part of the insider build 18917. We will attempt to install WSL2 and setup a node.js development environment.
Windows has a Subsystem for Linux since 2016. It enabled us to use Linux distributions on our Windows 10 systems. It now comes with Windows Subsystem for Linux 2, with a shift in their architecture, improving both the performance and the compatibility between windows and the subsystem. Further information can be found in Microsoft's developer blog
The development environment we will set up is composed of:
gitas our version control system.
oh-my-zshto replace bash (optional).
visual studio codeas our text editor.
docker-composeto containerise our projects .
But first we need to install WSL2.
The first thing we are going to do is enable the
Windows Insider Program
It can be enabled in the
Update and Security >
Windows Insider Program. Here are the steps
- Logging in to
Windows Insider accountor create one.
- At the time of writing, WSL2 is in the
Fastbuilds, so the
insider settingsshould be set to
- Then we head to
Update and Security>
Windows Updateand check for updates. We then install the latest build, then restart our machine.
- We should now have the latest updates, and with that comes WSL2. Next we will see how we can activate WSL2.
In order to install WSL2, WSL the first needs to be installed. Open a Powershell (as an Administrator) and type:
Enable-WindowsOptionalFeature -Online -FeatureName Microsoft-Windows-Subsystem-Linux
When prompted to restart our machine, we just answer with [Y]es.
After the computer restarted, we head to
the Microsoft Store and search the term
After clicking on
Run Linux on Windows we choose to get
ubuntu as our linux distribution. Once ubuntu is installed, we launch it. After a first initialization we are prompted for the
Unix username and the
Unix password. We then update ubuntu's package manager (this might take some time and you will be prompted for information twice, normally).
sudo apt update && sudo apt upgrade
We are now one step away from enabling WSL2.
Let's open a powershell again, and enable another optional feature
Enable-WindowsOptionalFeature -Online -FeatureName VirtualMachinePlatform
Again, we are prompted to restart the system. [Y]es again.
After the machine rebooted, we open a powershell as Administrator for the last time, to make sure that we make use of WSL2!
wsl --set-version ubuntu 2
This process might take a few minutes, says Powershell.
Note: I have ran this installation on two different machines during the same week, and once I had to type
ubuntu and the other one
ubuntu-18.04. There are several ubuntus in the store, I might have picked different ones.
Next we set WSL2 as our default choice for WSL
wsl --set-default-version 2
And this is it, we have now successfully installed WSL2. Time to set up our development environment.
The release announcement blogpost asks us "To make sure to put the files that we will be accessing frequently inside of our Linux root file system to enjoy the file performances benefits".
We can now access files from the windows
explorer. It is as easy as typing
\\wsl$\Ubuntu\home in the explorer navigation bar. We are now in our home folder.
The home folder can be pinned to
Most of the installation will happen in the ubuntu console. As good practice, before installing anything on linux run
sudo apt update && sudo apt upgrade
We can now start setting up our development environment.
In this section we are replacing the default
bash terminal with
oh-my-zsh. You can skip to the development tools section if you plan to keep use
zsh we open a
terminal (the ubuntu app) and run
sudo apt install zsh
zsh can now be launched just by typing
zsh in the terminal. A
.zshrc file needs to be created, and we are prompted for a choice. He we pick (0) as the
.zshrc file will be replaced when we install
We don't want to type zsh each and everu time we start the ubuntu app, so the next thing we want to is change the default shell to use
zsh. To do so, we'll use the chsh command as per this example. Simply run
chsh -s $(which zsh)
After this is done, we will change the theme of our
zsh and to do so, we will leverage the power of oh-my-zsh. A simple command will install it:
sh -c "$(curl -fsSL https://raw.github.com/robbyrussell/oh-my-zsh/master/tools/install.sh)"
zsh also comes with a set of plugins that could be useful to increase your development speed. Completion plugins are also available for
npm. Please refer to the plugin page to find anything that suits you. I enjoy working with the git plugin. Talking about git, it is the next tool we are going to install.
Note: When running
sudo apt upgrade or
sudo apt-get update, the following error code could be encountered:
E: Release file for https://download.docker.com/linux/ubuntu/dists/bionic/InRelease is not valid yet (invalid for another 15h 3min 13s). Updates for this repository will not be applied.
This is dues to a known issue in WSL. A temporary fix is to call
sudo hwclock -s
To install git, in a wsl terminal, we run
sudo apt update && sudo apt upgrade sudo apt install git
The next step is to deal with cross plateform problems, where sometimes git recognise changes in files, when there are none. This is due to windows using CRLF and linux LF to signify an end of line. To fix that, the following line can be run:
git config --global core.autocrlf input
First we create a SSH key on your new linux subsystem. Instructions can be found (here)[https://help.github.com/en/enterprise/2.15/user/articles/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent]
To generate a private and a public key for git, we run:
ssh-keygen -t rsa -b 4096 -C "email@example.com" #replace with your email
This will generate a new ssh key. When prompted to choose a file where the key will be saved, we can use either the default location or input your preferred location for the file. For this example we will consider that we used the default location
Start the ssh-agent:
eval "$(ssh-agent -s)"
We then add the ssh private key to the ssh-agent
After that we can add the key to a github or a (gitlab)[https://docs.gitlab.com/ee/ssh/#adding-an-ssh-key-to-your-gitlab-account] account.
Note: I currently need to run
eval "$(ssh-agent -s)" and
ssh-add ~/.ssh/id_rsa every time I restart my laptop.
Now that we installed git, we are sure that the code we write does not get lost. Now to write our code, let's install Visual Studio Code.
We browse (the Visual Studio Code website)[https://code.visualstudio.com/], download visual studio code for Windows, and install it.
During the installation process, we make sure to check the box to add Visual Studio Code to the PATH, it is recommended for an extension we'll install later.
Code comes with heaps of extensions, but the one we are interested in is VS Code Remote Development. It bundles a few extensions that are useful for remote development, including
Remote - WSL which will do some magic for us.
In VS Code, in the extension tab we look for
Remote Development and install it.
zsh terminal we browse to our home folder and create a
cd ~ && mkdir dev && cd dev
Now we just start code from a ubuntu terminal
It should open a new VS Code window, and install a VS Code server on our WSL. Once this is done, we can now create files in our editor and they will be created in the linux file system.
This article is written using exactly this setup \o/
This last part is for those among us who installed
zsh. Once VS Code is connected to WSL, it is possible to modify the default shell to be
zsh. This will take effect after relaunching the terminal.
Now that we have installed Visual Studio Code, let's install node.js
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.34.0/install.sh | zsh
Note: If you did not install
zsh, the previous command should be run with
bash instead of
If the installation is successful the following command should return
nvm. If it does not, a simple restart of the terminal should fix it.
command -v nvm
Let's have a look at the commands available in nvm
The command we are interested in in the
nvm install command. Let's install node's latest LTS (Long-term support) version:
nvm install --lts
That's it, we installed
npm. But let's check that I am not lying by checking the versions.
node --version && npm --version
Our journey to set up our development environment is almost complete. The last thing we need to do is to take one last (whale-)boat trip. Here comes Docker.
First we need to update
sudo apt-get update
After what we install a few required dependencies
sudo apt-get install \ apt-transport-https \ ca-certificates \ curl \ gnupg-agent \ software-properties-common
We then need to add Docker's official GPG key
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -
We need to make sure that we have the key with fingerprint
9DC8 5822 9FC7 DD38 854A E2D8 8D81 803C 0EBF CD88
sudo apt-key fingerprint 0EBFCD88
Docker needs to be added to the list of repositories
sudo add-apt-repository \ "deb [arch=amd64] https://download.docker.com/linux/ubuntu \ $(lsb_release -cs) \ stable"
Note: My processor is an amd64 process, if you have a different type of processor, replace
[arch=amd64] accordingly (other possible values:
We are now ready to install (Docker Community Edition)[https://docs.docker.com/install/]
sudo apt-get update sudo apt-get install docker-ce docker-ce-cli containerd.io
Now let's make sure that docker is installed.
sudo docker run hello-world
This should download a test image and run it in a container. If the docker service is not started, it needs a (manual kickstart)[https://docs.docker.com/config/daemon/systemd/] and in our case, with ubuntu we will use:
sudo service docker start sudo docker run hello-world
First download the stable release of Docker Compose (
1.24.1 at time of writing)
sudo curl -L "https://github.com/docker/compose/releases/download/1.24.1/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
Once the binary is downloaded, it needs to have execution permissions:
sudo chmod +x /usr/local/bin/docker-compose
Finally we check the installation by running
which should return a docker-compose version and a build id (
docker-compose version 1.24.1, build xxxxxxxx at time of writing)
We have now installed the tools for us to start developing node apps. WSL2 is currently only in beta mode, so we will most likely encounter issues. Don't hesitate to report any issue encountered (double checking first if the issue has been encountered yet).
I hope that you enjoyed this article, the first one I ever wrote. Feel free to leave some feedback.
That's all folks!