Shav Vimalendiran
BlogWiki ↗
  • The Last MoatsJul 7, 2026
  • The Tech FrontierJul 6, 2026
  • The Trust BarrierJul 4, 2026
  • I Open-Sourced My Coding Agents' MemoryJun 24, 2026
  • How I Gave My Coding Agents Persistent MemoryMar 12, 2026
  • Multi‑Agent Web Exploration with Shared Graph MemoryFeb 19, 2026
  • Our Lessons from Building Production Voice AIJan 11, 2026
  • Reinforcement Learning, Memory and LawDec 10, 2025
  • Automating Secret ManagementOct 23, 2025
  • The Knowledge LayerOct 5, 2025
  • OTel Sidecars on FargateSep 11, 2025
  • Git Disasters and Process DebtSep 7, 2025
  • Is Code Rotting Due To AI?Sep 3, 2025
  • The Integration IllusionAug 30, 2025
  • When MCP FailsAug 26, 2025
  • Context EngineeringAug 22, 2025
  • Stop Email Spoofing with DMARCAug 5, 2025
  • SOTA Embedding Retrieval: Gemini + pgvector for Production ChatJul 21, 2025
  • Agentic Design PatternsJun 21, 2025
  • Building AI Agents for Automated PodcastsJan 1, 2025
  • Rediscovering CursorDec 2, 2024
  • GraphRAG > Traditional Vector RAGAug 8, 2024
  • Cultural Bias in LLMsJul 20, 2024
  • Mapping out the AI Landscape with Topic ModellingJul 7, 2024
  • Sustainable Cloud Computing: Carbon-Aware AIJun 27, 2024
  • Defensive Technology for the Next Decade of AIJun 24, 2024
  • Situational Awareness: The Decade AheadJun 13, 2024
  • Mechanistic Interpretability: A SurveyJun 7, 2024
  • Why I Left UbuntuMay 24, 2024
  • Multi-Agent CollaborationApr 16, 2024
  • Building Better Retrieval SystemsMar 28, 2024
  • Building an Automated Newsletter-to-Summary Pipeline with Zapier AI Actions vs AWS SES & LambdaFeb 3, 2024
  • Local AI Image GenerationDec 15, 2023
  • Deploying a Distributed Ray Python Server with Kubernetes, EKS & KubeRayNov 15, 2023
  • ›Making the Switch to Linux for DevelopmentOct 24, 2023
  • Scaling Options Pricing with RayOct 1, 2023
  • The Async Worker PoolSep 23, 2023
  • Browser Fingerprinting: Introducing My First NPM PackageSep 8, 2023
  • Reading Data from @socket.io/redis-emitter without Using a Socket.io ClientJul 6, 2023
  • Socket.io Middleware for Redux Store IntegrationJul 1, 2023
  • Sharing TypeScript Code Between Microservices: A Guide Using Git SubmodulesApr 21, 2023
  • Efficient Dataset Storage: Beyond CSVsFeb 3, 2023
  • Why I switched from Plain React to Next.js 13Nov 8, 2022
  • Deploy & Scale Socket.io Containers in ECS with ElasticacheNov 3, 2022
  • Implementing TOTP Authentication in Python using PyOTPSep 13, 2022
  • Simplifying Lambda Layer ARNs and Creating Custom Layers in AWSSep 9, 2022
  • TimeScaleDB Deployment: Docker Containers and EC2 SetupJun 23, 2022
  • How to SSH into an EC2 Instance Using PuTTYDec 16, 2021
Loading post…

In This Post

Why Linux?Work EnvironmentSetting Up a New Linux System for DevelopmentEssential ToolsUI/User ExperienceUseful Shortcuts and AliasesUnderstanding the PATH VariableSetting PATH in Windows vs LinuxFinal Thoughts
Published: October 24, 2023
PreviousNext

Making the Switch to Linux for Development

Linux continues to be a popular choice among developers, ranking as the 2nd most commonly used operating system for coding in the Stack Overflow Developer Survey of 2022. In this post, I'll share why I switched from Windows to Linux for development and how I set up my system for various tasks, including web development and machine learning.

Ubuntu Desktop

Why Linux?

So why did I make the switch from Windows to Linux? Well, apart from many developers praising Linux's superiority for development, I was also curious about several compelling features:

  1. Built-in Package Managers - Quickly install what you need without searching for installers
  2. Ease of Access & Installation - Documentation and guides are easier to follow
  3. Web Development - I'll be coding in the same OS as my server environment, making deployment errors more familiar
  4. Native Docker Support - Significantly faster performance
  5. Better Command Line Utilities - No need for additional shells like Git Bash
  6. SSH Support - Access servers without additional installations
  7. Free - No licensing costs
  8. Customization - Choose from different distributions and customize your desktop. I tried three distros (PopOS, Fedora, and Ubuntu), and the flexibility of tailoring your OS to your specific needs is refreshing
  9. Flexibility - Adapt the OS for your specific needs, from docks to icons to themes

Work Environment

I was concerned about breaking things during the transition, so I documented the most important aspects of my Linux setup for anyone interested in using Linux as their primary development OS. If you've just installed PopOS, Fedora, or Ubuntu, you're probably facing a lengthy post-install process to configure your system for development. I went through this setup three times while testing different distros, so I documented everything I needed to remember.

I'm currently running Ubuntu 23.10 Mantic Minotaur with GNOME 45 as the desktop environment, and I'm very satisfied with this combination. I find Ubuntu particularly suitable for development machines, and it looks great too. I use it for various tasks including TypeScript, Python, AI development, running Docker containers, cloud deployments, and blogging.

Setting Up a New Linux System for Development

Essential Tools

Development tool choices are largely subjective and don't matter much as long as you're comfortable with your selections. Below are my preferred tools for key development categories:

  1. System Updates

    • Run sudo apt-get update and restart your system
  2. NVIDIA Drivers

    • Install via GNOME Software for GPU acceleration
  3. IDE & Code Editors

    • I use VS Code for web development (JavaScript/TypeScript) and PyCharm for AI, data science, and Python development
    • VS Code configuration: Set window.titleBarStyle to custom to prevent the default Linux title bar
    • Also set editor.selectionClipboard to false to disable middle-click paste behavior
  4. Python Versions

    • Since Ubuntu 23.10 isn't an LTS version, the deadsnakes PPA isn't available
    • Instead, compile and install Python from source
    • Important: Use sudo make altinstall instead of sudo make install to avoid overwriting the default Python version
    • Add the Python interpreters to PyCharm after installation
Python Interpreter Versions
  1. SSH Key for GitHub

    • Install Git: sudo apt-get install git
    • Check version: git --version
    • Configure Git: git config --global user.name "your-username" && git config --global user.email "your-email@example.com"
    • Generate SSH key: ssh-keygen
    • View the generated key: cat ~/.ssh/id_rsa.pub
    • Add to your GitHub SSH keys settings by clicking "New SSH Key"
  2. Node.js & NPM

    • Install with: sudo apt install nodejs npm
    • This installs the V8 JavaScript engine, Node.js runtime, npm package manager, and dependencies
    • Repository versions are typically current Node.js LTS releases
  3. NVM (Node Version Manager)

    • NVM is a bash script for managing multiple Node.js versions
    • Visit the NVM GitHub page for latest installation instructions
    • Install latest Node: nvm install node
    • Install specific version: nvm install 14.7.0
    • The first version installed becomes default for new shells
    • List available versions: nvm ls-remote
    • Switch versions: nvm use node
  4. Docker or Podman

    • Consider using Podman as a Docker alternative with alias docker="podman"
    • For Docker, install Docker Desktop for Linux
    • Before signing into Docker Hub, initialize pass
  5. Go Programming Language

    • Download tarball from the Go website
    • Extract: sudo tar -C /usr/bin -xvf go1.21.4.linux-amd64.tar.gz
    • Set environment path by editing .profile: sudo nano ~/.profile
    • Add: export PATH=$PATH:/usr/bin/go/bin
    • Refresh profile: source ~/.profile
  6. D2 Diagram Tool

    • Install with: go install oss.terrastruct.com/d2@latest
    • Ensure it's added to your system PATH

UI/User Experience

After installing the essential development tools, I customized the user interface and experience:

  1. GNOME Extensions

    • Use GNOME Tweaks for customization
    • Many features are hidden by default (maximize/minimize buttons, appearance tweaks, icons)
  2. Display Settings

    • Adjust fonts and DPI as needed for your monitor setup
  3. VPN Configuration

    • I use Surfshark VPN with the following setup:
    • Change DNS servers to Google DNS
    • Download Surfshark OpenVPN configurations
    • Configure OpenVPN through the Settings UI
    • Use nm-connection-manager to automatically start VPN on WiFi connection
  4. Icons & Themes

    • I use the WhiteSur Icon Pack and McMojave cursors
    • Note: The App Center in Ubuntu 23.10 installs snaps, and snap .desktop files are located at:
/var/lib/snapd/desktop/applications/snap-name_application-name.desktop
  • Important: This file gets overwritten on snap updates, so don't edit it directly
  • Instead, copy the .desktop file to: ~/.local/share/applications/snap-name_application-name.desktop
  • Keep the exact naming schema (snap-name_application-name) when copying
  • Edit the copied file with new icon paths
  • WhiteSur icons are located at: /home/username/.local/share/icons/WhiteSur-dark/apps/scalable
  • Search for specific app icons: ls | grep chrome
  1. Keyboard Shortcuts

    • Set terminal shortcut: flatpak run com.raggesilver.BlackBox on Shift + Ctrl + '
  2. Essential Applications

    • Browser: Brave Browser
    • Communication: Discord, WhatsApp
    • Office Suite: LibreOffice (handles Microsoft Office and Keynote formats), plus Google Docs online
    • Terminal: BlackBox Terminal
    • Media: Spotify
  3. Quality of Life Improvements

    • Add bookmarks with Ctrl + D in the file manager

Useful Shortcuts and Aliases

In my .bashrc:

alias docker="podman"
alias grm="git rebase master"
alias grc="git rebase --continue"
alias gra="git rebase --abort"
alias grs="git rebase --skip"
alias gpo="git push origin"
alias gs="git stash"
alias gsa="git stash apply"
alias dps="docker ps"
alias dk="docker kill"
alias dpsa="docker ps -a"
alias dipa="dipa"
alias drm="docker rm"
alias cl="clear"
alias fopen="xdg-open ."
alias gacp='f(){ git add . && git commit -m "$1" && git push; }; f'
alias charm="sh /opt/pycharm-2023.2.2/bin/pycharm.sh"
 
function mkcd {
  command mkdir $1 && cd $1
}
 
function dipa(){
  docker rm -v $(docker ps -a -q -f status=exited);
  docker volume rm $(docker volume ls -qf dangling=true);
  docker rmi $(docker images -qf dangling=true);
}

Understanding the PATH Variable

The PATH environment variable is crucial for command-line work. It's a list of directories that tells your operating system where to look for executable programs, allowing you to type script instead of the full path like /home/me/bin/script.

Setting PATH in Windows vs Linux

Windows Process:

  1. System Settings - Search for "System (Control Panel)"
  2. Advanced System Settings - Click "Advanced system settings"
  3. Environment Variables - Select "Environment Variables"
  4. Edit PATH - Locate PATH under "System Variables" and edit
  5. Add Directory - Prepend your directory followed by semicolon (;)
  6. Apply Changes - Click "OK" and restart terminal

Linux Process:

  1. Edit .bashrc - Open ~/.bashrc in a text editor
  2. Add Export - Add export PATH="your-dir:$PATH" to the end
  3. Apply Changes - Save and restart terminal or run source ~/.bashrc

Final Thoughts

Switching to Linux should make my development workflow more efficient, though I'm still new to the platform and want to give it a proper evaluation before drawing concrete conclusions. While there were setup challenges with GPU drivers and system configuration, I'm excited about the potential benefits.

The flexibility, customization options, and developer-focused tools make Linux an attractive choice for development work. The ability to work in the same environment as production servers, combined with superior command-line utilities and package management, creates a more streamlined development experience.

If you're considering making the switch, I hope this guide helps you set up your Linux system for development success. The initial investment in configuration pays dividends in productivity and system understanding.


Loading comments...
PreviousDeploying a Distributed Ray Python Server with Kubernetes, EKS & KubeRayNextScaling Options Pricing with Ray

Be the first to share your thoughts!