I have a Python script that needs to be run from within a specific
Anaconda environment (which I’ll call
environment_name
) for reasons that aren’t relevant here. It was tricky to
get this working, so I figured it was worth a post. Here’s what made this
challenging:
- The script only works if it’s actually run in a specific environment
(accessed by executing
conda activate environment_name
), it’s not enough to set the python path in the shebang1 - I want to be able to run the script when I’m not in that environment, or even when I’m not using Anaconda at all (which is usually the case)
- Activating an Anaconda environment in any shell script requires extra steps
The solution I landed on is to replace the typical shebang line with a block of code that looks like this:
#! /bin/sh -
':' '''Describe the script here--this script just prints the Python version'
eval "$(conda shell.bash hook)"
conda activate environment_name
exec python3 -- "$0" "$@"
'''
import sys
print("Hello from Python", sys.version)
This approach is not without weaknesses:
- It (probably?) requires that
/bin/sh
be bash (or maybe just bash-like?), which is not always the case; you might need to replace/bin/sh
with the full path to bash - The script may need to be run as a specific user, I haven’t checked
- The code looks ugly and interferes with code-highlighting
- It’s certainly fragile in other ways I’ve yet to find
I’m sharing it anyway because it did solve my problem, and I hope to save somebody else the time it took me to figure this out. Or better yet, be told the “right” way to do this from a Python/Anaconda expert.
-
The first line of most contemporary python scripts is
#!/usr/bin/env python3
, which tells the shell to use python to execute the rest of the script. Since Anaconda installs additional copies of Python, sometimes it’s enough to replace this with something like#!/home/username/anaconda3/envs/environment_name/bin/python3
, but that didn’t work here. ↩︎