1
1
Fork 0
mirror of https://github.com/pypa/pip synced 2023-12-13 21:30:23 +01:00

Merge pull request #11466 from minrk/build_env_isolation

This commit is contained in:
Tzu-ping Chung 2022-09-26 11:00:21 +08:00 committed by GitHub
commit 0a21080411
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 38 additions and 4 deletions

1
news/6264.bugfix.rst Normal file
View file

@ -0,0 +1 @@
Fix build environment isolation on some system Pythons.

View file

@ -4,6 +4,7 @@
import logging
import os
import pathlib
import site
import sys
import textwrap
from collections import OrderedDict
@ -55,6 +56,26 @@ def get_runnable_pip() -> str:
return os.fsdecode(source / "__pip-runner__.py")
def _get_system_sitepackages() -> Set[str]:
"""Get system site packages
Usually from site.getsitepackages,
but fallback on `get_purelib()/get_platlib()` if unavailable
(e.g. in a virtualenv created by virtualenv<20)
Returns normalized set of strings.
"""
if hasattr(site, "getsitepackages"):
system_sites = site.getsitepackages()
else:
# virtualenv < 20 overwrites site.py without getsitepackages
# fallback on get_purelib/get_platlib.
# this is known to miss things, but shouldn't in the cases
# where getsitepackages() has been removed (inside a virtualenv)
system_sites = [get_purelib(), get_platlib()]
return {os.path.normcase(path) for path in system_sites}
class BuildEnvironment:
"""Creates and manages an isolated environment to install build deps"""
@ -75,9 +96,8 @@ class BuildEnvironment:
# Customize site to:
# - ensure .pth files are honored
# - prevent access to system site packages
system_sites = {
os.path.normcase(site) for site in (get_purelib(), get_platlib())
}
system_sites = _get_system_sitepackages()
self._site_dir = os.path.join(temp_dir.path, "site")
if not os.path.exists(self._site_dir):
os.mkdir(self._site_dir)

View file

@ -4,7 +4,7 @@ from typing import Optional
import pytest
from pip._internal.build_env import BuildEnvironment
from pip._internal.build_env import BuildEnvironment, _get_system_sitepackages
from tests.lib import (
PipTestEnvironment,
TestPipResult,
@ -226,6 +226,10 @@ def test_build_env_isolation(script: PipTestEnvironment) -> None:
script.pip_install_local("-t", target, pkg_whl)
script.environ["PYTHONPATH"] = target
system_sites = _get_system_sitepackages()
# there should always be something to exclude
assert system_sites
run_with_build_env(
script,
"",
@ -247,5 +251,14 @@ def test_build_env_isolation(script: PipTestEnvironment) -> None:
})), file=sys.stderr)
print('sys.path:\n ' + '\n '.join(sys.path), file=sys.stderr)
sys.exit(1)
"""
f"""
# second check: direct check of exclusion of system site packages
import os
normalized_path = [os.path.normcase(path) for path in sys.path]
for system_path in {system_sites!r}:
assert system_path not in normalized_path, \
f"{{system_path}} found in {{normalized_path}}"
""",
)