Personal note on setting up WSL2 as a development server
Some reasons why you might want to do this:
-
You have a beefy PC, but less-powerful laptop
Say you already have a powerful PC, you can leverage your PC resources while working from your, say, Chromebook.
-
You like working from a Mac, but have some relatively heavy Docker workloads
File system performance on Docker for Mac has always been behind Docker for Linux. There is a long-running issue here that eventually became a roadmap item here.
For me, I have a pretty good gaming PC (i5-12400, 32GB RAM, EVO 970 Plus NVMe SSD) and a pretty good MacBook as well. Though I have heavy Docker use in my daily works and running Docker on my MacBook is just not pleasant. RAM usages are high and anytime something that involves I/O read/write happens in the containers (think hot reloads, builds/compilations), things will slow down. The fans in my MacBook would constantly be spinning.
Offloading Docker to my Windows PC makes a lot of sense for my case, as I am not using my PC anyway during work hours. My MacBook fans now no longer spins in my daily work and everything simply runs much more smoothly now. Sure, I could've just worked directly on the PC, but I prefer MacBook's hardware and the OS and softwares available on the platform helps my productivity.
Even if you don't need Docker, this setup might still benefit you if you already have a beefy PC. You'd be able to leverage your powerful PC while still be able to work from anywhere using your less-powerful laptop as long as both devices are connected to the internet.
Before doing anything, first install WSL2 on Windows 10/11 machine
-
Shut down the current running WSL
wsl --shutdown
-
Export the WSL mount image
wsl --export Ubuntu E:\WSL\Ubuntu\ubuntu.tar # Replace the directory as needed. This will be the directory where the WSL distro disk will be mounted
-
Unregister the previously installed distro
wsl --unregister Ubuntu
-
Import the distro from the
.tar
file we had before. This willregister
the distro againwsl --import Ubuntu E:\WSL\Ubuntu\Ubuntu E:\WSL\Ubuntu\ubuntu.tar --version 2
Source: https://medium.com/@gilad215/ssh-into-a-wsl2-host-remotely-and-reliabley-578a12c91a2
-
Log into the WSL distro
wsl
-
Install
openssh-server
in the WSL distrosudo apt install openssh-server
-
Update SSH configuration in the distro
# edit /etc/ssh/sshd_config with the following three changes Port 2222 # port 2222 is used here just so it's different than the default port 22, but still easy to remember ListenAddress 0.0.0.0 PasswordAuthentication yes
-
Add your user to
sudo
group and run thessh
service for the first timesudo adduser <username> sudo sudo service ssh start
-
Next, we want to allow starting
ssh
service next time without passwordnano /etc/sudoers.d/<username> # Put the following line in the file <username> ALL=(ALL) NOPASSWD:ALL
-
Try stopping and then starting the SSH service, it should work without asking for password
# stop the service service ssh stop # start the service service ssh start
-
On the Windows machine, run the
./ssh-setup.ps1
script. This will allow the windows machine to forward incoming SSH connection to the WSL distro. -
Verify that SSH is working by running the following commands:
- From windows machine, try SSH-ing into WSL
ssh wsluser@windows.ip -p 2222
- From another device in the same network, try SSH-ing into WSL
ssh wsluser@windows.ip -p 2222
Note: Replace
wsluser
with the username you created for the WSL distro. Replacewindows.ip
with the IP address assigned to your Windows PC in your local network. - From windows machine, try SSH-ing into WSL
-
The
./setup-ssh.ps1
script would need to be re-run whenever the WSL is restarted, because it would be assigned a different IP. We can automate running this script whenever the windows machine boot by doing the following:- Press Win+R on Windows and enter shell:startup. This will open the Startup folder. Right click and create a new Shortcut.
- Target: C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe -Command “C:\scripts\wsl-ports.ps1”
- Try running the shortcut to make sure it works. Make sure to adjust the path to the script accordingly.
Note that this only runs the script whenever Windows restarts, not when the WSL restarts. If you restart WSL manually, remember to re-run the script as well.
- Install Docker on Windows with WSL2 backend
- Once installed, go into
Settings -> Resources -> WSL Integration
and enable integration with the previously installed Ubuntu distro. This makes it sodocker
is available in the distro, even though we never installed docker into the distro ourselves.
-
Make sure docker WSL instances are registered already.
wsl -l -v # There should be `docker-desktop` and `docker-desktop-data` WSL instances in the output # We only care about moving `docker-desktop-data`
-
Quit Docker (right click Docker icon on tray, quit Docker)
-
Shutdown the WSL instances
wsl --shutdown docker-desktop wsl --shutdown docker-desktop-data
-
Export
docker-desktop-data
. This is where containers and images data will reside in.wsl --export docker-desktop-data E:\Docker\wsl\data\docker-desktop-data.tar # Replace the directory as needed. This will be the directory where Docker's images and data are stored
-
Unregister
docker-desktop-data
wsl --unregister docker-desktop-data
-
Import
wsl --import docker-desktop-data E:\Docker\wsl\data E:\Docker\wsl\data\docker-desktop-data.tar --version 2
-
Start Docker desktop again, everything should work.
By default, WSL will allocate up to 50% of your physical RAM as memory and 25% of it as swap. If you are running a lot of docker containers, this can fill up quickly. Also, WSL will keep the memory for itself eventhough the instances might not be using all that memory.
To limit the amount of memory used by WSL instances, we can configure it by creating a .wslconfig
file in the Windows machine home folder. This is usually C:\Users\UserName\.wslconfig
.
See the sample .wslconfig
file
When using VSCode with WSL integration, the user used is the default-set WSL user. If you are working with Docker and are running some scripts in the container that create some files/directories, those files/directories might be created with the root
user.
When trying to delete the file from VSCode, you might get permission denied
error because of this. A solution would be to go into the container and update the owner of those files/directories.
sudo chown -R username path
Use Tailscale and set up the 2 devices in the same network. With this, you can simply update the IP address for SSH temporarily and still access your dev server from anywhere, as long as both devices are connected to the internet.
ssh wsluser@windows.ip.in.tailscale.network -p 2222