Windows + WSL Development Environment (Setup Guide)

This document describes exactly how to reproduce my current personal development environment:

This is not a generic guide. Follow it top-to-bottom for the same result.


0. Preconditions

  • Windows 10 22H2+ or Windows 11
  • Virtualization enabled in BIOS
  • A GitHub account
  • ChatGPT Plus account (for reasoning; API optional)

1. Install WSL2 + Ubuntu

Open PowerShell as Administrator:

wsl --install

Reboot when prompted.

After reboot, open Windows Terminal and select Ubuntu.

Create:

  • Linux username
  • Linux password

Verify WSL version

wsl -l -v

Expected:

Ubuntu    Running    2

2. Update Linux Base System

Inside Ubuntu:

sudo apt update && sudo apt upgrade -y

Install baseline packages:

sudo apt install -y \
  build-essential \
  curl wget unzip zip \
  ca-certificates gnupg lsb-release

3. Shell: Bash + Starship

Ensure Bash is default shell

echo $SHELL

If not /bin/bash:

chsh -s /bin/bash
exec bash

Install Starship

curl -sS https://starship.rs/install.sh | sh

Enable it:

echo 'eval "$(starship init bash)"' >> ~/.bashrc
exec bash

Starship configuration

Create config:

mkdir -p ~/.config
nano ~/.config/starship.toml

Paste:

format = "$username$directory$git_branch$git_status$java$cmd_duration $character"
add_newline = false

[username]
show_always = false
style_user = "dimmed white"
style_root = "bold red"
format = "[$user]($style) "

[directory]
truncate_to_repo = true
style = "bold cyan"
format = "[$path]($style)"

[git_branch]
symbol = "  "
style = "bold purple"
format = "[$symbol$branch]($style)"

[git_status]
style = "yellow"
format = "[$all_status]($style)"

[java]
symbol = " ☕ "
style = "red"
format = "[$symbol$version]($style)"

[cmd_duration]
min_time = 500
style = "dimmed white"
format = " [⏱ $duration]($style)"

[character]
success_symbol = "\\$"
error_symbol = "\\$!"

[hostname]
disabled = true
[time]
disabled = true
[battery]
disabled = true
[memory_usage]
disabled = true

Reload:

exec bash

Verify:

~ $

4. VS Code + WSL

Install VS Code (Windows)

Download: https://code.visualstudio.com

Install with defaults.

Install extensions

In VS Code → Extensions (Windows side):

  • Remote - WSL

Inside the WSL environment (server-side extensions):

  • Python
  • Pylance
  • Python Environments
  • Debugpy
  • Extension Pack for Java
  • Maven for Java
  • Gradle for Java
  • Java Debugger
  • Java Test Runner
  • Java Dependency Viewer
  • ShellCheck
  • Continue

Launch VS Code from WSL

cd ~
code .

Verify bottom-left shows:

WSL: Ubuntu

5. Java Toolchain (SDKMAN)

Install SDKMAN

curl -s "https://get.sdkman.io" | bash
source "$HOME/.sdkman/bin/sdkman-init.sh"

Verify:

sdk version

Install JDKs

sdk install java 21-tem
sdk install java 17-tem
sdk default java 21-tem

Verify:

java -version

Maven & Gradle

sdk install maven
sdk install gradle

6. Python (pyenv + venv-first)

Install dependencies

sudo apt install -y \
  python3 python3-venv python3-pip \
  pipx \
  libssl-dev zlib1g-dev libbz2-dev \
  libreadline-dev libsqlite3-dev \
  libffi-dev xz-utils tk-dev

Install pyenv

curl https://pyenv.run | bash

Add to ~/.bashrc:

export PYENV_ROOT="$HOME/.pyenv"
export PATH="$PYENV_ROOT/bin:$PATH"
eval "$(pyenv init -)"

Reload:

exec bash

Install Python:

pyenv install 3.12.8
pyenv global 3.12.8
python --version

Project workflow

python -m venv .venv
source .venv/bin/activate
pip install -U pip

7. Node.js (nvm)

Install nvm

curl -fsSL https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.1/install.sh | bash
exec bash

Install Node

nvm install --lts
nvm alias default lts/*
node -v

8. Rust

curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
exec bash
rustup component add rustfmt clippy

9. Common CLI Tools

sudo apt install -y \
  jq ripgrep fd-find bat tree htop \
  lsof dnsutils file less httpie shellcheck

Aliases:

echo "alias fd=fdfind" >> ~/.bashrc
echo "alias bat=batcat" >> ~/.bashrc
exec bash

10. Personal ~/bin (symlinked)

mkdir -p ~/projects/oss/dotfiles/bin
ln -s ~/projects/oss/dotfiles/bin ~/bin

Add to PATH (if not already):

echo 'export PATH="$HOME/bin:$PATH"' >> ~/.bashrc
exec bash

11. Git (SSH + GitHub privacy)

SSH preference

git config --global url."git@github.com:".insteadOf "https://github.com/"

Conditional identity

Create ~/.gitconfig-github:

[user]
  name = <Name>
  email = <Github Public Email>

Add to ~/.gitconfig:

[includeIf "hasconfig:remote.*.url:https://github.com/**"]
  path = ~/.gitconfig-github

Verify:

git config --show-origin --get user.email

12. Final Verification Checklist

which java
which python
which node
which cargo
which git

All should resolve inside $HOME.

Prompt should show $, not >.


End State

You now have:

  • Windows as host
  • Linux as dev OS
  • Clean multi-language toolchains
  • Deterministic shell
  • SSH-first Git
  • Minimal, professional CLI environment

This setup is intentionally boring — and built to last.