Using Virtual Environments to Keep Your Python Projects Clean
"It works on my machine." Three months ago, I said these exact words. My Flask app ran fine locally but crashed on the server. The culprit? I had Flask 2.0 installed globally. The server had Flask 1.1. My code used a 2.0 feature. Hours of debugging for what should have been a non-issue.
That was the day I finally started using virtual environments properly.
The Problem
Python installs packages globally by default. When you run pip install requests, it goes into your system Python. Every project on your machine shares those packages.
This creates conflicts:
- Project A needs Django 3.0
- Project B needs Django 4.0
- You can't have both installed globally
Upgrade Django for Project B, and Project A breaks.
The Solution: Isolated Environments
A virtual environment is a folder containing a copy of Python and its own site-packages directory. Packages installed inside stay inside. Each project gets its own sandbox.
Think of it like this: your system Python is the main house. A virtual environment is a tent in the backyard. Each tent has its own furniture. Nothing affects the main house or other tents.
Creating an Environment
Python 3.3+ includes venv. No extra installation needed.
# Navigate to your project folder first
cd my-project
# Create the environment
python -m venv venv
# This creates a "venv" folder in your project
You can name it anything, but venv or .venv are conventions everyone recognizes.
Activating and Deactivating
Creating isn't enough—you have to activate it.
# Mac/Linux
source venv/bin/activate
# Windows (Command Prompt)
venv\Scripts\activate.bat
# Windows (PowerShell)
venv\Scripts\Activate.ps1
Your prompt changes to show (venv) at the start. Now pip install goes into the virtual environment, not your system.
When you're done:
deactivate
Managing Dependencies
With your environment activated:
# Install packages
pip install flask requests
# See what's installed
pip list
# Save to file
pip freeze > requirements.txt
requirements.txt lists every package and exact version. When a teammate clones your project:
# Create their own environment
python -m venv venv
source venv/bin/activate
# Install everything you have
pip install -r requirements.txt
Same versions. Same behavior. No surprises.
Never Commit venv/
The venv folder can contain thousands of files and is OS-specific. A venv created on Mac won't work on Windows.
Add it to .gitignore:
# .gitignore
venv/
.venv/
__pycache__/
*.pyc
Commit requirements.txt. Never commit venv/.
IDE Integration
VS Code and PyCharm detect virtual environments automatically. If yours doesn't:
- VS Code: Cmd/Ctrl+Shift+P → "Python: Select Interpreter" → choose the one in
venv/bin/python - PyCharm: Settings → Project → Python Interpreter → Add → Existing environment
Now autocomplete and linting use your project's packages, not system packages.
The Workflow
Every new project:
- Create folder
python -m venv venv- Activate it
- Install packages
pip freeze > requirements.txt- Add
venv/to.gitignore - Code
It becomes muscle memory after a few projects.
Alternatives
For more complex projects, tools like Poetry handle virtual environments plus dependency resolution plus packaging in one tool. But for learning and simple projects, venv is perfect.
Master the basics first. Graduate to fancier tools when you hit their limitations.