Skip to content
Damjan Georgievski edited this page Oct 28, 2018 · 2 revisions

pep-370 based virtual environments

I don't like virtualenv! It seems to me like a huge hack. Python versions more recent than 2.6 have http://www.python.org/dev/peps/pep-0370/ support that can almost fully replace virtualenv without the hacks and ugliness.

This is a bash helper function that will ease the creation of virtual environments acording to the ##pep-370## standard.

The activate script is loosely based on virtualenv, but overall this is much simpler tool than virtualenv since it doesn't need to make a copy (or a link) of the python binary or of anything from ##/usr/lib/python2.6/##.

# Create a PEP-370 Python virtual env
function create_env () {
    ENV=`readlink -f $1` || return 1
    mkdir $ENV || return 1
    mkdir $ENV/bin || return 1
    cat <<-EOF > $ENV/bin/activate
        # first check if other env is active
        [ x"$PYTHONUSERBASE" != x ] && echo "PYTHONUSERBASE already active from $PYTHONUSERBASE. Use 'deactivate' first." && return 1

	# setup pep-370
        # alternatively ENV=$(dirname $(readlink -f $BASH_SOURCE)/..) would make the activate script stateless
	export PYTHONUSERBASE=$ENV

	# configure pip
	export PIP_INSTALL_OPTION=--user

	# setup the bash prompt
	_OLD_PS1=\$PS1
	PS1="[$1]\$PS1"

	# setup the bash path
	_OLD_PATH=\$PATH
	PATH=\$PYTHONUSERBASE/bin:\$PATH

	# .. and at last allow for cleanup
	alias deactivate='PATH=\$_OLD_PATH; PS1=\$_OLD_PS1; unset PIP_INSTALL_OPTION; unset PYTHONUSERBASE; unalias deactivate'
	EOF
    echo "source $ENV/bin/activate in your shell to activate this environment."
}
# end of PEP-370 creator

I have this in my ##/.bashrc##, but on Debian/Ubuntu you can put it in ##/.bash_aliases## too. It seems to work in zsh too. But beware of the TAB characters - they are needed in that cat <<-EOF segment.

The activate script also configures pip (versions 0.7 and up) to install in the virtual environment by default.

Usage:

damjan$ create_env xxx
damjan$ source xxx/bin/activate
[xxx]damjan$
[xxx]damjan$ pip install Flask
...
[xxx]damjan$ python
>>> import sys
>>> sys.path
...
[xxx]damjan$ deactivate
damjan$
damjan$ ls xxx/lib/python2.6/site-packages/ # too see how simple and elegant it is

TODO:

  • error handling and reporting