pyenv-virtualenv: Tox can't find python3.x executable in virtualenv

After creating a virtualenv with:

pyenv virtualenv 3.5.3 myenv

I’m not able to run tox with this ini file:

[tox]
envlist = py35

[testenv]
commands =
    pytest {posargs: --pep8 --pylint}

deps = .[test]

The following error appears:

ERROR: InvocationError: Failed to get version_info for python3.5: b"pyenv: python3.5: command not found\n\nThe `python3.5' command exists in these Python versions:\n  3.5.3\n\n"

After checking my virtualenv it’s clear that it doesn’t contain a python3.5 symlink.

(myenv) ➜  ~ ll /home/stefanga/.pyenv/versions/myenv/bin/      
total 32K
-rw-r--r-- 1 stefanga axusers 2.2K Mar  3 13:06 activate
-rw-r--r-- 1 stefanga axusers 1.3K Mar  3 13:06 activate.csh
-rw-r--r-- 1 stefanga axusers 2.4K Mar  3 13:06 activate.fish
-rwxr-xr-x 1 stefanga axusers  276 Mar  3 13:06 easy_install
-rwxr-xr-x 1 stefanga axusers  276 Mar  3 13:06 easy_install-3.5
-rwxr-xr-x 1 stefanga axusers  248 Mar  3 13:06 pip
-rwxr-xr-x 1 stefanga axusers  248 Mar  3 13:06 pip3
-rwxr-xr-x 1 stefanga axusers  248 Mar  3 13:06 pip3.5
lrwxrwxrwx 1 stefanga axusers   47 Mar  3 13:06 python -> /home/stefanga/.pyenv/versions/3.5.3/bin/python
lrwxrwxrwx 1 stefanga axusers    6 Mar  3 13:06 python3 -> python

After creating the python3.5 -> python symlink manually tox executed without any errors.

Shouldn’t all executables (python, pythonx and python x.y) be available in the virtualenv?

<bountysource-plugin>

Want to back this issue? Post a bounty on it! We accept bounties via Bountysource. </bountysource-plugin>

About this issue

  • Original URL
  • State: closed
  • Created 7 years ago
  • Reactions: 15
  • Comments: 16

Most upvoted comments

If you think so, just write something by yourself.

To anyone that finds this thread and experience the same issue and don’t want to use yet another plugin to solve it.

I’ve found a workaround to this issue.

By specifying exactly which python binary you want to use you can get the expected behaviour.

pyenv virtualenv -p python3.5 3.5.3 myenv

will create a virtualenv with the following contents in ./bin

ll ~/.pyenv/versions/myenv/bin 
total 12M
-rw-r--r-- 1 stefanga axusers 2.1K Mar  7 14:51 activate
-rw-r--r-- 1 stefanga axusers 1.1K Mar  7 14:51 activate.csh
-rw-r--r-- 1 stefanga axusers 2.2K Mar  7 14:51 activate.fish
-rw-r--r-- 1 stefanga axusers 1.2K Mar  7 14:51 activate_this.py
-rwxr-xr-x 1 stefanga axusers  277 Mar  7 14:51 easy_install
-rwxr-xr-x 1 stefanga axusers  277 Mar  7 14:51 easy_install-3.5
-rwxr-xr-x 1 stefanga axusers  249 Mar  7 14:51 pip
-rwxr-xr-x 1 stefanga axusers  249 Mar  7 14:51 pip3
-rwxr-xr-x 1 stefanga axusers  249 Mar  7 14:51 pip3.5
lrwxrwxrwx 1 stefanga axusers    9 Mar  7 14:51 python -> python3.5
lrwxrwxrwx 1 stefanga axusers    9 Mar  7 14:51 python3 -> python3.5
-rwxr-xr-x 1 stefanga axusers  12M Mar  7 14:51 python3.5
-rwxr-xr-x 1 stefanga axusers 2.4K Mar  7 14:51 python-config
-rwxr-xr-x 1 stefanga axusers  256 Mar  7 14:51 wheel

The plugin (probably the python venv module) now creates a virtualenv with python3.5 binary as the primary binary and creates symlinks to this. The result is that I’ve got my pythonX.Y binary in the virtualenv and tox is happy again.

@madhurabhogate I would suggest that you create different venvs for different python versions. Then you can use them at the same time with pyenv <shell|local> <py35venv> <py36venv>. The python binaries from both venvs should be available in your path for tox to find.

# Do the following in your shell
$ pyenv virtualenv -p python3.5 3.5.4 py35
$ pyenv virtualenv -p python3.6 3.6.3 py36
$ pyenv shell py36 py35

# Then you should have two active environments you can use
$ pyenv versions
  system
  3.5.4
  3.5.4/envs/py35
  3.6.3
  3.6.3/envs/py36
* py35 (set by PYENV_VERSION environment variable)
* py36 (set by PYENV_VERSION environment variable)

# Now you should be able to run tox for both py35 and py36 envlists

The issue for me was simply a case of not having the Pythons on the pyenv path. Fixed by adding them to the path:

pyenv local 3.7.2 3.6.8 3.5.6 pypy3.5-6.0.0 pypy2.7-6.0.0

Note that there is a small typo in @gangefors 's example (at least for pyenv 1.2.7) with a flag:

$ brew install pyenv-virtualenv
$ pyenv virtualenv -p python3.5 3.5.6 py35
$ pyenv virtualenv -p python3.6 3.6.6 py36
$ pyenv virtualenv -p python3.7 3.7.0 py37
$ pyenv shell py35 py36 py37

If using with tox, order of cmds seems to be a tiny bit finnicky and very particular:

$ pyenv shell py35 py36 py37
$ python3.7 -m venv venv
$ source ./venv/bin/activate
$ tox

you can try:


pyenv shell 3.5.3

ref: https://github.com/pyenv/pyenv/issues/856