From ed9af52ff064663f8ed2f40191b144a2b6a9865b Mon Sep 17 00:00:00 2001 From: Nick Coghlan Date: Mon, 23 Dec 2013 17:39:12 +1000 Subject: [PATCH] Issue #19734: ignore pip env vars in ensurepip._uninstall --- Lib/ensurepip/__init__.py | 21 +++++++++++++++------ Lib/test/test_ensurepip.py | 14 ++++++++++++++ 2 files changed, 29 insertions(+), 6 deletions(-) diff --git a/Lib/ensurepip/__init__.py b/Lib/ensurepip/__init__.py index 5ceda516a2d..090c4108086 100644 --- a/Lib/ensurepip/__init__.py +++ b/Lib/ensurepip/__init__.py @@ -36,6 +36,14 @@ def version(): """ return _PIP_VERSION +def _clear_pip_environment_variables(): + # We deliberately ignore all pip environment variables + # when invoking pip + # See http://bugs.python.org/issue19734 for details + keys_to_remove = [k for k in os.environ if k.startswith("PIP_")] + for k in keys_to_remove: + del os.environ[k] + def bootstrap(*, root=None, upgrade=False, user=False, altinstall=False, default_pip=False, @@ -49,11 +57,7 @@ def bootstrap(*, root=None, upgrade=False, user=False, if altinstall and default_pip: raise ValueError("Cannot use altinstall and default_pip together") - # We deliberately ignore all pip environment variables - # See http://bugs.python.org/issue19734 for details - keys_to_remove = [k for k in os.environ if k.startswith("PIP_")] - for k in keys_to_remove: - del os.environ[k] + _clear_pip_environment_variables() # By default, installing pip and setuptools installs all of the # following scripts (X.Y == running Python version): @@ -101,7 +105,10 @@ def bootstrap(*, root=None, upgrade=False, user=False, _run_pip(args + [p[0] for p in _PROJECTS], additional_paths) def _uninstall(*, verbosity=0): - """Helper to support a clean default uninstall process on Windows""" + """Helper to support a clean default uninstall process on Windows + + Note that calling this function may alter os.environ. + """ # Nothing to do if pip was never installed, or has been removed try: import pip @@ -114,6 +121,8 @@ def _uninstall(*, verbosity=0): "({!r} installed, {!r} bundled)") raise RuntimeError(msg.format(pip.__version__, _PIP_VERSION)) + _clear_pip_environment_variables() + # Construct the arguments to be passed to the pip command args = ["uninstall", "-y"] if verbosity: diff --git a/Lib/test/test_ensurepip.py b/Lib/test/test_ensurepip.py index 8c125bf036c..2080ef115ca 100644 --- a/Lib/test/test_ensurepip.py +++ b/Lib/test/test_ensurepip.py @@ -160,6 +160,13 @@ class TestUninstall(unittest.TestCase): self.run_pip = run_pip_patch.start() self.addCleanup(run_pip_patch.stop) + # Avoid side effects on the actual os module + os_patch = unittest.mock.patch("ensurepip.os") + patched_os = os_patch.start() + self.addCleanup(os_patch.stop) + patched_os.path = os.path + self.os_environ = patched_os.environ = os.environ.copy() + def test_uninstall_skipped_when_not_installed(self): with fake_pip(None): ensurepip._uninstall() @@ -204,6 +211,13 @@ class TestUninstall(unittest.TestCase): ["uninstall", "-y", "-vvv", "pip", "setuptools"] ) + def test_pip_environment_variables_removed(self): + # ensurepip deliberately ignores all pip environment variables + # See http://bugs.python.org/issue19734 for details + self.os_environ["PIP_THIS_SHOULD_GO_AWAY"] = "test fodder" + with fake_pip(): + ensurepip._uninstall() + self.assertNotIn("PIP_THIS_SHOULD_GO_AWAY", self.os_environ)