Skip to content

Commit

Permalink
Fix provisioning from pyvenv interpreter (#1452)
Browse files Browse the repository at this point in the history
When the original interpreter [0] tox is called with is actually a pyvenv
it will set the `__PYVENV_LAUNCHER__` environment variable to the path of
pyvenv interpreter.

If tox configuration specifies `requires` and the requirements are not
satifsfied by [0], tox will create an intermediate virtual environment [1].

After setting up [1] tox will delegate the original call by spawning
a new [1] interpreter with the identical identical list of arguments.

It will also pass the value of `__PYVENV_LAUNCHER__` if present. This in turn
causes `sys.executable` to resolve to [0] instead of [1] therefore ignoring all
modifications including installed requirements.

The fix is to make sure that when [0] spawns [1], `__PYVENV_LAUNCHER__` is
removed from the environment.
  • Loading branch information
Kentzo authored and gaborbernat committed Nov 11, 2019
1 parent 8e6f64a commit 5582194
Show file tree
Hide file tree
Showing 4 changed files with 23 additions and 0 deletions.
1 change: 1 addition & 0 deletions CONTRIBUTORS
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ Hazal Ozturk
Henk-Jaap Wagenaar
Ian Stapleton Cordasco
Igor Duarte Cardoso
Ilya Kulakov
Ionel Maries Cristian
Itxaka Serrano
Jake Windle
Expand Down
1 change: 1 addition & 0 deletions docs/changelog/1452.bugfix.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Fix provisioning from a pyvenv interpreter. — by :user:`kentzo`
1 change: 1 addition & 0 deletions src/tox/session/commands/provision.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ def provision_tox(provision_venv, args):
try:
env = os.environ.copy()
env[str("TOX_PROVISION")] = str("1")
env.pop('__PYVENV_LAUNCHER__', None)
action.popen(provision_args, redirect=False, report_fail=False, env=env)
return 0
except InvocationError as exception:
Expand Down
20 changes: 20 additions & 0 deletions tests/integration/test_provision_int.py
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,26 @@ def test_provision_missing(initproj, cmd):
assert meta_python.exists()


def test_provision_from_pyvenv(initproj, cmd, monkeypatch):
initproj(
"pkg123-0.7",
filedefs={
"tox.ini": """\
[tox]
skipsdist=True
minversion = 3.7.0
requires =
setuptools == 40.6.3
[testenv]
commands=python -c "import sys; print(sys.executable); raise SystemExit(1)"
"""
},
)
monkeypatch.setenv(str("__PYVENV_LAUNCHER__"), sys.executable)
result = cmd("-e", "py", "-vv")
result.assert_fail()
assert '.tox/.tox/bin/python -m virtualenv' in result.out

@pytest.mark.skipif(
"sys.platform == 'win32'", reason="triggering SIGINT reliably on Windows is hard"
)
Expand Down

0 comments on commit 5582194

Please sign in to comment.