I came to know about virtualenv and pyenv a while ago, and used them separately for a while. Recently, while investigating best practices and tools for Python development I found pyenv-virtualenv. I find it useful (it takes care of using the right method for creating the virtual environment depending on the Python version) and clean (since the venv directory is not entangled with your codebase).

The problem I find is that previously (when using pyenv and virtualenv separately) I would push my requirements.txt file and my .python-version file to the repository. When cloning the project a few months later I could recreate my virtual environment using requirements.txt and could check .python-version to see which Python version I was developing on.

With pyenv-virtualenv, however, the .python-version file is less useful. Since in pyenv-virtualenv a virtual environment is treated like a new version of Python inside pyenv, and the way to link your project to the virtual environment is by "setting the Python version" to that virtual environment, the file no longer contains the exact Python version you are using.

Let's pretend I'm working on project Euler and decide to create a virtual environment for it using pyenv-virtualenv, and I call it project_euler. In order to make my code base to run on that virtual environment I need to go to the project's directory and type: pyenv local project_euler.

Now everything works great locally, but when I push to my repository and grab it again in a few months, .python-version won't be too useful, since it will only say "project_euler". Furthermore, if the person who downloads the repository has a virtualenv named project_euler as well which is configured differently to the one I was using when I pushed, they might use a wrongly-configured environment without realising it. This wasn't a problem when using pyenv and virtualenv separately, since .python-version only included information about the Python version then, not the name of the virtual environment in use.

What are the best practices to deal with these issues? I can think of several options:

  • Include the Python version in the name of your virtual environments: project_euler_3.5.3 (note that this does not solve the issue with using the wrong virtual environment by mistake).
  • Do not push .python-version, instead document the minimum supported Python version in the README.
  • Do not push .python-version, and do not document the Python version (doesn't seem right, since there are retrocompatibility issues even between minor revisions --e.g. 3.5 vs 3.4-- so it shouldn't be up to the user to have to guess).

2 Answers 2


I would recommend using pipenv for python development which solves a bunch of problems.

It is now the official tool recommended from python.org

If you have experience with say npm or something like that, pipenv behaves in similar ways. It does its bookkeeping in two files (Pipfile and Pipfile.lock).It helps you to create deterministic builds. In order to get a working environment, you commit both as you would with a requirements.txt alongside your code, check out the code, run pipenv install and voilà. With pipenv shell you enter your virtual environment.

In your Pipfile is a section for the purpose of defining the required python version, e.g.

python_version = "3.6"

The short answer is that with pip/virtualenv you can't. Both assume a compatible Python runtime is installed (they are Python packages after all). Specifying the version in the README is the way to go with that.

You could look into writing a custom installation script, but that's what setuptools is for. You can specify the required Python version with python_requires in setup.py. This will give a sensible error message if the required Python isn't present and has many ways to handle other custom install needs.

This may seem like yet another way to manage versions, but it is the Python standard and there are a lot of advantages, including years of community knowledge.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.