Python venv Not Activated - Packages Missing Across CI Steps
You installed packages into a virtualenv in one step, but a later step runs in a fresh shell that never activated it - so the interpreter on PATH is the system Python with none of your packages.
What this error means
A package installs fine, yet a later step fails with ModuleNotFoundError for that exact package. Activating the venv inside that step makes it work, proving the activation did not carry over.
Step "Install": Successfully installed flask-3.0.0
Step "Run": ModuleNotFoundError: No module named 'flask'Common causes
Each CI step is a new shell
In GitHub Actions and most CI systems, every run: step starts a fresh shell. A source .venv/bin/activate in one step does not persist to the next.
PATH/VIRTUAL_ENV not exported between steps
Activation just edits PATH for the current shell. Without exporting it to the job environment, later steps fall back to the system interpreter.
How to fix it
Add the venv to the job PATH once
On GitHub Actions, write the venv bin directory to $GITHUB_PATH so every later step uses it.
- run: |
python -m venv .venv
echo "$PWD/.venv/bin" >> "$GITHUB_PATH"
- run: pip install -r requirements.txt # uses the venv
- run: pytest # also uses the venvOr activate within each step
If you prefer, activate at the start of every step that needs the venv.
- run: |
. .venv/bin/activate
pytestHow to prevent it
- Persist the venv
binto the job PATH instead of relying on per-step activation. - Cache the venv keyed on your lockfile to keep steps consistent.
- Standardize on
python -minvocations that target the active interpreter.