diff --git a/setuptools/__init__.py b/setuptools/__init__.py index 4f5c01708a..82c8d0179f 100644 --- a/setuptools/__init__.py +++ b/setuptools/__init__.py @@ -110,11 +110,12 @@ def _fetch_build_eggs(dist: Distribution): raise -def setup(**attrs): +def setup(**attrs) -> Distribution: logging.configure() # Make sure we have any requirements needed to interpret 'attrs'. _install_setup_requires(attrs) - return distutils.core.setup(**attrs) + # Override return type of distutils.core.Distribution with setuptools.dist.Distribution + return distutils.core.setup(**attrs) # type: ignore[return-value] setup.__doc__ = distutils.core.setup.__doc__ @@ -216,14 +217,14 @@ def ensure_string_list(self, option: str) -> None: @overload def reinitialize_command( self, command: str, reinit_subcommands: bool = False, **kw - ) -> _Command: ... + ) -> Command: ... # override distutils.cmd.Command with setuptools.Command @overload def reinitialize_command( self, command: _CommandT, reinit_subcommands: bool = False, **kw ) -> _CommandT: ... def reinitialize_command( self, command: str | _Command, reinit_subcommands: bool = False, **kw - ) -> _Command: + ) -> Command | _Command: cmd = _Command.reinitialize_command(self, command, reinit_subcommands) vars(cmd).update(kw) return cmd # pyright: ignore[reportReturnType] # pypa/distutils#307 diff --git a/setuptools/build_meta.py b/setuptools/build_meta.py index 00fa5e1f70..3b209d6c2f 100644 --- a/setuptools/build_meta.py +++ b/setuptools/build_meta.py @@ -39,7 +39,7 @@ import warnings from collections.abc import Iterable, Iterator, Mapping from pathlib import Path -from typing import TYPE_CHECKING, Union +from typing import TYPE_CHECKING, NoReturn, Union import setuptools @@ -77,14 +77,14 @@ def __init__(self, specifiers) -> None: class Distribution(setuptools.dist.Distribution): - def fetch_build_eggs(self, specifiers): + def fetch_build_eggs(self, specifiers) -> NoReturn: specifier_list = list(parse_strings(specifiers)) raise SetupRequirementsError(specifier_list) @classmethod @contextlib.contextmanager - def patch(cls): + def patch(cls) -> Iterator[None]: """ Replace distutils.dist.Distribution with this class @@ -307,7 +307,7 @@ def _get_build_requires( return requirements - def run_setup(self, setup_script: str = 'setup.py'): + def run_setup(self, setup_script: str = 'setup.py') -> None: # Note that we can reuse our build directory between calls # Correctness comes first, then optimization later __file__ = os.path.abspath(setup_script) @@ -330,10 +330,14 @@ def run_setup(self, setup_script: str = 'setup.py'): "setup-py-deprecated.html", ) - def get_requires_for_build_wheel(self, config_settings: _ConfigSettings = None): + def get_requires_for_build_wheel( + self, config_settings: _ConfigSettings = None + ) -> list[str]: return self._get_build_requires(config_settings, requirements=[]) - def get_requires_for_build_sdist(self, config_settings: _ConfigSettings = None): + def get_requires_for_build_sdist( + self, config_settings: _ConfigSettings = None + ) -> list[str]: return self._get_build_requires(config_settings, requirements=[]) def _bubble_up_info_directory( @@ -364,7 +368,7 @@ def _find_info_directory(self, metadata_directory: StrPath, suffix: str) -> Path def prepare_metadata_for_build_wheel( self, metadata_directory: StrPath, config_settings: _ConfigSettings = None - ): + ) -> str: sys.argv = [ *sys.argv[:1], *self._global_args(config_settings), @@ -420,7 +424,7 @@ def build_wheel( wheel_directory: StrPath, config_settings: _ConfigSettings = None, metadata_directory: StrPath | None = None, - ): + ) -> str: def _build(cmd: list[str]): with suppress_known_deprecation(): return self._build_with_temp_dir( @@ -445,7 +449,7 @@ def _build(cmd: list[str]): def build_sdist( self, sdist_directory: StrPath, config_settings: _ConfigSettings = None - ): + ) -> str: return self._build_with_temp_dir( ['sdist', '--formats', 'gztar'], '.tar.gz', sdist_directory, config_settings ) @@ -467,7 +471,7 @@ def build_editable( wheel_directory: StrPath, config_settings: _ConfigSettings = None, metadata_directory: StrPath | None = None, - ): + ) -> str: # XXX can or should we hide our editable_wheel command normally? info_dir = self._get_dist_info_dir(metadata_directory) opts = ["--dist-info-dir", info_dir] if info_dir else [] @@ -479,12 +483,12 @@ def build_editable( def get_requires_for_build_editable( self, config_settings: _ConfigSettings = None - ): + ) -> list[str]: return self.get_requires_for_build_wheel(config_settings) def prepare_metadata_for_build_editable( self, metadata_directory: StrPath, config_settings: _ConfigSettings = None - ): + ) -> str: return self.prepare_metadata_for_build_wheel( metadata_directory, config_settings ) @@ -502,7 +506,7 @@ class _BuildMetaLegacyBackend(_BuildMetaBackend): and will eventually be removed. """ - def run_setup(self, setup_script: str = 'setup.py'): + def run_setup(self, setup_script: str = 'setup.py') -> None: # In order to maintain compatibility with scripts assuming that # the setup.py script is in a directory on the PYTHONPATH, inject # '' into sys.path. (pypa/setuptools#1642) diff --git a/setuptools/command/bdist_egg.py b/setuptools/command/bdist_egg.py index ac3e6ef1f9..e320205289 100644 --- a/setuptools/command/bdist_egg.py +++ b/setuptools/command/bdist_egg.py @@ -9,19 +9,21 @@ import re import sys import textwrap +from collections.abc import Iterator from sysconfig import get_path, get_python_version from types import CodeType -from typing import TYPE_CHECKING, Literal +from typing import TYPE_CHECKING, AnyStr, Literal from setuptools import Command from setuptools.extension import Library -from .._path import StrPathT, ensure_directory +from .._path import StrPath, StrPathT, ensure_directory from distutils import log from distutils.dir_util import mkpath, remove_tree if TYPE_CHECKING: + from _typeshed import GenericPath from typing_extensions import TypeAlias # Same as zipfile._ZipFileMode from typeshed @@ -40,7 +42,9 @@ def strip_module(filename): return filename -def sorted_walk(dir): +def sorted_walk( + dir: GenericPath[AnyStr], +) -> Iterator[tuple[AnyStr, list[AnyStr], list[AnyStr]]]: """Do os.walk in a reproducible way, independent of indeterministic filesystem readdir order """ @@ -163,7 +167,7 @@ def call_command(self, cmdname, **kw): self.run_command(cmdname) return cmd - def run(self): # noqa: C901 # is too complex (14) # FIXME + def run(self) -> None: # noqa: C901 # is too complex (14) # FIXME # Generate metadata first self.run_command("egg_info") # We run install_lib before install_data, because some data hacks @@ -234,7 +238,7 @@ def run(self): # noqa: C901 # is too complex (14) # FIXME self.egg_output, archive_root, verbose=self.verbose, - dry_run=self.dry_run, + dry_run=self.dry_run, # type: ignore[arg-type] # Is an actual boolean in vendored _distutils mode=self.gen_header(), ) if not self.keep_temp: @@ -247,7 +251,7 @@ def run(self): # noqa: C901 # is too complex (14) # FIXME self.egg_output, )) - def zap_pyfiles(self): + def zap_pyfiles(self) -> None: log.info("Removing .py files from temporary directory") for base, dirs, files in walk_egg(self.bdist_dir): for name in files: @@ -262,6 +266,8 @@ def zap_pyfiles(self): pattern = r'(?P.+)\.(?P[^.]+)\.pyc' m = re.match(pattern, name) + # We shouldn't find any non-pyc files in __pycache__ + assert m is not None path_new = os.path.join(base, os.pardir, m.group('name') + '.pyc') log.info("Renaming file from [%s] to [%s]" % (path_old, path_new)) try: @@ -325,7 +331,7 @@ def get_ext_outputs(self): NATIVE_EXTENSIONS: dict[str, None] = dict.fromkeys('.dll .so .dylib .pyd'.split()) -def walk_egg(egg_dir): +def walk_egg(egg_dir: StrPath) -> Iterator[tuple[str, list[str], list[str]]]: """Walk an unpacked egg's contents, skipping the metadata directory""" walker = sorted_walk(egg_dir) base, dirs, files = next(walker) @@ -411,7 +417,7 @@ def scan_module(egg_dir, base, name, stubs): return safe -def iter_symbols(code): +def iter_symbols(code: CodeType) -> Iterator[str]: """Yield names and strings used by `code` and its nested code objects""" yield from code.co_names for const in code.co_consts: diff --git a/setuptools/command/build_ext.py b/setuptools/command/build_ext.py index e5c6b76b38..39ae3594b1 100644 --- a/setuptools/command/build_ext.py +++ b/setuptools/command/build_ext.py @@ -93,7 +93,7 @@ class build_ext(_build_ext): editable_mode = False inplace = False - def run(self): + def run(self) -> None: """Build extensions in build directory, then copy if --inplace""" old_inplace, self.inplace = self.inplace, False _build_ext.run(self) @@ -223,7 +223,7 @@ def finalize_options(self) -> None: if self.editable_mode: self.inplace = True - def setup_shlib_compiler(self): + def setup_shlib_compiler(self) -> None: compiler = self.shlib_compiler = new_compiler( compiler=self.compiler, dry_run=self.dry_run, force=self.force ) diff --git a/setuptools/command/build_py.py b/setuptools/command/build_py.py index e7d60c6440..a09c222e48 100644 --- a/setuptools/command/build_py.py +++ b/setuptools/command/build_py.py @@ -41,7 +41,7 @@ class build_py(orig.build_py): editable_mode: bool = False existing_egg_info_dir: StrPath | None = None #: Private API, internal use only. - def finalize_options(self): + def finalize_options(self) -> None: orig.build_py.finalize_options(self) self.package_data = self.distribution.package_data self.exclude_package_data = self.distribution.exclude_package_data or {} @@ -93,7 +93,7 @@ def _get_data_files(self): self.analyze_manifest() return list(map(self._get_pkg_data_files, self.packages or ())) - def get_data_files_without_manifest(self): + def get_data_files_without_manifest(self) -> list[tuple[str, str, str, list[str]]]: """ Generate list of ``(package,src_dir,build_dir,filenames)`` tuples, but without triggering any attempt to analyze or build the manifest. @@ -103,7 +103,7 @@ def get_data_files_without_manifest(self): self.__dict__.setdefault('manifest_files', {}) return list(map(self._get_pkg_data_files, self.packages or ())) - def _get_pkg_data_files(self, package): + def _get_pkg_data_files(self, package: str) -> tuple[str, str, str, list[str]]: # Locate package source directory src_dir = self.get_package_dir(package) @@ -272,7 +272,7 @@ def initialize_options(self): self.editable_mode = False self.existing_egg_info_dir = None - def get_package_dir(self, package): + def get_package_dir(self, package: str) -> str: res = orig.build_py.get_package_dir(self, package) if self.distribution.src_root is not None: return os.path.join(self.distribution.src_root, res) diff --git a/setuptools/command/develop.py b/setuptools/command/develop.py index 7eee29d491..777309e0a4 100644 --- a/setuptools/command/develop.py +++ b/setuptools/command/develop.py @@ -26,7 +26,7 @@ class develop(namespaces.DevelopInstaller, easy_install): command_consumes_arguments = False # override base - def run(self): + def run(self) -> None: # type: ignore[override] # Not including easy_install's show_deprecation argument if self.uninstall: self.multi_version = True self.uninstall_link() diff --git a/setuptools/command/easy_install.py b/setuptools/command/easy_install.py index 66fe68f7a9..bd393d3697 100644 --- a/setuptools/command/easy_install.py +++ b/setuptools/command/easy_install.py @@ -747,12 +747,15 @@ def install_item( return dist return None - def select_scheme(self, name): + def select_scheme(self, name) -> None: try: install._select_scheme(self, name) except AttributeError: # stdlib distutils - install.install.select_scheme(self, name.replace('posix', 'unix')) + install.install.select_scheme( + self, # type: ignore[arg-type] # Pretend it's the correct type for stdlib compatibility + name.replace('posix', 'unix'), + ) # FIXME: 'easy_install.process_distribution' is too complex (12) def process_distribution( # noqa: C901 diff --git a/setuptools/command/egg_info.py b/setuptools/command/egg_info.py index a300356d33..48346394c0 100644 --- a/setuptools/command/egg_info.py +++ b/setuptools/command/egg_info.py @@ -2,6 +2,8 @@ Create a distribution's .egg-info directory and contents""" +from __future__ import annotations + import functools import os import re @@ -196,11 +198,11 @@ def initialize_options(self): # allow the 'tag_svn_revision' to be detected and # set, supporting sdists built on older Setuptools. @property - def tag_svn_revision(self) -> None: + def tag_svn_revision(self) -> int | None: pass @tag_svn_revision.setter - def tag_svn_revision(self, value): + def tag_svn_revision(self, value) -> None: pass #################################### diff --git a/setuptools/command/sdist.py b/setuptools/command/sdist.py index 64e866c96b..43e935f5bb 100644 --- a/setuptools/command/sdist.py +++ b/setuptools/command/sdist.py @@ -3,6 +3,7 @@ import contextlib import os import re +from collections.abc import Iterator from itertools import chain from typing import ClassVar @@ -16,7 +17,7 @@ _default_revctrl = list -def walk_revctrl(dirname=''): +def walk_revctrl(dirname='') -> Iterator: """Find all files under revision control""" for ep in metadata.entry_points(group='setuptools.file_finders'): yield from ep.load()(dirname) @@ -195,7 +196,7 @@ def _manifest_is_not_generated(self): first_line = fp.readline() return first_line != b'# file GENERATED by distutils, do NOT edit\n' - def read_manifest(self): + def read_manifest(self) -> None: """Read the manifest file (named by 'self.manifest') and use it to fill in 'self.filelist', the list of files to include in the source distribution. diff --git a/setuptools/command/setopt.py b/setuptools/command/setopt.py index 200cdff0f7..62e670e431 100644 --- a/setuptools/command/setopt.py +++ b/setuptools/command/setopt.py @@ -27,7 +27,7 @@ def config_file(kind="local"): raise ValueError("config_file() type must be 'local', 'global', or 'user'", kind) -def edit_config(filename, settings, dry_run=False): +def edit_config(filename, settings, dry_run=False) -> None: """Edit a configuration file to include `settings` `settings` is a dictionary of dictionaries or ``None`` values, keyed by @@ -88,7 +88,7 @@ def initialize_options(self): self.user_config = None self.filename = None - def finalize_options(self): + def finalize_options(self) -> None: filenames = [] if self.global_config: filenames.append(config_file('global')) diff --git a/setuptools/command/test.py b/setuptools/command/test.py index 341b11a20e..5d03c91102 100644 --- a/setuptools/command/test.py +++ b/setuptools/command/test.py @@ -1,5 +1,7 @@ from __future__ import annotations +from typing import NoReturn + from setuptools import Command from setuptools.warnings import SetuptoolsDeprecationWarning @@ -35,11 +37,11 @@ class _test(Command): ('test-runner=', 'r', "Test runner to use"), ] - def initialize_options(self): + def initialize_options(self) -> None: pass - def finalize_options(self): + def finalize_options(self) -> None: pass - def run(self): + def run(self) -> NoReturn: raise RuntimeError("Support for the test command was removed in Setuptools 72") diff --git a/setuptools/config/expand.py b/setuptools/config/expand.py index 54c68bed4f..1c48961fd5 100644 --- a/setuptools/config/expand.py +++ b/setuptools/config/expand.py @@ -387,7 +387,7 @@ def __init__(self, distribution: Distribution) -> None: self._dist = distribution self._called = False - def __call__(self): + def __call__(self) -> None: """Trigger the automatic package discovery, if it is still necessary.""" if not self._called: self._called = True @@ -401,7 +401,7 @@ def __exit__( exc_type: type[BaseException] | None, exc_value: BaseException | None, traceback: TracebackType | None, - ): + ) -> None: if self._called: self._dist.set_defaults.analyse_name() # Now we can set a default name @@ -411,7 +411,7 @@ def _get_package_dir(self) -> Mapping[str, str]: return {} if pkg_dir is None else pkg_dir @property - def package_dir(self) -> Mapping[str, str]: + def package_dir(self) -> LazyMappingProxy[str, str]: """Proxy to ``package_dir`` that may trigger auto-discovery when used.""" return LazyMappingProxy(self._get_package_dir) diff --git a/setuptools/config/setupcfg.py b/setuptools/config/setupcfg.py index b35d0b00cd..1a6830dda4 100644 --- a/setuptools/config/setupcfg.py +++ b/setuptools/config/setupcfg.py @@ -14,6 +14,7 @@ import contextlib import functools import os +from abc import abstractmethod from collections import defaultdict from collections.abc import Iterable, Iterator from functools import partial, wraps @@ -269,7 +270,8 @@ def _section_options( yield name.lstrip('.'), value @property - def parsers(self): + @abstractmethod + def parsers(self) -> dict[str, Callable]: """Metadata item name to parser function mapping.""" raise NotImplementedError( '%s must provide .parsers property' % self.__class__.__name__ @@ -546,7 +548,7 @@ def __init__( self.root_dir = root_dir @property - def parsers(self): + def parsers(self) -> dict[str, Callable]: """Metadata item name to parser function mapping.""" parse_list = self._parse_list parse_file = partial(self._parse_file, root_dir=self.root_dir) @@ -623,7 +625,7 @@ def _parse_requirements_list(self, label: str, value: str): return [line for line in parsed if not line.startswith("#")] @property - def parsers(self): + def parsers(self) -> dict[str, Callable]: """Metadata item name to parser function mapping.""" parse_list = self._parse_list parse_bool = self._parse_bool diff --git a/setuptools/dist.py b/setuptools/dist.py index 5b3175fb5b..694fe4a56b 100644 --- a/setuptools/dist.py +++ b/setuptools/dist.py @@ -6,7 +6,7 @@ import os import re import sys -from collections.abc import Iterable, MutableMapping, Sequence +from collections.abc import Iterable, Iterator, MutableMapping, Sequence from glob import iglob from pathlib import Path from typing import TYPE_CHECKING, Any, Union @@ -696,7 +696,7 @@ def _finalize_setup_keywords(self): if value is not None: ep.load()(self, ep.name, value) - def get_egg_cache_dir(self): + def get_egg_cache_dir(self) -> str: from . import windows_support egg_cache_dir = os.path.join(os.curdir, '.eggs') @@ -943,7 +943,7 @@ def get_cmdline_options(self) -> dict[str, dict[str, str | None]]: return d - def iter_distribution_names(self): + def iter_distribution_names(self) -> Iterator[str]: """Yield all packages, modules, and extension names in distribution""" yield from self.packages or () diff --git a/setuptools/extension.py b/setuptools/extension.py index 76e03d9d6b..98e819a4ae 100644 --- a/setuptools/extension.py +++ b/setuptools/extension.py @@ -13,7 +13,7 @@ import distutils.extension -def _have_cython(): +def _have_cython() -> bool: """ Return True if Cython can be imported. """ diff --git a/setuptools/monkey.py b/setuptools/monkey.py index d8e30dbb80..0e780b7fee 100644 --- a/setuptools/monkey.py +++ b/setuptools/monkey.py @@ -69,7 +69,7 @@ def get_unpatched_class(cls: type[_T]) -> type[_T]: return base -def patch_all(): +def patch_all() -> None: import setuptools # we can't patch distutils.cmd, alas @@ -105,7 +105,7 @@ def _patch_distribution_metadata(): setattr(distutils.dist.DistributionMetadata, attr, new_val) -def patch_func(replacement, target_mod, func_name): +def patch_func(replacement, target_mod, func_name) -> None: """ Patch func_name in target_mod with replacement diff --git a/setuptools/msvc.py b/setuptools/msvc.py index 8d6d2cf084..d2bf10cc75 100644 --- a/setuptools/msvc.py +++ b/setuptools/msvc.py @@ -13,7 +13,7 @@ import os import os.path import platform -from typing import TYPE_CHECKING, TypedDict +from typing import TYPE_CHECKING, TypedDict, overload from more_itertools import unique_everseen @@ -50,11 +50,11 @@ class PlatformInfo: current_cpu = environ.get('processor_architecture', '').lower() - def __init__(self, arch) -> None: + def __init__(self, arch: str) -> None: self.arch = arch.lower().replace('x64', 'amd64') @property - def target_cpu(self): + def target_cpu(self) -> str: """ Return Target CPU architecture. @@ -65,7 +65,7 @@ def target_cpu(self): """ return self.arch[self.arch.find('_') + 1 :] - def target_is_x86(self): + def target_is_x86(self) -> bool: """ Return True if target CPU is x86 32 bits.. @@ -76,7 +76,7 @@ def target_is_x86(self): """ return self.target_cpu == 'x86' - def current_is_x86(self): + def current_is_x86(self) -> bool: """ Return True if current CPU is x86 32 bits.. @@ -135,7 +135,7 @@ def target_dir(self, hidex86=False, x64=False) -> str: else r'\%s' % self.target_cpu ) - def cross_dir(self, forcex86=False): + def cross_dir(self, forcex86=False) -> str: r""" Cross platform specific subfolder. @@ -180,7 +180,7 @@ def __init__(self, platform_info) -> None: self.pi = platform_info @property - def visualstudio(self) -> str: + def visualstudio(self) -> LiteralString: """ Microsoft Visual Studio root registry key. @@ -192,7 +192,7 @@ def visualstudio(self) -> str: return 'VisualStudio' @property - def sxs(self): + def sxs(self) -> LiteralString: """ Microsoft Visual Studio SxS registry key. @@ -204,7 +204,7 @@ def sxs(self): return os.path.join(self.visualstudio, 'SxS') @property - def vc(self): + def vc(self) -> LiteralString: """ Microsoft Visual C++ VC7 registry key. @@ -216,7 +216,7 @@ def vc(self): return os.path.join(self.sxs, 'VC7') @property - def vs(self): + def vs(self) -> LiteralString: """ Microsoft Visual Studio VS7 registry key. @@ -228,7 +228,7 @@ def vs(self): return os.path.join(self.sxs, 'VS7') @property - def vc_for_python(self) -> str: + def vc_for_python(self) -> LiteralString: """ Microsoft Visual C++ for Python registry key. @@ -240,7 +240,7 @@ def vc_for_python(self) -> str: return r'DevDiv\VCForPython' @property - def microsoft_sdk(self) -> str: + def microsoft_sdk(self) -> LiteralString: """ Microsoft SDK registry key. @@ -252,7 +252,7 @@ def microsoft_sdk(self) -> str: return 'Microsoft SDKs' @property - def windows_sdk(self): + def windows_sdk(self) -> LiteralString: """ Microsoft Windows/Platform SDK registry key. @@ -264,7 +264,7 @@ def windows_sdk(self): return os.path.join(self.microsoft_sdk, 'Windows') @property - def netfx_sdk(self): + def netfx_sdk(self) -> LiteralString: """ Microsoft .NET Framework SDK registry key. @@ -276,7 +276,7 @@ def netfx_sdk(self): return os.path.join(self.microsoft_sdk, 'NETFXSDK') @property - def windows_kits_roots(self) -> str: + def windows_kits_roots(self) -> LiteralString: """ Microsoft Windows Kits Roots registry key. @@ -287,7 +287,11 @@ def windows_kits_roots(self) -> str: """ return r'Windows Kits\Installed Roots' - def microsoft(self, key, x86=False): + @overload + def microsoft(self, key: LiteralString, x86: bool = False) -> LiteralString: ... + @overload + def microsoft(self, key: str, x86: bool = False) -> str: ... # type: ignore[misc] + def microsoft(self, key: str, x86: bool = False) -> str: """ Return key in Microsoft software registry. @@ -306,7 +310,7 @@ def microsoft(self, key, x86=False): node64 = '' if self.pi.current_is_x86() or x86 else 'Wow6432Node' return os.path.join('Software', node64, 'Microsoft', key) - def lookup(self, key, name): + def lookup(self, key: str, name: str) -> str | None: """ Look for values in registry in Microsoft software registry. @@ -366,7 +370,9 @@ class SystemInfo: ProgramFiles = environ.get('ProgramFiles', '') ProgramFilesx86 = environ.get('ProgramFiles(x86)', ProgramFiles) - def __init__(self, registry_info, vc_ver=None) -> None: + def __init__( + self, registry_info: RegistryInfo, vc_ver: float | None = None + ) -> None: self.ri = registry_info self.pi = self.ri.pi @@ -395,7 +401,7 @@ def _find_latest_available_vs_ver(self): vc_vers.update(self.known_vs_paths) return sorted(vc_vers)[-1] - def find_reg_vs_vers(self): + def find_reg_vs_vers(self) -> list[float]: """ Find Microsoft Visual Studio versions available in registry. @@ -486,7 +492,7 @@ def _as_float_version(version): return float('.'.join(version.split('.')[:2])) @property - def VSInstallDir(self): + def VSInstallDir(self) -> str: """ Microsoft Visual Studio directory. @@ -504,7 +510,7 @@ def VSInstallDir(self): return self.ri.lookup(self.ri.vs, '%0.1f' % self.vs_ver) or default @property - def VCInstallDir(self): + def VCInstallDir(self) -> str: """ Microsoft Visual C++ directory. @@ -595,7 +601,7 @@ def WindowsSdkVersion(self) -> tuple[LiteralString, ...]: return () @property - def WindowsSdkLastVersion(self): + def WindowsSdkLastVersion(self) -> str: """ Microsoft Windows SDK last version. @@ -607,7 +613,7 @@ def WindowsSdkLastVersion(self): return self._use_last_dir_name(os.path.join(self.WindowsSdkDir, 'lib')) @property - def WindowsSdkDir(self) -> str | None: # noqa: C901 # is too complex (12) # FIXME + def WindowsSdkDir(self) -> str: # noqa: C901 # is too complex (12) # FIXME """ Microsoft Windows SDK directory. @@ -650,7 +656,7 @@ def WindowsSdkDir(self) -> str | None: # noqa: C901 # is too complex (12) # F return sdkdir @property - def WindowsSDKExecutablePath(self): + def WindowsSDKExecutablePath(self) -> str | None: """ Microsoft Windows SDK executable directory. @@ -687,7 +693,7 @@ def WindowsSDKExecutablePath(self): return None @property - def FSharpInstallDir(self): + def FSharpInstallDir(self) -> str: """ Microsoft Visual F# directory. @@ -700,7 +706,7 @@ def FSharpInstallDir(self): return self.ri.lookup(path, 'productdir') or '' @property - def UniversalCRTSdkDir(self): + def UniversalCRTSdkDir(self) -> str | None: """ Microsoft Universal CRT SDK directory. @@ -721,7 +727,7 @@ def UniversalCRTSdkDir(self): return None @property - def UniversalCRTSdkLastVersion(self): + def UniversalCRTSdkLastVersion(self) -> str: """ Microsoft Universal C Runtime SDK last version. @@ -733,7 +739,7 @@ def UniversalCRTSdkLastVersion(self): return self._use_last_dir_name(os.path.join(self.UniversalCRTSdkDir, 'lib')) @property - def NetFxSdkVersion(self): + def NetFxSdkVersion(self) -> tuple[LiteralString, ...]: """ Microsoft .NET Framework SDK versions. @@ -750,7 +756,7 @@ def NetFxSdkVersion(self): ) @property - def NetFxSdkDir(self): + def NetFxSdkDir(self) -> str | None: """ Microsoft .NET Framework SDK directory. @@ -759,7 +765,6 @@ def NetFxSdkDir(self): str path """ - sdkdir = '' for ver in self.NetFxSdkVersion: loc = os.path.join(self.ri.netfx_sdk, ver) sdkdir = self.ri.lookup(loc, 'kitsinstallationfolder') @@ -768,7 +773,7 @@ def NetFxSdkDir(self): return sdkdir @property - def FrameworkDir32(self): + def FrameworkDir32(self) -> str: """ Microsoft .NET Framework 32bit directory. @@ -784,7 +789,7 @@ def FrameworkDir32(self): return self.ri.lookup(self.ri.vc, 'frameworkdir32') or guess_fw @property - def FrameworkDir64(self): + def FrameworkDir64(self) -> str: """ Microsoft .NET Framework 64bit directory. diff --git a/setuptools/package_index.py b/setuptools/package_index.py index 97806e8ff8..3ae0f838ca 100644 --- a/setuptools/package_index.py +++ b/setuptools/package_index.py @@ -18,6 +18,7 @@ import urllib.error import urllib.parse import urllib.request +from collections.abc import Iterator from fnmatch import translate from functools import wraps from typing import NamedTuple @@ -113,7 +114,7 @@ def egg_info_for_url(url): return base, fragment -def distros_for_url(url, metadata=None): +def distros_for_url(url, metadata=None) -> Iterator[Distribution]: """Yield egg or source distribution objects that might be found at a URL""" base, fragment = egg_info_for_url(url) yield from distros_for_location(url, base, metadata) @@ -125,7 +126,9 @@ def distros_for_url(url, metadata=None): ) -def distros_for_location(location, basename, metadata=None): +def distros_for_location( + location, basename, metadata=None +) -> list[Distribution] | Iterator[Distribution]: """Yield egg or source distribution objects based on basename""" if basename.endswith('.egg.zip'): basename = basename[:-4] # strip the .zip @@ -169,7 +172,7 @@ def distros_for_filename(filename, metadata=None): def interpret_distro_name( location, basename, metadata, py_version=None, precedence=SOURCE_DIST, platform=None -): +) -> Iterator[Distribution]: """Generate the interpretation of a source distro name Note: if `location` is a filesystem filename, you should call @@ -244,7 +247,7 @@ class ContentChecker: A null content checker that defines the interface for checking content """ - def feed(self, block): + def feed(self, block) -> None: """ Feed a block of data to the hash. """ @@ -256,7 +259,7 @@ def is_valid(self): """ return True - def report(self, reporter, template): + def report(self, reporter, template) -> None: """ Call reporter with information about the checker (hash name) substituted into the template. @@ -286,7 +289,7 @@ def from_url(cls, url): return ContentChecker() return cls(**match.groupdict()) - def feed(self, block): + def feed(self, block) -> None: self.hash.update(block) def is_valid(self): @@ -1017,7 +1020,7 @@ def __str__(self) -> str: class PyPIConfig(configparser.RawConfigParser): - def __init__(self): + def __init__(self) -> None: """ Load from ~/.pypirc """ diff --git a/setuptools/sandbox.py b/setuptools/sandbox.py index 2d84242d66..88271cfc94 100644 --- a/setuptools/sandbox.py +++ b/setuptools/sandbox.py @@ -144,7 +144,7 @@ def __exit__( # suppress the exception return True - def resume(self): + def resume(self) -> None: "restore and re-raise any exception" if '_saved' not in vars(self): @@ -300,7 +300,7 @@ def __exit__( exc_type: type[BaseException] | None, exc_value: BaseException | None, traceback: TracebackType | None, - ): + ) -> None: self._active = False builtins.open = _open self._copy(_os) diff --git a/setuptools/wheel.py b/setuptools/wheel.py index fb19f1a65a..9dac318da3 100644 --- a/setuptools/wheel.py +++ b/setuptools/wheel.py @@ -8,6 +8,7 @@ import posixpath import re import zipfile +from collections.abc import Iterator from packaging.tags import sys_tags from packaging.utils import canonicalize_name @@ -62,7 +63,7 @@ def unpack(src_dir, dst_dir) -> None: @contextlib.contextmanager -def disable_info_traces(): +def disable_info_traces() -> Iterator[None]: """ Temporarily disable info traces. """