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

Ignoring revisions in .git-blame-ignore-revs. Click here to bypass and see the normal blame view.

181 lines
6.3 KiB
Python
Raw Permalink Normal View History

"""
locations.py tests
"""
2017-05-16 12:16:30 +02:00
import getpass
import os
import shutil
2017-05-16 12:16:30 +02:00
import sys
import sysconfig
import tempfile
from pathlib import Path
from typing import Any, Dict
2021-02-10 11:38:21 +01:00
from unittest.mock import Mock
import pytest
from pip._internal.locations import SCHEME_KEYS, _should_use_sysconfig, get_scheme
if sys.platform == "win32":
pwd = Mock()
else:
import pwd
def _get_scheme_dict(*args: Any, **kwargs: Any) -> Dict[str, str]:
scheme = get_scheme(*args, **kwargs)
return {k: getattr(scheme, k) for k in SCHEME_KEYS}
class TestLocations:
def setup_method(self) -> None:
self.tempdir = tempfile.mkdtemp()
self.st_uid = 9999
self.username = "example"
self.patch()
def teardown_method(self) -> None:
self.revert_patch()
shutil.rmtree(self.tempdir, ignore_errors=True)
def patch(self) -> None:
"""first store and then patch python methods pythons"""
self.tempfile_gettempdir = tempfile.gettempdir
self.old_os_fstat = os.fstat
2013-01-26 08:09:46 +01:00
if sys.platform != "win32":
# os.geteuid and pwd.getpwuid are not implemented on windows
self.old_os_geteuid = os.geteuid
self.old_pwd_getpwuid = pwd.getpwuid
self.old_getpass_getuser = getpass.getuser
# now patch
tempfile.gettempdir = lambda: self.tempdir
getpass.getuser = lambda: self.username
os.fstat = lambda fd: self.get_mock_fstat(fd)
if sys.platform != "win32":
2021-11-22 08:52:23 +01:00
os.geteuid = lambda: self.st_uid
2021-09-28 12:51:46 +02:00
pwd.getpwuid = self.get_mock_getpwuid
def revert_patch(self) -> None:
"""revert the patches to python methods"""
tempfile.gettempdir = self.tempfile_gettempdir
getpass.getuser = self.old_getpass_getuser
2013-01-26 08:09:46 +01:00
if sys.platform != "win32":
# os.geteuid and pwd.getpwuid are not implemented on windows
os.geteuid = self.old_os_geteuid
pwd.getpwuid = self.old_pwd_getpwuid
os.fstat = self.old_os_fstat
def get_mock_fstat(self, fd: int) -> os.stat_result:
"""returns a basic mock fstat call result.
Currently only the st_uid attribute has been set.
"""
result = Mock()
result.st_uid = self.st_uid
return result
2021-09-28 12:51:46 +02:00
def get_mock_getpwuid(self, uid: int) -> Any:
"""returns a basic mock pwd.getpwuid call result.
Currently only the pw_name attribute has been set.
"""
result = Mock()
result.pw_name = self.username
return result
def test_default_should_use_sysconfig(
self, monkeypatch: pytest.MonkeyPatch
) -> None:
monkeypatch.delattr(sysconfig, "_PIP_USE_SYSCONFIG", raising=False)
if sys.version_info[:2] >= (3, 10):
assert _should_use_sysconfig() is True
else:
assert _should_use_sysconfig() is False
@pytest.mark.parametrize("vendor_value", [True, False, None, "", 0, 1])
def test_vendor_overriden_should_use_sysconfig(
self, monkeypatch: pytest.MonkeyPatch, vendor_value: Any
) -> None:
monkeypatch.setattr(
sysconfig, "_PIP_USE_SYSCONFIG", vendor_value, raising=False
)
assert _should_use_sysconfig() is bool(vendor_value)
2019-09-06 10:29:34 +02:00
class TestDistutilsScheme:
def test_root_modifies_appropriately(self) -> None:
# This deals with nt/posix path differences
# root is c:\somewhere\else or /somewhere/else
root = os.path.normcase(
os.path.abspath(os.path.join(os.path.sep, "somewhere", "else"))
2021-08-13 15:23:45 +02:00
)
norm_scheme = _get_scheme_dict("example")
root_scheme = _get_scheme_dict("example", root=root)
for key, value in norm_scheme.items():
drive, path = os.path.splitdrive(os.path.abspath(value))
expected = os.path.join(root, path[1:])
2014-03-13 21:04:43 +01:00
assert os.path.abspath(root_scheme[key]) == expected
@pytest.mark.incompatible_with_sysconfig
@pytest.mark.incompatible_with_venv
def test_distutils_config_file_read(
self, tmpdir: Path, monkeypatch: pytest.MonkeyPatch
) -> None:
# This deals with nt/posix path differences
install_scripts = os.path.normcase(
os.path.abspath(os.path.join(os.path.sep, "somewhere", "else"))
2021-08-13 15:23:45 +02:00
)
f = tmpdir / "config" / "setup.cfg"
f.parent.mkdir()
f.write_text("[install]\ninstall-scripts=" + install_scripts)
from distutils.dist import Distribution
2020-09-23 15:08:01 +02:00
# patch the function that returns what config files are present
monkeypatch.setattr(
Distribution,
"find_config_files",
lambda self: [f],
)
scheme = _get_scheme_dict("example")
assert scheme["scripts"] == install_scripts
@pytest.mark.incompatible_with_sysconfig
@pytest.mark.incompatible_with_venv
# when we request install-lib, we should install everything (.py &
# .so) into that path; i.e. ensure platlib & purelib are set to
# this path. sysconfig does not support this.
def test_install_lib_takes_precedence(
self, tmpdir: Path, monkeypatch: pytest.MonkeyPatch
) -> None:
# This deals with nt/posix path differences
install_lib = os.path.normcase(
os.path.abspath(os.path.join(os.path.sep, "somewhere", "else"))
2021-08-13 15:23:45 +02:00
)
f = tmpdir / "config" / "setup.cfg"
f.parent.mkdir()
f.write_text("[install]\ninstall-lib=" + install_lib)
from distutils.dist import Distribution
2020-09-23 15:08:01 +02:00
# patch the function that returns what config files are present
monkeypatch.setattr(
Distribution,
"find_config_files",
lambda self: [f],
)
scheme = _get_scheme_dict("example")
assert scheme["platlib"] == install_lib + os.path.sep
assert scheme["purelib"] == install_lib + os.path.sep
2020-07-07 11:34:23 +02:00
def test_prefix_modifies_appropriately(self) -> None:
2020-07-07 11:34:23 +02:00
prefix = os.path.abspath(os.path.join("somewhere", "else"))
normal_scheme = _get_scheme_dict("example")
prefix_scheme = _get_scheme_dict("example", prefix=prefix)
2020-07-07 11:34:23 +02:00
def _calculate_expected(value: str) -> str:
2020-07-07 11:34:23 +02:00
path = os.path.join(prefix, os.path.relpath(value, sys.prefix))
return os.path.normpath(path)
expected = {k: _calculate_expected(v) for k, v in normal_scheme.items()}
assert prefix_scheme == expected