Skip to content

Commit

Permalink
Merge https://github.com/pypa/distutils into distutils-6852b20
Browse files Browse the repository at this point in the history
  • Loading branch information
jaraco committed Sep 29, 2022
2 parents badd706 + 6852b20 commit aea5615
Show file tree
Hide file tree
Showing 11 changed files with 250 additions and 234 deletions.
2 changes: 1 addition & 1 deletion setuptools/_distutils/dist.py
Expand Up @@ -334,7 +334,7 @@ def find_config_files(self):
- a file named by an environment variable
"""
check_environ()
files = [str(path) for path in self._gen_paths() if path.is_file()]
files = [str(path) for path in self._gen_paths() if os.path.isfile(path)]

if DEBUG:
self.announce("using config files: %s" % ', '.join(files))
Expand Down
14 changes: 7 additions & 7 deletions setuptools/_distutils/sysconfig.py
Expand Up @@ -13,6 +13,7 @@
import re
import sys
import sysconfig
import pathlib

from .errors import DistutilsPlatformError
from . import py39compat
Expand Down Expand Up @@ -40,14 +41,13 @@
project_base = os.getcwd()


# python_build: (Boolean) if true, we're either building Python or
# building an extension with an un-installed Python, so we use
# different (hard-wired) directories.
def _is_python_source_dir(d):
for fn in ("Setup", "Setup.local"):
if os.path.isfile(os.path.join(d, "Modules", fn)):
return True
return False
"""
Return True if the target directory appears to point to an
un-installed Python.
"""
modules = pathlib.Path(d).joinpath('Modules')
return any(modules.joinpath(fn).is_file() for fn in ('Setup', 'Setup.local'))


_sys_home = getattr(sys, '_home', None)
Expand Down
18 changes: 18 additions & 0 deletions setuptools/_distutils/tests/py37compat.py
@@ -0,0 +1,18 @@
import os
import sys
import platform


def subprocess_args_compat(*args):
return list(map(os.fspath, args))


def subprocess_args_passthrough(*args):
return list(args)


subprocess_args = (
subprocess_args_compat
if platform.system() == "Windows" and sys.version_info < (3, 8)
else subprocess_args_passthrough
)
8 changes: 0 additions & 8 deletions setuptools/_distutils/tests/py38compat.py
Expand Up @@ -18,27 +18,19 @@

try:
from test.support.os_helper import (
change_cwd,
rmtree,
EnvironmentVarGuard,
TESTFN,
unlink,
skip_unless_symlink,
temp_dir,
create_empty_file,
temp_cwd,
)
except (ModuleNotFoundError, ImportError):
from test.support import (
change_cwd,
rmtree,
EnvironmentVarGuard,
TESTFN,
unlink,
skip_unless_symlink,
temp_dir,
create_empty_file,
temp_cwd,
)


Expand Down
8 changes: 4 additions & 4 deletions setuptools/_distutils/tests/test_archive_util.py
Expand Up @@ -9,6 +9,7 @@
import pathlib

import pytest
import path

from distutils import archive_util
from distutils.archive_util import (
Expand All @@ -23,7 +24,6 @@
from test.support import patch
from .unix_compat import require_unix_id, require_uid_0, grp, pwd, UID_0_SUPPORT

from .py38compat import change_cwd
from .py38compat import check_warnings


Expand Down Expand Up @@ -95,7 +95,7 @@ def _make_tarball(self, tmpdir, target_name, suffix, **kwargs):
base_name = os.path.join(tmpdir2, target_name)

# working with relative paths to avoid tar warnings
with change_cwd(tmpdir):
with path.Path(tmpdir):
make_tarball(splitdrive(base_name)[1], 'dist', **kwargs)

# check if the compressed tarball was created
Expand Down Expand Up @@ -227,7 +227,7 @@ def test_make_zipfile(self):
# creating something to tar
tmpdir = self._create_files()
base_name = os.path.join(self.mkdtemp(), 'archive')
with change_cwd(tmpdir):
with path.Path(tmpdir):
make_zipfile(base_name, 'dist')

# check if the compressed tarball was created
Expand All @@ -253,7 +253,7 @@ def fake_zipfile(*a, **kw):
# create something to tar and compress
tmpdir = self._create_files()
base_name = os.path.join(self.mkdtemp(), 'archive')
with change_cwd(tmpdir):
with path.Path(tmpdir):
make_zipfile(base_name, 'dist')

tarball = base_name + '.zip'
Expand Down
9 changes: 5 additions & 4 deletions setuptools/_distutils/tests/test_build_ext.py
Expand Up @@ -8,6 +8,10 @@
import tempfile
import importlib
import shutil
import re

import path
import pytest

from distutils.core import Distribution
from distutils.command.build_ext import build_ext
Expand All @@ -27,10 +31,7 @@
)

from test import support
from . import py38compat as os_helper
from . import py38compat as import_helper
import pytest
import re


@pytest.fixture()
Expand All @@ -47,7 +48,7 @@ def user_site_dir(request):
# bpo-30132: On Windows, a .pdb file may be created in the current
# working directory. Create a temporary working directory to cleanup
# everything at the end of the test.
with os_helper.change_cwd(self.tmp_dir):
with path.Path(self.tmp_dir):
yield

site.USER_BASE = orig_user_base
Expand Down
59 changes: 28 additions & 31 deletions setuptools/_distutils/tests/test_core.py
Expand Up @@ -8,7 +8,6 @@

import pytest

from . import py38compat as os_helper
from distutils.dist import Distribution

# setup script that uses __file__
Expand Down Expand Up @@ -61,65 +60,63 @@ def save_stdout(monkeypatch):
monkeypatch.setattr(sys, 'stdout', sys.stdout)


@pytest.fixture
def temp_file(tmp_path):
return tmp_path / 'file'


@pytest.mark.usefixtures('save_env')
@pytest.mark.usefixtures('save_argv')
@pytest.mark.usefixtures('cleanup_testfn')
class TestCore:
def write_setup(self, text, path=os_helper.TESTFN):
f = open(path, "w")
try:
f.write(text)
finally:
f.close()
return path

def test_run_setup_provides_file(self):
def test_run_setup_provides_file(self, temp_file):
# Make sure the script can use __file__; if that's missing, the test
# setup.py script will raise NameError.
distutils.core.run_setup(self.write_setup(setup_using___file__))
temp_file.write_text(setup_using___file__)
distutils.core.run_setup(temp_file)

def test_run_setup_preserves_sys_argv(self):
def test_run_setup_preserves_sys_argv(self, temp_file):
# Make sure run_setup does not clobber sys.argv
argv_copy = sys.argv.copy()
distutils.core.run_setup(self.write_setup(setup_does_nothing))
temp_file.write_text(setup_does_nothing)
distutils.core.run_setup(temp_file)
assert sys.argv == argv_copy

def test_run_setup_defines_subclass(self):
def test_run_setup_defines_subclass(self, temp_file):
# Make sure the script can use __file__; if that's missing, the test
# setup.py script will raise NameError.
dist = distutils.core.run_setup(self.write_setup(setup_defines_subclass))
temp_file.write_text(setup_defines_subclass)
dist = distutils.core.run_setup(temp_file)
install = dist.get_command_obj('install')
assert 'cmd' in install.sub_commands

def test_run_setup_uses_current_dir(self):
# This tests that the setup script is run with the current directory
# as its own current directory; this was temporarily broken by a
# previous patch when TESTFN did not use the current directory.
def test_run_setup_uses_current_dir(self, tmp_path):
"""
Test that the setup script is run with the current directory
as its own current directory.
"""
sys.stdout = io.StringIO()
cwd = os.getcwd()

# Create a directory and write the setup.py file there:
os.mkdir(os_helper.TESTFN)
setup_py = os.path.join(os_helper.TESTFN, "setup.py")
distutils.core.run_setup(self.write_setup(setup_prints_cwd, path=setup_py))
setup_py = tmp_path / 'setup.py'
setup_py.write_text(setup_prints_cwd)
distutils.core.run_setup(setup_py)

output = sys.stdout.getvalue()
if output.endswith("\n"):
output = output[:-1]
assert cwd == output

def test_run_setup_within_if_main(self):
dist = distutils.core.run_setup(
self.write_setup(setup_within_if_main), stop_after="config"
)
def test_run_setup_within_if_main(self, temp_file):
temp_file.write_text(setup_within_if_main)
dist = distutils.core.run_setup(temp_file, stop_after="config")
assert isinstance(dist, Distribution)
assert dist.get_name() == "setup_within_if_main"

def test_run_commands(self):
def test_run_commands(self, temp_file):
sys.argv = ['setup.py', 'build']
dist = distutils.core.run_setup(
self.write_setup(setup_within_if_main), stop_after="commandline"
)
temp_file.write_text(setup_within_if_main)
dist = distutils.core.run_setup(temp_file, stop_after="commandline")
assert 'build' not in dist.have_run
distutils.core.run_commands(dist)
assert 'build' in dist.have_run
Expand Down
37 changes: 24 additions & 13 deletions setuptools/_distutils/tests/test_dist.py
Expand Up @@ -14,7 +14,6 @@
from distutils.cmd import Command

from test.support import captured_stdout, captured_stderr
from .py38compat import TESTFN
from distutils.tests import support
from distutils import log

Expand Down Expand Up @@ -95,15 +94,15 @@ def test_command_packages_cmdline(self, clear_argv):
'distutils' not in Distribution.parse_config_files.__module__,
reason='Cannot test when virtualenv has monkey-patched Distribution',
)
def test_venv_install_options(self, request):
def test_venv_install_options(self, tmp_path):
sys.argv.append("install")
request.addfinalizer(functools.partial(os.unlink, TESTFN))
file = str(tmp_path / 'file')

fakepath = '/somedir'

jaraco.path.build(
{
TESTFN: f"""
file: f"""
[install]
install-base = {fakepath}
install-platbase = {fakepath}
Expand All @@ -124,9 +123,9 @@ def test_venv_install_options(self, request):

# Base case: Not in a Virtual Environment
with mock.patch.multiple(sys, prefix='/a', base_prefix='/a'):
d = self.create_distribution([TESTFN])
d = self.create_distribution([file])

option_tuple = (TESTFN, fakepath)
option_tuple = (file, fakepath)

result_dict = {
'install_base': option_tuple,
Expand All @@ -153,35 +152,35 @@ def test_venv_install_options(self, request):

# Test case: In a Virtual Environment
with mock.patch.multiple(sys, prefix='/a', base_prefix='/b'):
d = self.create_distribution([TESTFN])
d = self.create_distribution([file])

for key in result_dict.keys():
assert key not in d.command_options.get('install', {})

def test_command_packages_configfile(self, request, clear_argv):
def test_command_packages_configfile(self, tmp_path, clear_argv):
sys.argv.append("build")
request.addfinalizer(functools.partial(os.unlink, TESTFN))
file = str(tmp_path / "file")
jaraco.path.build(
{
TESTFN: """
file: """
[global]
command_packages = foo.bar, splat
""",
}
)

d = self.create_distribution([TESTFN])
d = self.create_distribution([file])
assert d.get_command_packages() == ["distutils.command", "foo.bar", "splat"]

# ensure command line overrides config:
sys.argv[1:] = ["--command-packages", "spork", "build"]
d = self.create_distribution([TESTFN])
d = self.create_distribution([file])
assert d.get_command_packages() == ["distutils.command", "spork"]

# Setting --command-packages to '' should cause the default to
# be used even if a config file specified something else:
sys.argv[1:] = ["--command-packages", "", "build"]
d = self.create_distribution([TESTFN])
d = self.create_distribution([file])
assert d.get_command_packages() == ["distutils.command"]

def test_empty_options(self, request):
Expand Down Expand Up @@ -259,6 +258,18 @@ def test_find_config_files_disable(self, temp_home):
# make sure --no-user-cfg disables the user cfg file
assert len(all_files) - 1 == len(files)

@pytest.mark.skipif(
'platform.system() == "Windows"',
reason='Windows does not honor chmod 000',
)
def test_find_config_files_permission_error(self, fake_home):
"""
Finding config files should not fail when directory is inaccessible.
"""
fake_home.joinpath(pydistutils_cfg).write_text('')
fake_home.chmod(0o000)
Distribution().find_config_files()


@pytest.mark.usefixtures('save_env')
@pytest.mark.usefixtures('save_argv')
Expand Down

0 comments on commit aea5615

Please sign in to comment.