09-30-2022 07:46 AM - edited 12-01-2022 12:12 PM
pyenv for Managing Python Versions and Environments
The Python language has many working versions. At the time of this writing, Python has progressed all the way from version 1.0 in 1994 to version 3.10 and beyond today. Often, different projects we have benefited from or contributed to require exact Python versions in order to run as expected. Wouldn’t it be nice to have a ‘version manager’ for Python to switch between versions locally in different directories, as well as in our virtual environments?
* I've had better success with the following process inside of an IDE, like VS Code, than in the Terminal
$ python -V
Python 2.7.12
It may be 2.7 or 3.0 or 3.6, but regardless, it’s probably not the version you want, at least not all the time.
Normally, when we install Python, we do so globally. But this can be problematic if we need to run another version besides the one we installed globally.
pyenv builds from source; this means we definitely need to install the required dependencies first. They vary by operating systems.
macOS
$ brew install openssl readline sqlite3 xz zlib
Ubuntu/Debian
$ sudo apt-get install -y make build-essential libssl-dev zlib1g-dev \libbz2-dev libreadline-dev libsqlite3-dev wget curl llvm libncurses5-dev \libncursesw5-dev xz-utils tk-dev libffi-dev liblzma-dev python-openssl
Fedora/CentOS/RHEL
$ sudo yum install gcc zlib-devel bzip2 bzip2-devel readline-devel sqlite \sqlite-devel openssl-devel xz xz-devel libffi-devel
Windows
Originally, pyenv did not support Windows at all. However, there is some basic support for Windows now available via the pyen-win project.
Get pyenv for Windows here: https://github.com/pyenv-win/pyenv-win
Once again, the instructions vary by operating system. The recommended method is to use cURL and the pyenv-installer. This one command will do that for you.
$ curl https://pyenv.run | bash
However, there are other installation methods, including with brew and with GitHub checkout. To see what those are, see the pyenv GitHub repository here:
https://github.com/pyenv/pyenv#installation
One thing you do not want to skip, is setting up your shell environment, whether bash or zsh, for pyenv. The instructions are here:
https://github.com/pyenv/pyenv#set-up-your-shell-environment-for-pyenv
When pyenv is properly installed, you should see something like this:
WARNING: seems you still have not added 'pyenv' to the load path. Load pyenv automatically by adding the following to ~/.bashrc: export PATH="$HOME/.pyenv/bin:$PATH"eval "$(pyenv init -)"eval "$(pyenv virtualenv-init -)"
Once you see that, restart your shell and we can begin installing python versions with pyenv.
$ exec "$SHELL" # Or just restart your terminal
With the following command, we can see all the Python version available from pyenv (the list is too long to show).
$ pyenv install –list
Let’s say we want to see just the available Python 3.8 versions; we can run this command.
$ pyenv install --list | grep "3.8"
3.8.0
3.8-dev
3.8.1
3.8.2
3.8.3
3.8.4
3.8.5
3.8.6
3.8.7
3.8.8
3.8.9
3.8.10
3.8.11
3.8.12
3.8.13
miniconda-3.8.3
miniconda3-3.8.3
miniconda3-3.8-4.8.2
miniconda3-3.8-4.8.3
miniconda3-3.8-4.9.2
miniconda3-3.8-4.10.1
miniconda3-3.8-4.10.3
miniconda3-3.8-4.11.0
miniconda3-3.8-4.12.0
pypy2.7-7.3.8-src
pypy2.7-7.3.8
pypy3.7-7.3.8-src
pypy3.7-7.3.8
pypy3.8-7.3.6-src
pypy3.8-7.3.6
pypy3.8-7.3.7-src
pypy3.8-7.3.7
pypy3.8-7.3.8-src
pypy3.8-7.3.8
pypy3.8-7.3.9-src
pypy3.8-7.3.9
pypy3.9-7.3.8-src
pypy3.9-7.3.8
Now suppose you need to install Python 3.8.11 in order to run a certain application locally. Run this command.
$ pyenv install 3.8.11
It will take a few moments to install. When it’s done, we can check pyenv for the versions of Python now available to us.
$ pyenv versions* system3.8.11
We can now see version 3.8.11 is available to us. ‘system’ has an (*) next to it to indicate this is the version that is currently active. ‘system’ denotes the Python version installed with your operating system.
Python 3.8.11 is a good version of Python to set as our global version; it’s relatively recent but not too new. There are two ways we can set it as the global version. Here’s the first way.
$ pyenv global 3.8.11
The second way is to edit the version in this file:
/Users/<your username>/.python-version
Let’s confirm 3.8.11 is the global Python version.
$ pyenv global
3.8.11
Okay, once I have the global version set, I almost never mess with it. When we want to change versions, we can use ‘pyenv local’.
Let’s say we want to use Python 3.8.9 when working in a certain directory. First, I’d install that version.
$ pyenv install 3.8.9
Then we create a directory, cd into that directory and set the local version of Python to 3.8.9
$ mkdir test_dir_3.8.9 && cd test_dir_3.8.9
test_dir_3.8.9 $ pyenv local 3.8.9
Let’s test to make sure version 3.8.9 is running in our new directory.
test_dir_3.8.9 $ python -V
Python 3.8.9
If we cd out of the new directory, the Python version will revert to the global version.
test_dir_3.8.9 $ cd .. && python -V
Python 3.8.11
We can create a virtual environment with a specific Python version in a single command.
$ pyenv virtualenv <python_version> <environment_name>
The <environment_name> is a name chosen by the user to help keep track of the environment. The best practice is to give the virtual environment the same name as your project. For example, if we were working on a project called ‘cisco_meraki_analysis’, which required Python 3.8.9, we would run this command.
$ pyenv virtualenv 3.8.9 cisco_meraki_analysis
*remember to make sure you have 3.8.9. installed with pyenv. You can check that with:
$ pyenv versions
If you need to install it, use this:
$ pyenv install 3.8.9
Alright, let’s activate the ‘cisco_meraki_analysis’ virtual environment, which we’ve linked with Python version 3.8.9.
Here’s the format for activating the virtual environment:
$ pyenv activate <environment_name>
Once I do that, we can tell we have entered the virtual environment because the name of the environment is presented in parentheses at the beginning of the command prompt:
(cisco_meraki_analysis) $
Let’s test whether Python version 3.8.9 is active inside the virtual environment.
(cisco_meraki_analysis) $ python -V
Python 3.8.9
Once we cd back out of this virtual environment, the Python version changes to global or local version you have set.
(cisco_meraki_analysis) $ cd .. && python -V
Python 3.8.11
If we cd back into the cisco_meraki_analysis directory, we will automatically enter the virtual environment with the correct Python version inside.
$ cd cisco_meraki_analysis
(cisco_meraki_analysis) $ python -V
Python 3.8.9
If we ever need to deactivate our virtual environment, we use the following command:
$ pyenv shell system
To reactivate it again, use:
$ pyenv activate <environment_name>
If you ever wish to delete a pyenv virtual environment, you can do so by deleting that folder under ~/.pyenv/versions/<your Python version>/envs/
We know the ‘env’ in ‘pyenv’ stands for ‘environment’, but it might just stand for ‘envy’ when your developer friends and colleagues see how effortlessly you glide between Python versions using pyenv.
Seriously though, pyenv is a game-changer, time-saver and the best way to organize multiple Python version on our systems. If we take the time to learn it and use it, we can save ourselves a lot of time and headaches. I hope this article has answered any questions you have about pyenv and motivated you to try it out for yourself.
* An MP3 version of this article, in English, can be downloaded, as a ZIP file, from the Attachments at the bottom of the page.
Find answers to your questions by entering keywords or phrases in the Search bar above. New here? Use these resources to familiarize yourself with the community: