diff --git a/conftest.py b/conftest.py index 8dcf7e6805..749f4737fb 100644 --- a/conftest.py +++ b/conftest.py @@ -42,10 +42,7 @@ def pytest_configure(config): if sys.version_info < (3, 6): - collect_ignore.append('docs/conf.py') # uses f-strings - collect_ignore.append('pavement.py') - - + collect_ignore.extend(('docs/conf.py', 'pavement.py')) if sys.version_info < (3, 9) or sys.platform == 'cygwin': collect_ignore.append('tools/finalize.py') diff --git a/pkg_resources/__init__.py b/pkg_resources/__init__.py index 288280c78d..fe407ab7e9 100644 --- a/pkg_resources/__init__.py +++ b/pkg_resources/__init__.py @@ -145,17 +145,14 @@ def _declare_state(vartype, **kw): def __getstate__(): - state = {} g = globals() - for k, v in _state_vars.items(): - state[k] = g['_sget_' + v](g[k]) - return state + return {k: g[f'_sget_{v}'](g[k]) for k, v in _state_vars.items()} def __setstate__(state): g = globals() for k, v in state.items(): - g['_sset_' + _state_vars[k]](k, g[k], v) + g[f'_sset_{_state_vars[k]}'](k, g[k], v) return state @@ -196,7 +193,7 @@ def get_supported_platform(): m = macosVersionString.match(plat) if m is not None and sys.platform == "darwin": try: - plat = 'macosx-%s-%s' % ('.'.join(_macos_vers()[:2]), m.group(3)) + plat = f"macosx-{'.'.join(_macos_vers()[:2])}-{m.group(3)}" except ValueError: # not macOS pass @@ -359,9 +356,7 @@ def requirers(self): @property def requirers_str(self): - if not self.requirers: - return 'the application' - return ', '.join(self.requirers) + return 'the application' if not self.requirers else ', '.join(self.requirers) def report(self): return self._template.format(**locals()) @@ -467,20 +462,14 @@ def compatible_platforms(provided, required): # easy case return True - # macOS special cases - reqMac = macosVersionString.match(required) - if reqMac: + if reqMac := macosVersionString.match(required): provMac = macosVersionString.match(provided) # is this a Mac package? if not provMac: - # this is backwards compatibility for packages built before - # setuptools 0.6. All packages built after this point will - # use the new macOS designation. - provDarwin = darwinVersionString.match(provided) - if provDarwin: + if provDarwin := darwinVersionString.match(provided): dversion = int(provDarwin.group(1)) - macosversion = "%s.%s" % (reqMac.group(1), reqMac.group(2)) + macosversion = f"{reqMac.group(1)}.{reqMac.group(2)}" if ( dversion == 7 and macosversion >= "10.3" @@ -496,11 +485,7 @@ def compatible_platforms(provided, required): return False # is the required OS major update >= the provided one? - if int(provMac.group(2)) > int(reqMac.group(2)): - return False - - return True - + return int(provMac.group(2)) <= int(reqMac.group(2)) # XXX Linux and other platforms' special cases should go here return False @@ -545,53 +530,53 @@ def get_entry_info(dist, group, name): class IMetadataProvider: - def has_metadata(name): + def has_metadata(self): """Does the package's distribution contain the named metadata?""" - def get_metadata(name): + def get_metadata(self): """The named metadata resource as a string""" - def get_metadata_lines(name): + def get_metadata_lines(self): """Yield named metadata resource as list of non-blank non-comment lines Leading and trailing whitespace is stripped from each line, and lines with ``#`` as the first non-blank character are omitted.""" - def metadata_isdir(name): + def metadata_isdir(self): """Is the named metadata a directory? (like ``os.path.isdir()``)""" - def metadata_listdir(name): + def metadata_listdir(self): """List of metadata names in the directory (like ``os.listdir()``)""" - def run_script(script_name, namespace): + def run_script(self, namespace): """Execute the named script in the supplied namespace dictionary""" class IResourceProvider(IMetadataProvider): """An object that provides access to package resources""" - def get_resource_filename(manager, resource_name): + def get_resource_filename(self, resource_name): """Return a true filesystem path for `resource_name` `manager` must be an ``IResourceManager``""" - def get_resource_stream(manager, resource_name): + def get_resource_stream(self, resource_name): """Return a readable file-like object for `resource_name` `manager` must be an ``IResourceManager``""" - def get_resource_string(manager, resource_name): + def get_resource_string(self, resource_name): """Return a string containing the contents of `resource_name` `manager` must be an ``IResourceManager``""" - def has_resource(resource_name): + def has_resource(self): """Does the package contain the named resource?""" - def resource_isdir(resource_name): + def resource_isdir(self): """Is the named resource a directory? (like ``os.path.isdir()``)""" - def resource_listdir(resource_name): + def resource_listdir(self): """List of resource names in the directory (like ``os.listdir()``)""" @@ -863,9 +848,9 @@ def _resolve_dist( dist = best[req.key] = env.best_match( req, ws, installer, replace_conflicting=replace_conflicting ) - if dist is None: - requirers = required_by.get(req, None) - raise DistributionNotFound(req, requirers) + if dist is None: + requirers = required_by.get(req, None) + raise DistributionNotFound(req, requirers) to_activate.append(dist) if dist not in req: # Oops, the "best" so far conflicts with a dependency @@ -908,10 +893,7 @@ def find_plugins(self, plugin_env, full_env=None, installer=None, fallback=True) ``VersionConflict`` instance. """ - plugin_projects = list(plugin_env) - # scan project names in alphabetic order - plugin_projects.sort() - + plugin_projects = sorted(plugin_env) error_info = {} distributions = {} @@ -949,9 +931,7 @@ def find_plugins(self, plugin_env, full_env=None, installer=None, fallback=True) # success, no need to try any more versions of this project break - distributions = list(distributions) - distributions.sort() - + distributions = sorted(distributions) return distributions, error_info def require(self, *requirements): @@ -1272,7 +1252,7 @@ def get_cache_path(self, archive_name, names=()): extract, as it tracks the generated names for possible cleanup later. """ extract_path = self.extraction_path or get_default_cache() - target_path = os.path.join(extract_path, archive_name + '-tmp', *names) + target_path = os.path.join(extract_path, f'{archive_name}-tmp', *names) try: _bypass_ensure_directory(target_path) except Exception: @@ -1413,8 +1393,7 @@ def _forgiving_version(version): """ version = version.replace(' ', '.') - match = _PEP440_FALLBACK.search(version) - if match: + if match := _PEP440_FALLBACK.search(version): safe = match["safe"] rest = version[len(safe) :] else: @@ -1520,7 +1499,7 @@ def get_metadata(self, name): except UnicodeDecodeError as exc: # Include the path in the error message to simplify # troubleshooting, and without changing the exception type. - exc.reason += ' in {} file at path: {}'.format(name, path) + exc.reason += f' in {name} file at path: {path}' raise def get_metadata_lines(self, name): @@ -1536,12 +1515,10 @@ def resource_listdir(self, resource_name): return self._listdir(self._fn(self.module_path, resource_name)) def metadata_listdir(self, name): - if self.egg_info: - return self._listdir(self._fn(self.egg_info, name)) - return [] + return self._listdir(self._fn(self.egg_info, name)) if self.egg_info else [] def run_script(self, script_name, namespace): - script = 'scripts/' + script_name + script = f'scripts/{script_name}' if not self.has_metadata(script): raise ResolutionError( "Script {script!r} not found in metadata at {self.egg_info!r}".format( @@ -1586,9 +1563,7 @@ def _listdir(self, path): def _fn(self, base, resource_name): self._validate_resource_path(resource_name) - if resource_name: - return os.path.join(base, *resource_name.split('/')) - return base + return os.path.join(base, *resource_name.split('/')) if resource_name else base @staticmethod def _validate_resource_path(path): @@ -1660,7 +1635,7 @@ def _validate_resource_path(path): # for compatibility, warn; in future # raise ValueError(msg) issue_warning( - msg[:-1] + " and will raise exceptions in a future release.", + f"{msg[:-1]} and will raise exceptions in a future release.", DeprecationWarning, ) @@ -1825,7 +1800,7 @@ def _zipinfo_name(self, fspath): return '' if fspath.startswith(self.zip_pre): return fspath[len(self.zip_pre) :] - raise AssertionError("%s is not a subpath of %s" % (fspath, self.zip_pre)) + raise AssertionError(f"{fspath} is not a subpath of {self.zip_pre}") def _parts(self, zip_path): # Convert a zipfile subpath into an egg-relative path part list. @@ -1833,7 +1808,7 @@ def _parts(self, zip_path): fspath = self.zip_pre + zip_path if fspath.startswith(self.egg_root + os.sep): return fspath[len(self.egg_root) + 1 :].split(os.sep) - raise AssertionError("%s is not a subpath of %s" % (fspath, self.egg_root)) + raise AssertionError(f"{fspath} is not a subpath of {self.egg_root}") @property def zipinfo(self): @@ -2092,8 +2067,7 @@ def find_eggs_in_zip(importer, path_item, only=False): for subitem in metadata.resource_listdir(''): if _is_egg_path(subitem): subpath = os.path.join(path_item, subitem) - dists = find_eggs_in_zip(zipimport.zipimporter(subpath), subpath) - yield from dists + yield from find_eggs_in_zip(zipimport.zipimporter(subpath), subpath) elif subitem.lower().endswith(('.dist-info', '.egg-info')): subpath = os.path.join(path_item, subitem) submeta = EggMetadata(zipimport.zipimporter(subpath)) @@ -2206,8 +2180,7 @@ def non_empty_lines(path): """ with open(path) as f: for line in f: - line = line.strip() - if line: + if line := line.strip(): yield line @@ -2370,8 +2343,7 @@ def fixup_namespace_packages(path_item, parent=None): _imp.acquire_lock() try: for package in _namespace_packages.get(parent, ()): - subpath = _handle_ns(package, path_item) - if subpath: + if subpath := _handle_ns(package, path_item): fixup_namespace_packages(subpath, package) finally: _imp.release_lock() @@ -2485,11 +2457,11 @@ def __init__(self, name, module_name, attrs=(), extras=(), dist=None): self.dist = dist def __str__(self): - s = "%s = %s" % (self.name, self.module_name) + s = f"{self.name} = {self.module_name}" if self.attrs: s += ':' + '.'.join(self.attrs) if self.extras: - s += ' [%s]' % ','.join(self.extras) + s += f" [{','.join(self.extras)}]" return s def __repr__(self): @@ -2566,7 +2538,7 @@ def parse(cls, src, dist=None): def _parse_extras(cls, extras_spec): if not extras_spec: return () - req = Requirement.parse('x' + extras_spec) + req = Requirement.parse(f'x{extras_spec}') if req.specs: raise ValueError() return req.extras @@ -2587,10 +2559,7 @@ def parse_group(cls, group, lines, dist=None): @classmethod def parse_map(cls, data, dist=None): """Parse a map of entry point groups""" - if isinstance(data, dict): - data = data.items() - else: - data = split_sections(data) + data = data.items() if isinstance(data, dict) else split_sections(data) maps = {} for group, lines in data: if group is None: @@ -2650,8 +2619,7 @@ def from_location(cls, location, basename, metadata=None, **kw): if ext.lower() in _distributionImpl: cls = _distributionImpl[ext.lower()] - match = EGG_NAME(basename) - if match: + if match := EGG_NAME(basename): project_name, version, py_version, platform = match.group( 'name', 'ver', 'pyver', 'plat' ) @@ -2763,9 +2731,7 @@ def version(self): version = self._get_version() if version is None: path = self._get_metadata_path_for_display(self.PKG_INFO) - msg = ("Missing 'Version:' header and/or {} file at path: {}").format( - self.PKG_INFO, path - ) + msg = f"Missing 'Version:' header and/or {self.PKG_INFO} file at path: {path}" raise ValueError(msg, self) from e return version @@ -2793,10 +2759,9 @@ def _filter_extras(dm): new_extra = extra reqs = dm.pop(extra) new_extra, _, marker = extra.partition(':') - fails_marker = marker and ( + if fails_marker := marker and ( invalid_marker(marker) or not evaluate_marker(marker) - ) - if fails_marker: + ): reqs = [] new_extra = safe_extra(new_extra) or None @@ -2847,9 +2812,7 @@ def _get_metadata(self, name): def _get_version(self): lines = self._get_metadata(self.PKG_INFO) - version = _version_from_file(lines) - - return version + return _version_from_file(lines) def activate(self, path=None, replace=False): """Ensure distribution is importable on `path` (default=sys.path)""" @@ -2864,21 +2827,14 @@ def activate(self, path=None, replace=False): def egg_name(self): """Return what this distribution's standard .egg filename should be""" - filename = "%s-%s-py%s" % ( - to_filename(self.project_name), - to_filename(self.version), - self.py_version or PY_MAJOR, - ) + filename = f"{to_filename(self.project_name)}-{to_filename(self.version)}-py{self.py_version or PY_MAJOR}" if self.platform: - filename += '-' + self.platform + filename += f'-{self.platform}' return filename def __repr__(self): - if self.location: - return "%s (%s)" % (self, self.location) - else: - return str(self) + return f"{self} ({self.location})" if self.location else str(self) def __str__(self): try: @@ -2886,7 +2842,7 @@ def __str__(self): except ValueError: version = None version = version or "[unknown version]" - return "%s %s" % (self.project_name, version) + return f"{self.project_name} {version}" def __getattr__(self, attr): """Delegate all unrecognized public attributes to .metadata provider""" @@ -2896,8 +2852,14 @@ def __getattr__(self, attr): def __dir__(self): return list( - set(super().__dir__()) - | set(attr for attr in self._provider.__dir__() if not attr.startswith('_')) + ( + set(super().__dir__()) + | { + attr + for attr in self._provider.__dir__() + if not attr.startswith('_') + } + ) ) @classmethod @@ -2909,9 +2871,9 @@ def from_filename(cls, filename, metadata=None, **kw): def as_requirement(self): """Return a ``Requirement`` that matches this distribution exactly""" if isinstance(self.parsed_version, packaging.version.Version): - spec = "%s==%s" % (self.project_name, self.parsed_version) + spec = f"{self.project_name}=={self.parsed_version}" else: - spec = "%s===%s" % (self.project_name, self.parsed_version) + spec = f"{self.project_name}==={self.parsed_version}" return Requirement.parse(spec) @@ -2930,9 +2892,7 @@ def get_entry_map(self, group=None): ep_map = self._ep_map = EntryPoint.parse_map( self._get_metadata('entry_points.txt'), self ) - if group is not None: - return ep_map.get(group, {}) - return ep_map + return ep_map.get(group, {}) if group is not None else ep_map def get_entry_info(self, group, name): """Return the EntryPoint object for `group`+`name`, or ``None``""" @@ -3037,7 +2997,7 @@ def has_version(self): try: self.version except ValueError: - issue_warning("Unbuilt egg for " + repr(self)) + issue_warning(f"Unbuilt egg for {repr(self)}") return False except SystemError: # TODO: remove this except clause when python/cpython#103632 is fixed. @@ -3070,8 +3030,7 @@ def _reload_version(self): take an extra step and try to get the version number from the metadata file itself instead of the filename. """ - md_version = self._get_version() - if md_version: + if md_version := self._get_version(): self._version = md_version return self @@ -3213,9 +3172,7 @@ def _always_object(classes): Ensure object appears in the mro even for old-style classes. """ - if object not in classes: - return classes + (object,) - return classes + return classes + (object,) if object not in classes else classes def _find_adapter(registry, ob): @@ -3257,13 +3214,12 @@ def split_sections(s): content = [] for line in yield_lines(s): if line.startswith("["): - if line.endswith("]"): - if section or content: - yield section, content - section = line[1:-1].strip() - content = [] - else: + if not line.endswith("]"): raise ValueError("Invalid section heading", line) + if section or content: + yield section, content + section = line[1:-1].strip() + content = [] else: content.append(line) diff --git a/pkg_resources/_vendor/importlib_resources/_adapters.py b/pkg_resources/_vendor/importlib_resources/_adapters.py index ea363d86a5..30bd38a8eb 100644 --- a/pkg_resources/_vendor/importlib_resources/_adapters.py +++ b/pkg_resources/_vendor/importlib_resources/_adapters.py @@ -35,7 +35,7 @@ def _io_wrapper(file, mode='r', *args, **kwargs): elif mode == 'rb': return file raise ValueError( - "Invalid mode value '{}', only 'r' and 'rb' are supported".format(mode) + f"Invalid mode value '{mode}', only 'r' and 'rb' are supported" ) @@ -118,7 +118,7 @@ class OrphanPath(abc.Traversable): """ def __init__(self, *path_parts): - if len(path_parts) < 1: + if not path_parts: raise ValueError('Need at least one path part to construct a path') self._path = path_parts diff --git a/pkg_resources/_vendor/importlib_resources/_common.py b/pkg_resources/_vendor/importlib_resources/_common.py index 3c6de1cfb2..01bf48ae53 100644 --- a/pkg_resources/_vendor/importlib_resources/_common.py +++ b/pkg_resources/_vendor/importlib_resources/_common.py @@ -67,9 +67,7 @@ def get_resource_reader(package: types.ModuleType) -> Optional[ResourceReader]: # TypeError. That seems terrible. spec = package.__spec__ reader = getattr(spec.loader, 'get_resource_reader', None) # type: ignore - if reader is None: - return None - return reader(spec.name) # type: ignore + return None if reader is None else reader(spec.name) @functools.singledispatch @@ -135,10 +133,8 @@ def _tempfile( del reader yield pathlib.Path(raw_path) finally: - try: + with contextlib.suppress(FileNotFoundError): _os_remove(raw_path) - except FileNotFoundError: - pass def _temp_file(path): diff --git a/pkg_resources/_vendor/jaraco/functools.py b/pkg_resources/_vendor/jaraco/functools.py index 67aeadc353..33128a4047 100644 --- a/pkg_resources/_vendor/jaraco/functools.py +++ b/pkg_resources/_vendor/jaraco/functools.py @@ -204,7 +204,7 @@ def _special_method_cache(method, cache_wrapper): if name not in special_names: return - wrapper_name = '__cached' + name + wrapper_name = f'__cached{name}' def proxy(self, *args, **kwargs): if wrapper_name not in vars(self): @@ -369,7 +369,7 @@ def retry_call(func, cleanup=lambda: None, retries=0, trap=()): to propagate. """ attempts = itertools.count() if retries == float('inf') else range(retries) - for attempt in attempts: + for _ in attempts: try: return func() except trap: @@ -508,7 +508,7 @@ def save_method_args(method): @functools.wraps(method) def wrapper(self, *args, **kwargs): - attr_name = '_saved_' + method.__name__ + attr_name = f'_saved_{method.__name__}' attr = args_and_kwargs(args, kwargs) setattr(self, attr_name, attr) return method(self, *args, **kwargs) diff --git a/pkg_resources/_vendor/more_itertools/more.py b/pkg_resources/_vendor/more_itertools/more.py index e0e2d3de92..4737793fef 100755 --- a/pkg_resources/_vendor/more_itertools/more.py +++ b/pkg_resources/_vendor/more_itertools/more.py @@ -369,10 +369,7 @@ def prepend(self, *items): self._cache.extendleft(reversed(items)) def __next__(self): - if self._cache: - return self._cache.popleft() - - return next(self._it) + return self._cache.popleft() if self._cache else next(self._it) def _get_slice(self, index): # Normalize the slice's arguments @@ -607,14 +604,13 @@ def strictly_n(iterable, n, too_short=None, too_long=None): """ if too_short is None: too_short = lambda item_count: raise_( - ValueError, - 'Too few items in iterable (got {})'.format(item_count), + ValueError, f'Too few items in iterable (got {item_count})' ) if too_long is None: too_long = lambda item_count: raise_( ValueError, - 'Too many items in iterable (got at least {})'.format(item_count), + f'Too many items in iterable (got at least {item_count})', ) it = iter(iterable) @@ -998,10 +994,7 @@ def __iter__(self): yield from self._cache.keys() def __getitem__(self, value): - if not self._validator(value): - return iter(()) - - return self._get_values(value) + return iter(()) if not self._validator(value) else self._get_values(value) def spy(iterable, n=1): @@ -1547,8 +1540,7 @@ def repeat_last(iterable, default=None): """ item = _marker - for item in iterable: - yield item + yield from iterable final = default if item is _marker else item yield from repeat(final) @@ -2045,7 +2037,9 @@ class numeric_range(abc.Sequence, abc.Hashable): def __init__(self, *args): argc = len(args) - if argc == 1: + if argc == 0: + raise TypeError(f'numeric_range expected at least 1 argument, got {argc}') + elif argc == 1: (self._stop,) = args self._start = type(self._stop)(0) self._step = type(self._stop - self._start)(1) @@ -2054,16 +2048,8 @@ def __init__(self, *args): self._step = type(self._stop - self._start)(1) elif argc == 3: self._start, self._stop, self._step = args - elif argc == 0: - raise TypeError( - 'numeric_range expected at least ' - '1 argument, got {}'.format(argc) - ) else: - raise TypeError( - 'numeric_range expected at most ' - '3 arguments, got {}'.format(argc) - ) + raise TypeError(f'numeric_range expected at most 3 arguments, got {argc}') self._zero = type(self._step)(0) if self._step == self._zero: @@ -2072,35 +2058,31 @@ def __init__(self, *args): self._init_len() def __bool__(self): - if self._growing: - return self._start < self._stop - else: - return self._start > self._stop + return self._start < self._stop if self._growing else self._start > self._stop def __contains__(self, elem): if self._growing: if self._start <= elem < self._stop: return (elem - self._start) % self._step == self._zero - else: - if self._start >= elem > self._stop: - return (self._start - elem) % (-self._step) == self._zero + elif self._start >= elem > self._stop: + return (self._start - elem) % (-self._step) == self._zero return False def __eq__(self, other): - if isinstance(other, numeric_range): - empty_self = not bool(self) - empty_other = not bool(other) - if empty_self or empty_other: - return empty_self and empty_other # True if both empty - else: - return ( - self._start == other._start - and self._step == other._step - and self._get_by_index(-1) == other._get_by_index(-1) - ) - else: + if not isinstance(other, numeric_range): return False + empty_self = not bool(self) + empty_other = not bool(other) + return ( + empty_self and empty_other + if empty_self or empty_other + else ( + self._start == other._start + and self._step == other._step + and self._get_by_index(-1) == other._get_by_index(-1) + ) + ) def __getitem__(self, key): if isinstance(key, int): @@ -2125,8 +2107,7 @@ def __getitem__(self, key): return numeric_range(start, stop, step) else: raise TypeError( - 'numeric range indices must be ' - 'integers or slices, not {}'.format(type(key).__name__) + f'numeric range indices must be integers or slices, not {type(key).__name__}' ) def __hash__(self): @@ -2166,13 +2147,9 @@ def __reduce__(self): def __repr__(self): if self._step == 1: - return "numeric_range({}, {})".format( - repr(self._start), repr(self._stop) - ) + return f"numeric_range({repr(self._start)}, {repr(self._stop)})" else: - return "numeric_range({}, {}, {})".format( - repr(self._start), repr(self._stop), repr(self._step) - ) + return f"numeric_range({repr(self._start)}, {repr(self._stop)}, {repr(self._step)})" def __reversed__(self): return iter( @@ -2190,13 +2167,12 @@ def index(self, value): q, r = divmod(value - self._start, self._step) if r == self._zero: return int(q) - else: - if self._start >= value > self._stop: - q, r = divmod(self._start - value, -self._step) - if r == self._zero: - return int(q) + elif self._start >= value > self._stop: + q, r = divmod(self._start - value, -self._step) + if r == self._zero: + return int(q) - raise ValueError("{} is not in numeric range".format(value)) + raise ValueError(f"{value} is not in numeric range") def _get_by_index(self, i): if i < 0: @@ -2406,10 +2382,7 @@ class islice_extended: def __init__(self, iterable, *args): it = iter(iterable) - if args: - self._iterable = _islice_helper(it, slice(*args)) - else: - self._iterable = it + self._iterable = _islice_helper(it, slice(*args)) if args else it def __iter__(self): return self @@ -2485,11 +2458,7 @@ def _islice_helper(it, s): # If start and stop are both negative they are comparable and # we can just slice. Otherwise we can adjust start to be negative # and then slice. - if start < 0: - i, j = start, stop - else: - i, j = min(start - len_iter, -1), None - + i, j = (start, stop) if start < 0 else (min(start - len_iter, -1), None) for index, item in list(cache)[i:j:step]: yield item else: @@ -2670,7 +2639,7 @@ def __len__(self): return len(self._target) def __repr__(self): - return '{}({})'.format(self.__class__.__name__, repr(self._target)) + return f'{self.__class__.__name__}({repr(self._target)})' class seekable: @@ -2761,10 +2730,7 @@ class seekable: def __init__(self, iterable, maxlen=None): self._source = iter(iterable) - if maxlen is None: - self._cache = [] - else: - self._cache = deque([], maxlen) + self._cache = [] if maxlen is None else deque([], maxlen) self._index = None def __iter__(self): @@ -3544,9 +3510,8 @@ def sample(iterable, k, weights=None): iterable = iter(iterable) if weights is None: return _sample_unweighted(iterable, k) - else: - weights = iter(weights) - return _sample_weighted(iterable, k, weights) + weights = iter(weights) + return _sample_weighted(iterable, k, weights) def is_sorted(iterable, key=None, reverse=False, strict=False): @@ -3657,9 +3622,7 @@ def __next__(self): @property def done(self): - if self._future is None: - return False - return self._future.done() + return False if self._future is None else self._future.done() @property def result(self): @@ -4280,9 +4243,7 @@ def minmax(iterable_or_value, *others, key=None, default=_marker): x, y = y, x if x < lo: lo = x - if hi < y: - hi = y - + hi = max(hi, y) else: lo_key = hi_key = key(lo) @@ -4385,7 +4346,7 @@ def gray_product(*iterables): if j == iterable_count: break a[j] = a[j] + o[j] - if a[j] == 0 or a[j] == len(all_iterables[j]) - 1: + if a[j] in [0, len(all_iterables[j]) - 1]: o[j] = -o[j] f[j] = f[j + 1] f[j + 1] = j + 1 diff --git a/pkg_resources/_vendor/more_itertools/recipes.py b/pkg_resources/_vendor/more_itertools/recipes.py index 3facc2e3a6..63321150f9 100644 --- a/pkg_resources/_vendor/more_itertools/recipes.py +++ b/pkg_resources/_vendor/more_itertools/recipes.py @@ -639,7 +639,7 @@ def random_combination_with_replacement(iterable, r): """ pool = tuple(iterable) n = len(pool) - indices = sorted(randrange(n) for i in range(r)) + indices = sorted(randrange(n) for _ in range(r)) return tuple(pool[i] for i in indices) @@ -881,10 +881,10 @@ def batched(iterable, n): it = iter(iterable) while True: - batch = list(islice(it, n)) - if not batch: + if batch := list(islice(it, n)): + yield batch + else: break - yield batch def transpose(it): diff --git a/pkg_resources/_vendor/packaging/__init__.py b/pkg_resources/_vendor/packaging/__init__.py index 13cadc7f04..52f4c227ea 100644 --- a/pkg_resources/_vendor/packaging/__init__.py +++ b/pkg_resources/_vendor/packaging/__init__.py @@ -12,4 +12,4 @@ __email__ = "donald@stufft.io" __license__ = "BSD-2-Clause or Apache-2.0" -__copyright__ = "2014-2019 %s" % __author__ +__copyright__ = f"2014-2019 {__author__}" diff --git a/pkg_resources/_vendor/packaging/_manylinux.py b/pkg_resources/_vendor/packaging/_manylinux.py index 449c655be6..1db6fa82bf 100644 --- a/pkg_resources/_vendor/packaging/_manylinux.py +++ b/pkg_resources/_vendor/packaging/_manylinux.py @@ -161,9 +161,7 @@ def _parse_glibc_version(version_str: str) -> Tuple[int, int]: @functools.lru_cache() def _get_glibc_version() -> Tuple[int, int]: version_str = _glibc_version_string() - if version_str is None: - return (-1, -1) - return _parse_glibc_version(version_str) + return (-1, -1) if version_str is None else _parse_glibc_version(version_str) # From PEP 513, PEP 600 @@ -178,9 +176,7 @@ def _is_compatible(name: str, arch: str, version: _GLibCVersion) -> bool: return True if hasattr(_manylinux, "manylinux_compatible"): result = _manylinux.manylinux_compatible(version[0], version[1], arch) - if result is not None: - return bool(result) - return True + return bool(result) if result is not None else True if version == _GLibCVersion(2, 5): if hasattr(_manylinux, "manylinux1_compatible"): return bool(_manylinux.manylinux1_compatible) diff --git a/pkg_resources/_vendor/packaging/_musllinux.py b/pkg_resources/_vendor/packaging/_musllinux.py index 706ba600a9..0d4471d827 100644 --- a/pkg_resources/_vendor/packaging/_musllinux.py +++ b/pkg_resources/_vendor/packaging/_musllinux.py @@ -22,10 +22,10 @@ def _parse_musl_version(output: str) -> Optional[_MuslVersion]: lines = [n for n in (n.strip() for n in output.splitlines()) if n] if len(lines) < 2 or lines[0][:4] != "musl": return None - m = re.match(r"Version (\d+)\.(\d+)", lines[1]) - if not m: + if m := re.match(r"Version (\d+)\.(\d+)", lines[1]): + return _MuslVersion(major=int(m.group(1)), minor=int(m.group(2))) + else: return None - return _MuslVersion(major=int(m.group(1)), minor=int(m.group(2))) @functools.lru_cache() diff --git a/pkg_resources/_vendor/packaging/_parser.py b/pkg_resources/_vendor/packaging/_parser.py index 5a18b758fe..9138491ceb 100644 --- a/pkg_resources/_vendor/packaging/_parser.py +++ b/pkg_resources/_vendor/packaging/_parser.py @@ -318,10 +318,7 @@ def _parse_marker_var(tokenizer: Tokenizer) -> MarkerVar: def process_env_var(env_var: str) -> Variable: - if ( - env_var == "platform_python_implementation" - or env_var == "python_implementation" - ): + if env_var in {"platform_python_implementation", "python_implementation"}: return Variable("platform_python_implementation") else: return Variable(env_var) diff --git a/pkg_resources/_vendor/packaging/markers.py b/pkg_resources/_vendor/packaging/markers.py index 8b98fca723..ddbab25c1a 100644 --- a/pkg_resources/_vendor/packaging/markers.py +++ b/pkg_resources/_vendor/packaging/markers.py @@ -85,10 +85,7 @@ def _format_marker( if isinstance(marker, list): inner = (_format_marker(m, first=False) for m in marker) - if first: - return " ".join(inner) - else: - return "(" + " ".join(inner) + ")" + return " ".join(inner) if first else "(" + " ".join(inner) + ")" elif isinstance(marker, tuple): return " ".join([m.serialize() for m in marker]) else: @@ -226,10 +223,7 @@ def __hash__(self) -> int: return hash((self.__class__.__name__, str(self))) def __eq__(self, other: Any) -> bool: - if not isinstance(other, Marker): - return NotImplemented - - return str(self) == str(other) + return str(self) == str(other) if isinstance(other, Marker) else NotImplemented def evaluate(self, environment: Optional[Dict[str, str]] = None) -> bool: """Evaluate a marker. diff --git a/pkg_resources/_vendor/packaging/requirements.py b/pkg_resources/_vendor/packaging/requirements.py index f34bfa85c8..dcc28b2e7a 100644 --- a/pkg_resources/_vendor/packaging/requirements.py +++ b/pkg_resources/_vendor/packaging/requirements.py @@ -42,9 +42,7 @@ def __init__(self, requirement_string: str) -> None: if parsed_url.scheme == "file": if urllib.parse.urlunparse(parsed_url) != parsed.url: raise InvalidRequirement("Invalid URL given") - elif not (parsed_url.scheme and parsed_url.netloc) or ( - not parsed_url.scheme and not parsed_url.netloc - ): + elif not (parsed_url.scheme and parsed_url.netloc): raise InvalidRequirement(f"Invalid URL: {parsed.url}") self.url: Optional[str] = parsed.url else: diff --git a/pkg_resources/_vendor/packaging/specifiers.py b/pkg_resources/_vendor/packaging/specifiers.py index ba8fe37b7f..70174b33f1 100644 --- a/pkg_resources/_vendor/packaging/specifiers.py +++ b/pkg_resources/_vendor/packaging/specifiers.py @@ -509,7 +509,7 @@ def _compare_greater_than(self, prospective: Version, spec_str: str) -> bool: return True def _compare_arbitrary(self, prospective: Version, spec: str) -> bool: - return str(prospective).lower() == str(spec).lower() + return str(prospective).lower() == spec.lower() def __contains__(self, item: Union[str, Version]) -> bool: """Return whether or not the item is contained in this specifier. @@ -608,11 +608,11 @@ def filter( ['1.3', '1.5a1'] """ - yielded = False found_prereleases = [] kw = {"prereleases": prereleases if prereleases is not None else True} + yielded = False # Attempt to iterate over all the values in the iterable and if any of # them match, yield them. for version in iterable: @@ -622,12 +622,12 @@ def filter( # If our version is a prerelease, and we were not set to allow # prereleases, then we'll store it for later in case nothing # else matches this specifier. - if parsed_version.is_prerelease and not ( - prereleases or self.prereleases + if ( + parsed_version.is_prerelease + and not prereleases + and not self.prereleases ): found_prereleases.append(version) - # Either this is not a prerelease, or we should have been - # accepting prereleases from the beginning. else: yielded = True yield version @@ -636,8 +636,7 @@ def filter( # any values, and if we have not and we have any prereleases stored up # then we will go ahead and yield the prereleases. if not yielded and found_prereleases: - for version in found_prereleases: - yield version + yield from found_prereleases _prefix_regex = re.compile(r"^([0-9]+)((?:a|b|c|rc)[0-9]+)$") @@ -646,8 +645,7 @@ def filter( def _version_split(version: str) -> List[str]: result: List[str] = [] for item in version.split("."): - match = _prefix_regex.search(item) - if match: + if match := _prefix_regex.search(item): result.extend(match.groups()) else: result.append(item) @@ -707,12 +705,9 @@ def __init__( # strip each item to remove leading/trailing whitespace. split_specifiers = [s.strip() for s in specifiers.split(",") if s.strip()] - # Parsed each individual specifier, attempting first to make it a - # Specifier. - parsed: Set[Specifier] = set() - for specifier in split_specifiers: - parsed.add(Specifier(specifier)) - + parsed: Set[Specifier] = { + Specifier(specifier) for specifier in split_specifiers + } # Turn our parsed specifiers into a frozen set and save them for later. self._specs = frozenset(parsed) @@ -730,12 +725,7 @@ def prereleases(self) -> Optional[bool]: # If we don't have any specifiers, and we don't have a forced value, # then we'll just return None since we don't know if this should have # pre-releases or not. - if not self._specs: - return None - - # Otherwise we'll see if any of the given specifiers accept - # prereleases, if any of them do we'll return True, otherwise False. - return any(s.prereleases for s in self._specs) + return None if not self._specs else any(s.prereleases for s in self._specs) @prereleases.setter def prereleases(self, value: bool) -> None: diff --git a/pkg_resources/_vendor/packaging/tags.py b/pkg_resources/_vendor/packaging/tags.py index 76d243414d..4abd3583b5 100644 --- a/pkg_resources/_vendor/packaging/tags.py +++ b/pkg_resources/_vendor/packaging/tags.py @@ -196,10 +196,7 @@ def cpython_tags( interpreter = f"cp{_version_nodot(python_version[:2])}" if abis is None: - if len(python_version) > 1: - abis = _cpython_abis(python_version, warn) - else: - abis = [] + abis = _cpython_abis(python_version, warn) if len(python_version) > 1 else [] abis = list(abis) # 'abi3' and 'none' are explicitly handled later. for explicit_abi in ("abi3", "none"): @@ -285,10 +282,7 @@ def generic_tags( interp_name = interpreter_name() interp_version = interpreter_version(warn=warn) interpreter = "".join([interp_name, interp_version]) - if abis is None: - abis = _generic_abi() - else: - abis = list(abis) + abis = _generic_abi() if abis is None else list(abis) platforms = list(platforms or platform_tags()) if "none" not in abis: abis.append("none") @@ -341,10 +335,7 @@ def _mac_arch(arch: str, is_32bit: bool = _32_BIT_INTERPRETER) -> str: if not is_32bit: return arch - if arch.startswith("ppc"): - return "ppc" - - return "i386" + return "ppc" if arch.startswith("ppc") else "i386" def _mac_binary_formats(version: MacVersion, cpu_arch: str) -> List[str]: @@ -411,12 +402,8 @@ def mac_platforms( version = cast("MacVersion", tuple(map(int, version_str.split(".")[:2]))) else: version = version - if arch is None: - arch = _mac_arch(cpu_arch) - else: - arch = arch - - if (10, 0) <= version and version < (11, 0): + arch = _mac_arch(cpu_arch) if arch is None else arch + if (10, 0) <= version < (11, 0): # Prior to Mac OS 11, each yearly release of Mac OS bumped the # "minor" version number. The major version was always 10. for minor_version in range(version[1], -1, -1): @@ -457,9 +444,9 @@ def mac_platforms( binary_format=binary_format, ) else: + binary_format = "universal2" for minor_version in range(16, 3, -1): compat_version = 10, minor_version - binary_format = "universal2" yield "macosx_{major}_{minor}_{binary_format}".format( major=compat_version[0], minor=compat_version[1], @@ -512,10 +499,7 @@ def interpreter_version(*, warn: bool = False) -> str: Returns the version of the running interpreter. """ version = _get_config_var("py_version_nodot", warn=warn) - if version: - version = str(version) - else: - version = _version_nodot(sys.version_info[:2]) + version = str(version) if version else _version_nodot(sys.version_info[:2]) return version @@ -540,7 +524,7 @@ def sys_tags(*, warn: bool = False) -> Iterator[Tag]: if interp_name == "pp": interp = "pp3" elif interp_name == "cp": - interp = "cp" + interpreter_version(warn=warn) + interp = f"cp{interpreter_version(warn=warn)}" else: interp = None yield from compatible_tags(interpreter=interp) diff --git a/pkg_resources/_vendor/packaging/version.py b/pkg_resources/_vendor/packaging/version.py index b30e8cbf84..048b201ca9 100644 --- a/pkg_resources/_vendor/packaging/version.py +++ b/pkg_resources/_vendor/packaging/version.py @@ -470,20 +470,13 @@ def _parse_letter_version( letter = "a" elif letter == "beta": letter = "b" - elif letter in ["c", "pre", "preview"]: + elif letter in {"c", "pre", "preview"}: letter = "rc" - elif letter in ["rev", "r"]: + elif letter in {"rev", "r"}: letter = "post" return letter, int(number) - if not letter and number: - # We assume if we are given a number, but we are not given a letter - # then this is using the implicit post release syntax (e.g. 1.0-1) - letter = "post" - - return letter, int(number) - - return None + return ("post", int(number)) if number else None _local_version_separators = re.compile(r"[\._-]") @@ -533,19 +526,9 @@ def _cmpkey( _pre = pre # Versions without a post segment should sort before those with one. - if post is None: - _post: PrePostDevType = NegativeInfinity - - else: - _post = post - + _post = NegativeInfinity if post is None else post # Versions without a development segment should sort after those with one. - if dev is None: - _dev: PrePostDevType = Infinity - - else: - _dev = dev - + _dev = Infinity if dev is None else dev if local is None: # Versions without a local segment should sort before those with one. _local: LocalType = NegativeInfinity diff --git a/pkg_resources/_vendor/platformdirs/android.py b/pkg_resources/_vendor/platformdirs/android.py index eda8093512..df09c53254 100644 --- a/pkg_resources/_vendor/platformdirs/android.py +++ b/pkg_resources/_vendor/platformdirs/android.py @@ -90,12 +90,14 @@ def _android_folder() -> str | None: except Exception: # if fails find an android folder looking path on the sys.path pattern = re.compile(r"/data/(data|user/\d+)/(.+)/files") - for path in sys.path: - if pattern.match(path): - result = path.split("/files")[0] - break - else: - result = None + result = next( + ( + path.split("/files")[0] + for path in sys.path + if pattern.match(path) + ), + None, + ) return result diff --git a/pkg_resources/_vendor/platformdirs/unix.py b/pkg_resources/_vendor/platformdirs/unix.py index 9aca5a0305..bf37a6994f 100644 --- a/pkg_resources/_vendor/platformdirs/unix.py +++ b/pkg_resources/_vendor/platformdirs/unix.py @@ -54,7 +54,7 @@ def site_data_dir(self) -> str: def _with_multi_path(self, path: str) -> str: path_list = path.split(os.pathsep) if not self.multipath: - path_list = path_list[0:1] + path_list = path_list[:1] path_list = [self._append_app_name_and_version(os.path.expanduser(p)) for p in path_list] return os.pathsep.join(path_list) diff --git a/pkg_resources/_vendor/typing_extensions.py b/pkg_resources/_vendor/typing_extensions.py index ef42417c20..a8848cb099 100644 --- a/pkg_resources/_vendor/typing_extensions.py +++ b/pkg_resources/_vendor/typing_extensions.py @@ -163,9 +163,7 @@ def __instancecheck__(self, obj): return super().__instancecheck__(obj) def __repr__(self): - if self is Any: - return "typing_extensions.Any" - return super().__repr__() + return "typing_extensions.Any" if self is Any else super().__repr__() class Any(metaclass=_AnyMeta): """Special type indicating an unconstrained type. @@ -193,7 +191,7 @@ def __new__(cls, *args, **kwargs): class _FinalForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): item = typing._type_check(parameters, @@ -265,7 +263,7 @@ def IntVar(name): class _LiteralForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): return typing._GenericAlias(self, parameters) @@ -768,20 +766,18 @@ def __new__(cls, name, bases, ns, total=True): for annotation_key, annotation_type in own_annotations.items(): annotation_origin = get_origin(annotation_type) if annotation_origin is Annotated: - annotation_args = get_args(annotation_type) - if annotation_args: + if annotation_args := get_args(annotation_type): annotation_type = annotation_args[0] annotation_origin = get_origin(annotation_type) - if annotation_origin is Required: - required_keys.add(annotation_key) - elif annotation_origin is NotRequired: - optional_keys.add(annotation_key) - elif total: + if ( + annotation_origin is Required + or annotation_origin is not NotRequired + and total + ): required_keys.add(annotation_key) else: optional_keys.add(annotation_key) - tp_dict.__annotations__ = annotations tp_dict.__required_keys__ = frozenset(required_keys) tp_dict.__optional_keys__ = frozenset(optional_keys) @@ -877,9 +873,7 @@ def _strip_extras(t): return _strip_extras(t.__args__[0]) if isinstance(t, typing._GenericAlias): stripped_args = tuple(_strip_extras(a) for a in t.__args__) - if stripped_args == t.__args__: - return t - return t.copy_with(stripped_args) + return t if stripped_args == t.__args__ else t.copy_with(stripped_args) if hasattr(types, "GenericAlias") and isinstance(t, types.GenericAlias): stripped_args = tuple(_strip_extras(a) for a in t.__args__) if stripped_args == t.__args__: @@ -1080,9 +1074,7 @@ def get_origin(tp): if isinstance(tp, (typing._GenericAlias, _typing_GenericAlias, _BaseGenericAlias, ParamSpecArgs, ParamSpecKwargs)): return tp.__origin__ - if tp is typing.Generic: - return typing.Generic - return None + return typing.Generic if tp is typing.Generic else None def get_args(tp): """Get type arguments with all substitutions performed. @@ -1114,7 +1106,7 @@ def get_args(tp): elif sys.version_info[:2] >= (3, 9): class _TypeAliasForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' @_TypeAliasForm def TypeAlias(self, parameters): @@ -1133,7 +1125,7 @@ def TypeAlias(self, parameters): else: class _TypeAliasForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' TypeAlias = _TypeAliasForm('TypeAlias', doc="""Special marker indicating that an assignment should @@ -1449,7 +1441,7 @@ def Concatenate(self, parameters): else: class _ConcatenateForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): return _concatenate_getitem(self, parameters) @@ -1474,7 +1466,7 @@ def __getitem__(self, parameters): elif sys.version_info[:2] >= (3, 9): class _TypeGuardForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' @_TypeGuardForm def TypeGuard(self, parameters): @@ -1527,7 +1519,7 @@ def is_str(val: Union[str, float]): class _TypeGuardForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): item = typing._type_check(parameters, @@ -1704,7 +1696,7 @@ def int_or_str(arg: int | str) -> None: elif sys.version_info[:2] >= (3, 9): class _ExtensionsSpecialForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' @_ExtensionsSpecialForm def Required(self, parameters): @@ -1746,7 +1738,7 @@ class Movie(TypedDict): else: class _RequiredForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): item = typing._type_check(parameters, @@ -1791,7 +1783,7 @@ class Movie(TypedDict): elif sys.version_info[:2] >= (3, 9): class _UnpackSpecialForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' class _UnpackAlias(typing._GenericAlias, _root=True): __class__ = typing.TypeVar @@ -1820,7 +1812,7 @@ class _UnpackAlias(typing._GenericAlias, _root=True): class _UnpackForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): item = typing._type_check(parameters, @@ -1939,7 +1931,7 @@ def __eq__(self, other): def __reduce__(self): return self.__name__ - def __init_subclass__(self, *args, **kwds): + def __init_subclass__(cls, *args, **kwds): if '_root' not in kwds: raise TypeError("Cannot subclass special typing classes") @@ -2178,7 +2170,7 @@ def __new__(cls, typename, bases, ns): # update from user namespace without overriding special namedtuple attributes for key in ns: if key in _prohibited_namedtuple_fields: - raise AttributeError("Cannot overwrite NamedTuple attribute " + key) + raise AttributeError(f"Cannot overwrite NamedTuple attribute {key}") elif key not in _special_namedtuple_fields and key not in nm_tpl._fields: setattr(nm_tpl, key, ns[key]) if typing.Generic in bases: diff --git a/pkg_resources/_vendor/zipp.py b/pkg_resources/_vendor/zipp.py index 26b723c1fd..d6abd364af 100644 --- a/pkg_resources/_vendor/zipp.py +++ b/pkg_resources/_vendor/zipp.py @@ -93,7 +93,7 @@ def resolve_dir(self, name): as a directory (with the trailing slash). """ names = self._name_set() - dirname = name + '/' + dirname = f'{name}/' dir_match = name not in names and dirname in names return dirname if dir_match else name diff --git a/pkg_resources/extern/__init__.py b/pkg_resources/extern/__init__.py index 948bcc6094..1ae0f0ee4c 100644 --- a/pkg_resources/extern/__init__.py +++ b/pkg_resources/extern/__init__.py @@ -18,19 +18,19 @@ def search_path(self): """ Search first the vendor package then as a natural package. """ - yield self.vendor_pkg + '.' + yield f'{self.vendor_pkg}.' yield '' def _module_matches_namespace(self, fullname): """Figure out if the target module is vendored.""" - root, base, target = fullname.partition(self.root_name + '.') + root, base, target = fullname.partition(f'{self.root_name}.') return not root and any(map(target.startswith, self.vendored_names)) def load_module(self, fullname): """ Iterate over the search path to locate and load fullname. """ - root, base, target = fullname.partition(self.root_name + '.') + root, base, target = fullname.partition(f'{self.root_name}.') for prefix in self.search_path: try: extant = prefix + target diff --git a/pkg_resources/tests/test_pkg_resources.py b/pkg_resources/tests/test_pkg_resources.py index c90dca7ff3..d4b09ba838 100644 --- a/pkg_resources/tests/test_pkg_resources.py +++ b/pkg_resources/tests/test_pkg_resources.py @@ -122,9 +122,8 @@ def test_resource_filename_rewrites_on_change(self): filename = zp.get_resource_filename(manager, 'data.dat') actual = datetime.datetime.fromtimestamp(os.stat(filename).st_mtime) assert actual == self.ref_time - f = open(filename, 'w') - f.write('hello, world?') - f.close() + with open(filename, 'w') as f: + f.write('hello, world?') ts = timestamp(self.ref_time) os.utime(filename, (ts, ts)) filename = zp.get_resource_filename(manager, 'data.dat') @@ -138,7 +137,7 @@ def test_get_cache_path(self): mgr = pkg_resources.ResourceManager() path = mgr.get_cache_path('foo') type_ = str(type(path)) - message = "Unexpected type from get_cache_path: " + type_ + message = f"Unexpected type from get_cache_path: {type_}" assert isinstance(path, str), message def test_get_cache_path_race(self, tmpdir): @@ -229,8 +228,8 @@ def test_get_metadata__bad_utf8(tmpdir): "codec can't decode byte 0xe9 in position 1: " 'invalid continuation byte in METADATA file at path: ' ) - assert expected in actual, 'actual: {}'.format(actual) - assert actual.endswith(metadata_path), 'actual: {}'.format(actual) + assert expected in actual, f'actual: {actual}' + assert actual.endswith(metadata_path), f'actual: {actual}' def make_distribution_no_version(tmpdir, basename): @@ -270,11 +269,11 @@ def test_distribution_version_missing( """ Test Distribution.version when the "Version" header is missing. """ - basename = 'foo.{}'.format(suffix) + basename = f'foo.{suffix}' dist, dist_dir = make_distribution_no_version(tmpdir, basename) - expected_text = ("Missing 'Version:' header and/or {} file at path: ").format( - expected_filename + expected_text = ( + f"Missing 'Version:' header and/or {expected_filename} file at path: " ) metadata_path = os.path.join(dist_dir, expected_filename) @@ -365,7 +364,7 @@ class Environment(str): env = Environment(tmpdir) tmpdir.chmod(stat.S_IRWXU) subs = 'home', 'lib', 'scripts', 'data', 'egg-base' - env.paths = dict((dirname, str(tmpdir / dirname)) for dirname in subs) + env.paths = {dirname: str(tmpdir / dirname) for dirname in subs} list(map(os.mkdir, env.paths.values())) return env diff --git a/pkg_resources/tests/test_resources.py b/pkg_resources/tests/test_resources.py index c90584a882..45083db229 100644 --- a/pkg_resources/tests/test_resources.py +++ b/pkg_resources/tests/test_resources.py @@ -52,7 +52,7 @@ class TestDistro: def testCollection(self): # empty path should produce no distributions ad = pkg_resources.Environment([], platform=None, python=None) - assert list(ad) == [] + assert not list(ad) assert ad['FooPkg'] == [] ad.add(dist_from_fn("FooPkg-1.3_1.egg")) ad.add(dist_from_fn("FooPkg-1.4-py2.4-win32.egg")) @@ -181,7 +181,7 @@ def testResolve(self): ad = pkg_resources.Environment([]) ws = WorkingSet([]) # Resolving no requirements -> nothing to install - assert list(ws.resolve([], ad)) == [] + assert not list(ws.resolve([], ad)) # Request something not in the collection -> DistributionNotFound with pytest.raises(pkg_resources.DistributionNotFound): ws.resolve(parse_requirements("Foo"), ad) @@ -194,7 +194,7 @@ def testResolve(self): ad.add(Distribution.from_filename("Foo-0.9.egg")) # Request thing(s) that are available -> list to activate - for i in range(3): + for _ in range(3): targets = list(ws.resolve(parse_requirements("Foo"), ad)) assert targets == [Foo] list(map(ws.add, targets)) @@ -224,7 +224,7 @@ def test_environment_marker_evaluation_negative(self): ad = pkg_resources.Environment([]) ws = WorkingSet([]) res = ws.resolve(parse_requirements("Foo;python_version<'2'"), ad) - assert list(res) == [] + assert not list(res) def test_environment_marker_evaluation_positive(self): ad = pkg_resources.Environment([]) @@ -404,8 +404,7 @@ def test_resolve_conflicts_with_prior(self): with pytest.raises(VersionConflict) as vc: ws.resolve(parse_requirements("Foo\nBar\n")) - msg = "Baz 1.0 is installed but Baz==2.0 is required by " - msg += repr(set(['Bar'])) + msg = "Baz 1.0 is installed but Baz==2.0 is required by " + repr({'Bar'}) assert vc.value.report() == msg @@ -561,8 +560,8 @@ def testOptionsAndHashing(self): r1 = Requirement.parse("Twisted[foo,bar]>=1.2") r2 = Requirement.parse("Twisted[bar,FOO]>=1.2") assert r1 == r2 - assert set(r1.extras) == set(("foo", "bar")) - assert set(r2.extras) == set(("foo", "bar")) + assert set(r1.extras) == {"foo", "bar"} + assert set(r2.extras) == {"foo", "bar"} assert hash(r1) == hash(r2) assert hash(r1) == hash(( "twisted", @@ -609,7 +608,7 @@ def testSetuptoolsProjectName(self): class TestParsing: def testEmptyParse(self): - assert list(parse_requirements('')) == [] + assert not list(parse_requirements('')) def testYielding(self): for inp, out in [ @@ -770,7 +769,7 @@ def symlinked_tmpdir(self, tmpdir): yield str(tmpdir) return - link_name = str(tmpdir) + '-linked' + link_name = f'{str(tmpdir)}-linked' os.symlink(str(tmpdir), link_name) try: yield type(tmpdir)(link_name) diff --git a/pkg_resources/tests/test_working_set.py b/pkg_resources/tests/test_working_set.py index 57f62b5492..30c021bdb4 100644 --- a/pkg_resources/tests/test_working_set.py +++ b/pkg_resources/tests/test_working_set.py @@ -49,10 +49,9 @@ def parse_distributions(s): metadata = Metadata(('requires.txt', requires)) else: metadata = None - dist = pkg_resources.Distribution( + yield pkg_resources.Distribution( project_name=name, version=version, metadata=metadata ) - yield dist class FakeInstaller: @@ -83,10 +82,7 @@ def parametrize_test_working_set_resolve(*test_list): installed_dists = list(parse_distributions(installed_dists)) installable_dists = list(parse_distributions(installable_dists)) requirements = list(pkg_resources.parse_requirements(requirements)) - for id_, replace_conflicting, expected in ( - (name, False, expected1), - (name + '_replace_conflicting', True, expected2), - ): + for id_, replace_conflicting, expected in ((name, False, expected1), (f'{name}_replace_conflicting', True, expected2)): idlist.append(id_) expected = strip_comments(expected.strip()) if re.match(r'\w+$', expected): diff --git a/setuptools/__init__.py b/setuptools/__init__.py index 563ca1c4ba..eb07bff76b 100644 --- a/setuptools/__init__.py +++ b/setuptools/__init__.py @@ -79,7 +79,8 @@ def _fetch_build_eggs(dist): try: dist.fetch_build_eggs(dist.setup_requires) except Exception as ex: - msg = """ + if "InvalidVersion" in ex.__class__.__name__: + msg = """ It is possible a package already installed in your system contains an version that is invalid according to PEP 440. You can try `pip install --use-pep517` as a workaround for this problem, @@ -88,7 +89,6 @@ def _fetch_build_eggs(dist): If the problem refers to a package that is not installed yet, please contact that package's maintainers or distributors. """ - if "InvalidVersion" in ex.__class__.__name__: if hasattr(ex, "add_note"): ex.add_note(msg) # PEP 678 else: @@ -180,9 +180,7 @@ def _ensure_stringlike(self, option, what, default=None): setattr(self, option, default) return default elif not isinstance(val, str): - raise DistutilsOptionError( - "'%s' must be a %s (got `%s`)" % (option, what, val) - ) + raise DistutilsOptionError(f"'{option}' must be a {what} (got `{val}`)") return val def ensure_string_list(self, option): @@ -203,10 +201,7 @@ def ensure_string_list(self, option): elif isinstance(val, str): setattr(self, option, re.split(r',\s*|\s+', val)) else: - if isinstance(val, list): - ok = all(isinstance(v, str) for v in val) - else: - ok = False + ok = all(isinstance(v, str) for v in val) if isinstance(val, list) else False if not ok: raise DistutilsOptionError( "'%s' must be a list of strings (got %r)" % (option, val) diff --git a/setuptools/_core_metadata.py b/setuptools/_core_metadata.py index 4bf3c7c947..9980827605 100644 --- a/setuptools/_core_metadata.py +++ b/setuptools/_core_metadata.py @@ -40,32 +40,24 @@ def rfc822_unescape(content: str) -> str: def _read_field_from_msg(msg: Message, field: str) -> Optional[str]: """Read Message header field.""" value = msg[field] - if value == 'UNKNOWN': - return None - return value + return None if value == 'UNKNOWN' else value def _read_field_unescaped_from_msg(msg: Message, field: str) -> Optional[str]: """Read Message header field and apply rfc822_unescape.""" value = _read_field_from_msg(msg, field) - if value is None: - return value - return rfc822_unescape(value) + return value if value is None else rfc822_unescape(value) def _read_list_from_msg(msg: Message, field: str) -> Optional[List[str]]: """Read Message header field and return all results as list.""" values = msg.get_all(field, None) - if values == []: - return None - return values + return None if values == [] else values def _read_payload_from_msg(msg: Message) -> Optional[str]: value = msg.get_payload().strip() - if value == 'UNKNOWN' or not value: - return None - return value + return None if value == 'UNKNOWN' or not value else value def read_pkg_file(self, file): diff --git a/setuptools/_distutils/_collections.py b/setuptools/_distutils/_collections.py index 5ad21cc7c9..6316f8e22a 100644 --- a/setuptools/_distutils/_collections.py +++ b/setuptools/_distutils/_collections.py @@ -175,8 +175,7 @@ def get(self, key, default=None): def _find_first_match_(self, keys, item): is_match = functools.partial(self.match, item) - matches = list(filter(is_match, keys)) - if matches: + if matches := list(filter(is_match, keys)): return matches[0] raise KeyError(item) diff --git a/setuptools/_distutils/_modified.py b/setuptools/_distutils/_modified.py index fbb95a8f27..1839a786dd 100644 --- a/setuptools/_distutils/_modified.py +++ b/setuptools/_distutils/_modified.py @@ -24,7 +24,7 @@ def newer(source, target): Raises DistutilsFileError if 'source' does not exist. """ if not os.path.exists(source): - raise DistutilsFileError("file '%s' does not exist" % os.path.abspath(source)) + raise DistutilsFileError(f"file '{os.path.abspath(source)}' does not exist") return _newer(source, target) diff --git a/setuptools/_distutils/_msvccompiler.py b/setuptools/_distutils/_msvccompiler.py index 4f081c7e92..884bfe58b1 100644 --- a/setuptools/_distutils/_msvccompiler.py +++ b/setuptools/_distutils/_msvccompiler.py @@ -101,10 +101,7 @@ def _find_vc2017(): return None, None path = os.path.join(path, "VC", "Auxiliary", "Build") - if os.path.isdir(path): - return 15, path - - return None, None + return (15, path) if os.path.isdir(path) else (None, None) PLAT_SPEC_TO_RUNTIME = { @@ -151,14 +148,12 @@ def _get_vc_env(plat_spec): log.error(exc.output) raise DistutilsPlatformError(f"Error executing {exc.cmd}") - env = { + return { key.lower(): value for key, _, value in (line.partition('=') for line in out.splitlines()) if key and value } - return env - def _find_exe(exe, paths=None): """Return path to an MSVC executable program. @@ -367,14 +362,14 @@ def compile( # noqa: C901 src = os.path.abspath(src) if ext in self._c_extensions: - input_opt = "/Tc" + src + input_opt = f"/Tc{src}" elif ext in self._cpp_extensions: - input_opt = "/Tp" + src + input_opt = f"/Tp{src}" add_cpp_opts = True elif ext in self._rc_extensions: # compile .RC to .RES file input_opt = src - output_opt = "/fo" + obj + output_opt = f"/fo{obj}" try: self.spawn([self.rc] + pp_opts + [output_opt, input_opt]) except DistutilsExecError as msg: @@ -398,9 +393,9 @@ def compile( # noqa: C901 # first compile .MC to .RC and .H file self.spawn([self.mc, '-h', h_dir, '-r', rc_dir, src]) base, _ = os.path.splitext(os.path.basename(src)) - rc_file = os.path.join(rc_dir, base + '.rc') + rc_file = os.path.join(rc_dir, f'{base}.rc') # then compile .RC to .RES file - self.spawn([self.rc, "/fo" + obj, rc_file]) + self.spawn([self.rc, f"/fo{obj}", rc_file]) except DistutilsExecError as msg: raise CompileError(msg) @@ -412,7 +407,7 @@ def compile( # noqa: C901 args = [self.cc] + compile_opts + pp_opts if add_cpp_opts: args.append('/EHsc') - args.extend((input_opt, "/Fo" + obj)) + args.extend((input_opt, f"/Fo{obj}")) args.extend(extra_postargs) try: @@ -431,9 +426,7 @@ def create_static_lib( output_filename = self.library_filename(output_libname, output_dir=output_dir) if self._need_link(objects, output_filename): - lib_args = objects + ['/OUT:' + output_filename] - if debug: - pass # XXX what goes here? + lib_args = objects + [f'/OUT:{output_filename}'] try: log.debug('Executing "%s" %s', self.lib, ' '.join(lib_args)) self.spawn([self.lib] + lib_args) @@ -477,10 +470,14 @@ def link( if self._need_link(objects, output_filename): ldflags = self._ldflags[target_desc, debug] - export_opts = ["/EXPORT:" + sym for sym in (export_symbols or [])] + export_opts = [f"/EXPORT:{sym}" for sym in (export_symbols or [])] ld_args = ( - ldflags + lib_opts + export_opts + objects + ['/OUT:' + output_filename] + ldflags + + lib_opts + + export_opts + + objects + + [f'/OUT:{output_filename}'] ) # The MSVC linker generates .lib and .exp files, which cannot be @@ -494,7 +491,7 @@ def link( os.path.basename(output_filename) ) implib_file = os.path.join(build_temp, self.library_filename(dll_name)) - ld_args.append('/IMPLIB:' + implib_file) + ld_args.append(f'/IMPLIB:{implib_file}') if extra_preargs: ld_args[:0] = extra_preargs @@ -541,7 +538,7 @@ def _fallback_spawn(self, cmd, env): # ccompiler.py. def library_dir_option(self, dir): - return "/LIBPATH:" + dir + return f"/LIBPATH:{dir}" def runtime_library_dir_option(self, dir): raise DistutilsPlatformError( @@ -554,10 +551,7 @@ def library_option(self, lib): def find_library_file(self, dirs, lib, debug=0): # Prefer a debugging library if found (and requested), but deal # with it if we don't have one. - if debug: - try_names = [lib + "_d", lib] - else: - try_names = [lib] + try_names = [f"{lib}_d", lib] if debug else [lib] for dir in dirs: for name in try_names: libfile = os.path.join(dir, self.library_filename(name)) diff --git a/setuptools/_distutils/archive_util.py b/setuptools/_distutils/archive_util.py index 7f9e1e00cc..6f846d394f 100644 --- a/setuptools/_distutils/archive_util.py +++ b/setuptools/_distutils/archive_util.py @@ -37,9 +37,7 @@ def _get_gid(name): result = getgrnam(name) except KeyError: result = None - if result is not None: - return result[2] - return None + return result[2] if result is not None else None def _get_uid(name): @@ -50,9 +48,7 @@ def _get_uid(name): result = getpwnam(name) except KeyError: result = None - if result is not None: - return result[2] - return None + return result[2] if result is not None else None def make_tarball( @@ -89,7 +85,7 @@ def make_tarball( "'xz' or 'compress'" ) - archive_name = base_name + '.tar' + archive_name = f'{base_name}.tar' if compress != 'compress': archive_name += compress_ext.get(compress, '') @@ -113,7 +109,7 @@ def _set_uid_gid(tarinfo): return tarinfo if not dry_run: - tar = tarfile.open(archive_name, 'w|%s' % tar_compression[compress]) + tar = tarfile.open(archive_name, f'w|{tar_compression[compress]}') try: tar.add(base_dir, filter=_set_uid_gid) finally: @@ -134,7 +130,7 @@ def _set_uid_gid(tarinfo): return archive_name -def make_zipfile(base_name, base_dir, verbose=0, dry_run=0): # noqa: C901 +def make_zipfile(base_name, base_dir, verbose=0, dry_run=0): # noqa: C901 """Create a zip file from all the files under 'base_dir'. The output zip file will be named 'base_name' + ".zip". Uses either the @@ -143,17 +139,13 @@ def make_zipfile(base_name, base_dir, verbose=0, dry_run=0): # noqa: C901 available, raises DistutilsExecError. Returns the name of the output zip file. """ - zip_filename = base_name + ".zip" + zip_filename = f"{base_name}.zip" mkpath(os.path.dirname(zip_filename), dry_run=dry_run) # If zipfile module is not available, try spawning an external # 'zip' command. if zipfile is None: - if verbose: - zipoptions = "-r" - else: - zipoptions = "-rq" - + zipoptions = "-r" if verbose else "-rq" try: spawn(["zip", zipoptions, zip_filename, base_dir], dry_run=dry_run) except DistutilsExecError: @@ -213,10 +205,9 @@ def check_archive_formats(formats): If all formats are known, returns None """ - for format in formats: - if format not in ARCHIVE_FORMATS: - return format - return None + return next( + (format for format in formats if format not in ARCHIVE_FORMATS), None + ) def make_archive( @@ -260,7 +251,7 @@ def make_archive( try: format_info = ARCHIVE_FORMATS[format] except KeyError: - raise ValueError("unknown archive format '%s'" % format) + raise ValueError(f"unknown archive format '{format}'") func = format_info[0] for arg, val in format_info[1]: diff --git a/setuptools/_distutils/bcppcompiler.py b/setuptools/_distutils/bcppcompiler.py index 3c2ba15410..82d7d9f665 100644 --- a/setuptools/_distutils/bcppcompiler.py +++ b/setuptools/_distutils/bcppcompiler.py @@ -131,17 +131,11 @@ def compile( # noqa: C901 continue # the 'for' loop # The next two are both for the real compiler. - if ext in self._c_extensions: + if ext in self._c_extensions or ext not in self._cpp_extensions: input_opt = "" - elif ext in self._cpp_extensions: - input_opt = "-P" else: - # Unknown file type -- no extra options. The compiler - # will probably fail, but let it just in case this is a - # file the compiler recognizes even if we don't. - input_opt = "" - - output_opt = "-o" + obj + input_opt = "-P" + output_opt = f"-o{obj}" # Compiler command line syntax is: "bcc32 [options] file(s)". # Note that the source file names must appear at the end of @@ -170,8 +164,6 @@ def create_static_lib( if self._need_link(objects, output_filename): lib_args = [output_filename, '/u'] + objects - if debug: - pass # XXX what goes here? try: self.spawn([self.lib] + lib_args) except DistutilsExecError as msg: @@ -218,17 +210,10 @@ def link( # noqa: C901 # Figure out linker args based on type of target. if target_desc == CCompiler.EXECUTABLE: startup_obj = 'c0w32' - if debug: - ld_args = self.ldflags_exe_debug[:] - else: - ld_args = self.ldflags_exe[:] + ld_args = self.ldflags_exe_debug[:] if debug else self.ldflags_exe[:] else: startup_obj = 'c0d32' - if debug: - ld_args = self.ldflags_shared_debug[:] - else: - ld_args = self.ldflags_shared[:] - + ld_args = self.ldflags_shared_debug[:] if debug else self.ldflags_shared[:] # Create a temporary exports file for use by the linker if export_symbols is None: def_file = '' @@ -236,11 +221,10 @@ def link( # noqa: C901 head, tail = os.path.split(output_filename) modname, ext = os.path.splitext(tail) temp_dir = os.path.dirname(objects[0]) # preserve tree structure - def_file = os.path.join(temp_dir, '%s.def' % modname) + def_file = os.path.join(temp_dir, f'{modname}.def') contents = ['EXPORTS'] - for sym in export_symbols or []: - contents.append(' {}=_{}'.format(sym, sym)) - self.execute(write_file, (def_file, contents), "writing %s" % def_file) + contents.extend(f' {sym}=_{sym}' for sym in export_symbols or []) + self.execute(write_file, (def_file, contents), f"writing {def_file}") # Borland C++ has problems with '/' in paths objects2 = map(os.path.normpath, objects) @@ -256,7 +240,7 @@ def link( # noqa: C901 objects.append(file) for ell in library_dirs: - ld_args.append("/L%s" % os.path.normpath(ell)) + ld_args.append(f"/L{os.path.normpath(ell)}") ld_args.append("/L.") # we sometimes use relative paths # list of object files @@ -326,10 +310,10 @@ def find_library_file(self, dirs, lib, debug=0): # compiler they care about, since (almost?) every Windows compiler # seems to have a different format for static libraries. if debug: - dlib = lib + "_d" - try_names = (dlib + "_bcpp", lib + "_bcpp", dlib, lib) + dlib = f"{lib}_d" + try_names = f"{dlib}_bcpp", f"{lib}_bcpp", dlib, lib else: - try_names = (lib + "_bcpp", lib) + try_names = f"{lib}_bcpp", lib for dir in dirs: for name in try_names: @@ -349,9 +333,7 @@ def object_filenames(self, source_filenames, strip_dir=0, output_dir=''): # use normcase to make sure '.rc' is really '.rc' and not '.RC' (base, ext) = os.path.splitext(os.path.normcase(src_name)) if ext not in (self.src_extensions + ['.rc', '.res']): - raise UnknownFileError( - "unknown file type '{}' (from '{}')".format(ext, src_name) - ) + raise UnknownFileError(f"unknown file type '{ext}' (from '{src_name}')") if strip_dir: base = os.path.basename(base) if ext == '.res': @@ -359,7 +341,7 @@ def object_filenames(self, source_filenames, strip_dir=0, output_dir=''): obj_names.append(os.path.join(output_dir, base + ext)) elif ext == '.rc': # these need to be compiled to .res-files - obj_names.append(os.path.join(output_dir, base + '.res')) + obj_names.append(os.path.join(output_dir, f'{base}.res')) else: obj_names.append(os.path.join(output_dir, base + self.obj_extension)) return obj_names @@ -379,7 +361,7 @@ def preprocess( pp_opts = gen_preprocess_options(macros, include_dirs) pp_args = ['cpp32.exe'] + pp_opts if output_file is not None: - pp_args.append('-o' + output_file) + pp_args.append(f'-o{output_file}') if extra_preargs: pp_args[:0] = extra_preargs if extra_postargs: diff --git a/setuptools/_distutils/ccompiler.py b/setuptools/_distutils/ccompiler.py index c1c7d5476e..cfcf9585a6 100644 --- a/setuptools/_distutils/ccompiler.py +++ b/setuptools/_distutils/ccompiler.py @@ -168,8 +168,7 @@ class (via the 'executables' class attribute), but most will have: for key in kwargs: if key not in self.executables: raise ValueError( - "unknown executable '%s' for class %s" - % (key, self.__class__.__name__) + f"unknown executable '{key}' for class {self.__class__.__name__}" ) self.set_executable(key, kwargs[key]) @@ -180,12 +179,7 @@ def set_executable(self, key, value): setattr(self, key, value) def _find_macro(self, name): - i = 0 - for defn in self.macros: - if defn[0] == name: - return i - i += 1 - return None + return next((i for i, defn in enumerate(self.macros) if defn[0] == name), None) def _check_macro_definitions(self, definitions): """Ensures that every element of 'definitions' is a valid macro @@ -195,16 +189,12 @@ def _check_macro_definitions(self, definitions): for defn in definitions: if not ( isinstance(defn, tuple) - and ( - len(defn) in (1, 2) - and (isinstance(defn[1], str) or defn[1] is None) - ) + and len(defn) in {1, 2} + and (isinstance(defn[1], str) or defn[1] is None) and isinstance(defn[0], str) ): raise TypeError( - ("invalid macro definition '%s': " % defn) - + "must be tuple (string,), (string, string), or " - + "(string, None)" + f"invalid macro definition '{defn}': must be tuple (string,), (string, string), or (string, None)" ) # -- Bookkeeping methods ------------------------------------------- @@ -477,11 +467,11 @@ def _need_link(self, objects, output_file): if self.force: return True else: - if self.dry_run: - newer = newer_group(objects, output_file, missing='newer') - else: - newer = newer_group(objects, output_file) - return newer + return ( + newer_group(objects, output_file, missing='newer') + if self.dry_run + else newer_group(objects, output_file) + ) def detect_language(self, sources): """Detect the language of a given file, or list of files. Uses @@ -957,10 +947,10 @@ def find_library_file(self, dirs, lib, debug=0): def object_filenames(self, source_filenames, strip_dir=0, output_dir=''): if output_dir is None: output_dir = '' - return list( + return [ self._make_out_path(output_dir, strip_dir, src_name) for src_name in source_filenames - ) + ] @property def out_extensions(self): @@ -972,9 +962,7 @@ def _make_out_path(self, output_dir, strip_dir, src_name): try: new_ext = self.out_extensions[ext] except LookupError: - raise UnknownFileError( - "unknown file type '{}' (from '{}')".format(ext, src_name) - ) + raise UnknownFileError(f"unknown file type '{ext}' (from '{src_name}')") if strip_dir: base = os.path.basename(base) return os.path.join(output_dir, base + new_ext) @@ -1010,8 +998,8 @@ def library_filename( expected = '"static", "shared", "dylib", "xcode_stub"' if lib_type not in eval(expected): raise ValueError(f"'lib_type' must be {expected}") - fmt = getattr(self, lib_type + "_lib_format") - ext = getattr(self, lib_type + "_lib_extension") + fmt = getattr(self, f"{lib_type}_lib_format") + ext = getattr(self, f"{lib_type}_lib_extension") dir, base = os.path.split(libname) filename = fmt % (base, ext) @@ -1076,14 +1064,17 @@ def get_default_compiler(osname=None, platform=None): osname = os.name if platform is None: platform = sys.platform - for pattern, compiler in _default_compilers: - if ( - re.match(pattern, platform) is not None - or re.match(pattern, osname) is not None - ): - return compiler - # Default to Unix compiler - return 'unix' + return next( + ( + compiler + for pattern, compiler in _default_compilers + if ( + re.match(pattern, platform) is not None + or re.match(pattern, osname) is not None + ) + ), + 'unix', + ) # Map compiler types to (module_name, class_name) pairs -- ie. where to @@ -1115,9 +1106,10 @@ def show_compilers(): # commands that use it. from distutils.fancy_getopt import FancyGetopt - compilers = [] - for compiler in compiler_class.keys(): - compilers.append(("compiler=" + compiler, None, compiler_class[compiler][2])) + compilers = [ + (f"compiler={compiler}", None, compiler_class[compiler][2]) + for compiler in compiler_class.keys() + ] compilers.sort() pretty_printer = FancyGetopt(compilers) pretty_printer.print_help("List of available compilers:") @@ -1143,19 +1135,19 @@ def new_compiler(plat=None, compiler=None, verbose=0, dry_run=0, force=0): (module_name, class_name, long_description) = compiler_class[compiler] except KeyError: - msg = "don't know how to compile C/C++ code on platform '%s'" % plat + msg = f"don't know how to compile C/C++ code on platform '{plat}'" if compiler is not None: - msg = msg + " with '%s' compiler" % compiler + msg = f"{msg} with '{compiler}' compiler" raise DistutilsPlatformError(msg) try: - module_name = "distutils." + module_name + module_name = f"distutils.{module_name}" __import__(module_name) module = sys.modules[module_name] klass = vars(module)[class_name] except ImportError: raise DistutilsModuleError( - "can't compile C/C++ code: unable to load module '%s'" % module_name + f"can't compile C/C++ code: unable to load module '{module_name}'" ) except KeyError: raise DistutilsModuleError( @@ -1192,25 +1184,24 @@ def gen_preprocess_options(macros, include_dirs): # and therefore common to all CCompiler classes. pp_opts = [] for macro in macros: - if not (isinstance(macro, tuple) and 1 <= len(macro) <= 2): + if not isinstance(macro, tuple) or not 1 <= len(macro) <= 2: raise TypeError( "bad macro definition '%s': " "each element of 'macros' list must be a 1- or 2-tuple" % macro ) if len(macro) == 1: # undefine this macro - pp_opts.append("-U%s" % macro[0]) + pp_opts.append(f"-U{macro[0]}") elif len(macro) == 2: if macro[1] is None: # define with no explicit value - pp_opts.append("-D%s" % macro[0]) + pp_opts.append(f"-D{macro[0]}") else: # XXX *don't* need to be clever about quoting the # macro value here, because we're going to avoid the # shell at all costs when we spawn the command! pp_opts.append("-D%s=%s" % macro) - for dir in include_dirs: - pp_opts.append("-I%s" % dir) + pp_opts.extend(f"-I{dir}" for dir in include_dirs) return pp_opts @@ -1221,11 +1212,7 @@ def gen_lib_options(compiler, library_dirs, runtime_library_dirs, libraries): directories. Returns a list of command-line options suitable for use with some compiler (depending on the two format strings passed in). """ - lib_opts = [] - - for dir in library_dirs: - lib_opts.append(compiler.library_dir_option(dir)) - + lib_opts = [compiler.library_dir_option(dir) for dir in library_dirs] for dir in runtime_library_dirs: opt = compiler.runtime_library_dir_option(dir) if isinstance(opt, list): @@ -1242,13 +1229,10 @@ def gen_lib_options(compiler, library_dirs, runtime_library_dirs, libraries): for lib in libraries: (lib_dir, lib_name) = os.path.split(lib) if lib_dir: - lib_file = compiler.find_library_file([lib_dir], lib_name) - if lib_file: + if lib_file := compiler.find_library_file([lib_dir], lib_name): lib_opts.append(lib_file) else: - compiler.warn( - "no library file corresponding to " "'%s' found (skipping)" % lib - ) + compiler.warn(f"no library file corresponding to '{lib}' found (skipping)") else: lib_opts.append(compiler.library_option(lib)) return lib_opts diff --git a/setuptools/_distutils/cmd.py b/setuptools/_distutils/cmd.py index 8fdcbc0ea2..85d1edad37 100644 --- a/setuptools/_distutils/cmd.py +++ b/setuptools/_distutils/cmd.py @@ -97,14 +97,10 @@ def __init__(self, dist): # XXX A more explicit way to customize dry_run would be better. def __getattr__(self, attr): - if attr == 'dry_run': - myval = getattr(self, "_" + attr) - if myval is None: - return getattr(self.distribution, attr) - else: - return myval - else: + if attr != 'dry_run': raise AttributeError(attr) + myval = getattr(self, f"_{attr}") + return getattr(self.distribution, attr) if myval is None else myval def ensure_finalized(self): if not self.finalized: @@ -135,7 +131,7 @@ def initialize_options(self): This method must be implemented by all command classes. """ raise RuntimeError( - "abstract method -- subclass %s must override" % self.__class__ + f"abstract method -- subclass {self.__class__} must override" ) def finalize_options(self): @@ -150,22 +146,22 @@ def finalize_options(self): This method must be implemented by all command classes. """ raise RuntimeError( - "abstract method -- subclass %s must override" % self.__class__ + f"abstract method -- subclass {self.__class__} must override" ) def dump_options(self, header=None, indent=""): from distutils.fancy_getopt import longopt_xlate if header is None: - header = "command options for '%s':" % self.get_command_name() + header = f"command options for '{self.get_command_name()}':" self.announce(indent + header, level=logging.INFO) - indent = indent + " " + indent = f"{indent} " for option, _, _ in self.user_options: option = option.translate(longopt_xlate) if option[-1] == "=": option = option[:-1] value = getattr(self, option) - self.announce(indent + "{} = {}".format(option, value), level=logging.INFO) + self.announce(f"{indent}{option} = {value}", level=logging.INFO) def run(self): """A command's raison d'etre: carry out the action it exists to @@ -178,7 +174,7 @@ def run(self): This method must be implemented by all command classes. """ raise RuntimeError( - "abstract method -- subclass %s must override" % self.__class__ + f"abstract method -- subclass {self.__class__} must override" ) def announce(self, msg, level=logging.DEBUG): @@ -213,9 +209,7 @@ def _ensure_stringlike(self, option, what, default=None): setattr(self, option, default) return default elif not isinstance(val, str): - raise DistutilsOptionError( - "'{}' must be a {} (got `{}`)".format(option, what, val) - ) + raise DistutilsOptionError(f"'{option}' must be a {what} (got `{val}`)") return val def ensure_string(self, option, default=None): @@ -236,10 +230,7 @@ def ensure_string_list(self, option): elif isinstance(val, str): setattr(self, option, re.split(r',\s*|\s+', val)) else: - if isinstance(val, list): - ok = all(isinstance(v, str) for v in val) - else: - ok = False + ok = all(isinstance(v, str) for v in val) if isinstance(val, list) else False if not ok: raise DistutilsOptionError( "'{}' must be a list of strings (got {!r})".format(option, val) @@ -249,7 +240,7 @@ def _ensure_tested_string(self, option, tester, what, error_fmt, default=None): val = self._ensure_stringlike(option, what, default) if val is not None and not tester(val): raise DistutilsOptionError( - ("error in '%s' option: " + error_fmt) % (option, val) + f"error in '%s' option: {error_fmt}" % (option, val) ) def ensure_filename(self, option): @@ -324,11 +315,11 @@ def get_sub_commands(self): a method that we call to determine if the subcommand needs to be run for the current distribution. Return a list of command names. """ - commands = [] - for cmd_name, method in self.sub_commands: - if method is None or method(self): - commands.append(cmd_name) - return commands + return [ + cmd_name + for cmd_name, method in self.sub_commands + if method is None or method(self) + ] # -- External world manipulation ----------------------------------- @@ -414,7 +405,7 @@ def make_file( timestamp checks. """ if skip_msg is None: - skip_msg = "skipping %s (inputs unchanged)" % outfile + skip_msg = f"skipping {outfile} (inputs unchanged)" # Allow 'infiles' to be a single string if isinstance(infiles, str): @@ -423,7 +414,7 @@ def make_file( raise TypeError("'infiles' must be a string, or a list or tuple of strings") if exec_msg is None: - exec_msg = "generating {} from {}".format(outfile, ', '.join(infiles)) + exec_msg = f"generating {outfile} from {', '.join(infiles)}" # If 'outfile' must be regenerated (either because it doesn't # exist, is out-of-date, or the 'force' flag is true) then diff --git a/setuptools/_distutils/command/bdist.py b/setuptools/_distutils/command/bdist.py index 6329039ce4..a65345d3c8 100644 --- a/setuptools/_distutils/command/bdist.py +++ b/setuptools/_distutils/command/bdist.py @@ -15,9 +15,10 @@ def show_formats(): """Print list of available formats (arguments to "--format" option).""" from ..fancy_getopt import FancyGetopt - formats = [] - for format in bdist.format_commands: - formats.append(("formats=" + format, None, bdist.format_commands[format][1])) + formats = [ + (f"formats={format}", None, bdist.format_commands[format][1]) + for format in bdist.format_commands + ] pretty_printer = FancyGetopt(formats) pretty_printer.print_help("List of available distribution formats:") @@ -101,7 +102,6 @@ def initialize_options(self): self.owner = None def finalize_options(self): - # have to finalize 'plat_name' before 'bdist_base' if self.plat_name is None: if self.skip_build: self.plat_name = get_platform() @@ -113,7 +113,7 @@ def finalize_options(self): # "build/bdist./dumb", "build/bdist./rpm", etc.) if self.bdist_base is None: build_base = self.get_finalized_command('build').build_base - self.bdist_base = os.path.join(build_base, 'bdist.' + self.plat_name) + self.bdist_base = os.path.join(build_base, f'bdist.{self.plat_name}') self.ensure_string_list('formats') if self.formats is None: @@ -135,7 +135,7 @@ def run(self): try: commands.append(self.format_commands[format][0]) except KeyError: - raise DistutilsOptionError("invalid format '%s'" % format) + raise DistutilsOptionError(f"invalid format '{format}'") # Reinitialize and run each command. for i in range(len(self.formats)): diff --git a/setuptools/_distutils/command/bdist_dumb.py b/setuptools/_distutils/command/bdist_dumb.py index 01dd79079b..f4a68a1d9b 100644 --- a/setuptools/_distutils/command/bdist_dumb.py +++ b/setuptools/_distutils/command/bdist_dumb.py @@ -95,35 +95,30 @@ def run(self): self.run_command('build') install = self.reinitialize_command('install', reinit_subcommands=1) - install.root = self.bdist_dir install.skip_build = self.skip_build install.warn_dir = 0 + install.root = self.bdist_dir log.info("installing to %s", self.bdist_dir) self.run_command('install') # And make an archive relative to the root of the # pseudo-installation tree. - archive_basename = "{}.{}".format( - self.distribution.get_fullname(), self.plat_name - ) + archive_basename = f"{self.distribution.get_fullname()}.{self.plat_name}" pseudoinstall_root = os.path.join(self.dist_dir, archive_basename) if not self.relative: archive_root = self.bdist_dir - else: - if self.distribution.has_ext_modules() and ( + elif self.distribution.has_ext_modules() and ( install.install_base != install.install_platbase ): - raise DistutilsPlatformError( - "can't make a dumb built distribution where " - "base and platbase are different (%s, %s)" - % (repr(install.install_base), repr(install.install_platbase)) - ) - else: - archive_root = os.path.join( - self.bdist_dir, ensure_relative(install.install_base) - ) + raise DistutilsPlatformError( + f"can't make a dumb built distribution where base and platbase are different ({repr(install.install_base)}, {repr(install.install_platbase)})" + ) + else: + archive_root = os.path.join( + self.bdist_dir, ensure_relative(install.install_base) + ) # Make the archive filename = self.make_archive( diff --git a/setuptools/_distutils/command/bdist_rpm.py b/setuptools/_distutils/command/bdist_rpm.py index 3ed608b479..ad7d5a1f57 100644 --- a/setuptools/_distutils/command/bdist_rpm.py +++ b/setuptools/_distutils/command/bdist_rpm.py @@ -203,10 +203,7 @@ def finalize_options(self): self.rpm_base = os.path.join(self.bdist_base, "rpm") if self.python is None: - if self.fix_python: - self.python = sys.executable - else: - self.python = "python3" + self.python = sys.executable if self.fix_python else "python3" elif self.fix_python: raise DistutilsOptionError( "--python and --fix-python are mutually exclusive options" @@ -214,7 +211,7 @@ def finalize_options(self): if os.name != 'posix': raise DistutilsPlatformError( - "don't know how to create RPM " "distributions on platform %s" % os.name + f"don't know how to create RPM distributions on platform {os.name}" ) if self.binary_only and self.source_only: raise DistutilsOptionError( @@ -232,8 +229,7 @@ def finalize_package_data(self): self.ensure_string('group', "Development/Libraries") self.ensure_string( 'vendor', - "%s <%s>" - % (self.distribution.get_contact(), self.distribution.get_contact_email()), + f"{self.distribution.get_contact()} <{self.distribution.get_contact_email()}>", ) self.ensure_string('packager') self.ensure_string_list('doc_files') @@ -296,9 +292,11 @@ def run(self): # noqa: C901 # Spec file goes into 'dist_dir' if '--spec-only specified', # build/rpm. otherwise. - spec_path = os.path.join(spec_dir, "%s.spec" % self.distribution.get_name()) + spec_path = os.path.join(spec_dir, f"{self.distribution.get_name()}.spec") self.execute( - write_file, (spec_path, self._make_spec_file()), "writing '%s'" % spec_path + write_file, + (spec_path, self._make_spec_file()), + f"writing '{spec_path}'", ) if self.spec_only: # stop if requested @@ -308,10 +306,7 @@ def run(self): # noqa: C901 # optional icon. saved_dist_files = self.distribution.dist_files[:] sdist = self.reinitialize_command('sdist') - if self.use_bzip2: - sdist.formats = ['bztar'] - else: - sdist.formats = ['gztar'] + sdist.formats = ['bztar'] if self.use_bzip2 else ['gztar'] self.run_command('sdist') self.distribution.dist_files = saved_dist_files @@ -323,7 +318,7 @@ def run(self): # noqa: C901 if os.path.exists(self.icon): self.copy_file(self.icon, source_dir) else: - raise DistutilsFileError("icon file '%s' does not exist" % self.icon) + raise DistutilsFileError(f"icon file '{self.icon}' does not exist") # build package log.info("building RPMs") @@ -335,9 +330,9 @@ def run(self): # noqa: C901 rpm_cmd.append('-bb') else: rpm_cmd.append('-ba') - rpm_cmd.extend(['--define', '__python %s' % self.python]) + rpm_cmd.extend(['--define', f'__python {self.python}']) if self.rpm3_mode: - rpm_cmd.extend(['--define', '_topdir %s' % os.path.abspath(self.rpm_base)]) + rpm_cmd.extend(['--define', f'_topdir {os.path.abspath(self.rpm_base)}']) if not self.keep_temp: rpm_cmd.append('--clean') @@ -350,13 +345,9 @@ def run(self): # noqa: C901 # Note that some of these may not be really built (if the file # list is empty) nvr_string = "%{name}-%{version}-%{release}" - src_rpm = nvr_string + ".src.rpm" + src_rpm = f"{nvr_string}.src.rpm" non_src_rpm = "%{arch}/" + nvr_string + ".%{arch}.rpm" - q_cmd = r"rpm -q --qf '{} {}\n' --specfile '{}'".format( - src_rpm, - non_src_rpm, - spec_path, - ) + q_cmd = f"rpm -q --qf '{src_rpm} {non_src_rpm}\n' --specfile '{spec_path}'" out = os.popen(q_cmd) try: @@ -373,9 +364,8 @@ def run(self): # noqa: C901 if source_rpm is None: source_rpm = ell[0] - status = out.close() - if status: - raise DistutilsExecError("Failed to execute: %s" % repr(q_cmd)) + if status := out.close(): + raise DistutilsExecError(f"Failed to execute: {repr(q_cmd)}") finally: out.close() diff --git a/setuptools/_distutils/command/build.py b/setuptools/_distutils/command/build.py index cc9b367ef9..e8003c4b54 100644 --- a/setuptools/_distutils/command/build.py +++ b/setuptools/_distutils/command/build.py @@ -68,17 +68,13 @@ def initialize_options(self): def finalize_options(self): # noqa: C901 if self.plat_name is None: self.plat_name = get_platform() - else: - # plat-name only supported for windows (other platforms are - # supported via ./configure flags, if at all). Avoid misleading - # other platforms. - if os.name != 'nt': - raise DistutilsOptionError( - "--plat-name only supported on Windows (try " - "using './configure --help' on your platform)" - ) - - plat_specifier = ".{}-{}".format(self.plat_name, sys.implementation.cache_tag) + elif os.name != 'nt': + raise DistutilsOptionError( + "--plat-name only supported on Windows (try " + "using './configure --help' on your platform)" + ) + + plat_specifier = f".{self.plat_name}-{sys.implementation.cache_tag}" # Make it so Python 2.x and Python 2.x with --with-pydebug don't # share the same build directories. Doing so confuses the build @@ -92,11 +88,8 @@ def finalize_options(self): # noqa: C901 if self.build_purelib is None: self.build_purelib = os.path.join(self.build_base, 'lib') if self.build_platlib is None: - self.build_platlib = os.path.join(self.build_base, 'lib' + plat_specifier) + self.build_platlib = os.path.join(self.build_base, f'lib{plat_specifier}') - # 'build_lib' is the actual directory that we will use for this - # particular module distribution -- if user didn't supply it, pick - # one of 'build_purelib' or 'build_platlib'. if self.build_lib is None: if self.distribution.has_ext_modules(): self.build_lib = self.build_platlib @@ -106,7 +99,7 @@ def finalize_options(self): # noqa: C901 # 'build_temp' -- temporary directory for compiler turds, # "build/temp." if self.build_temp is None: - self.build_temp = os.path.join(self.build_base, 'temp' + plat_specifier) + self.build_temp = os.path.join(self.build_base, f'temp{plat_specifier}') if self.build_scripts is None: self.build_scripts = os.path.join( self.build_base, 'scripts-%d.%d' % sys.version_info[:2] diff --git a/setuptools/_distutils/command/build_clib.py b/setuptools/_distutils/command/build_clib.py index b3f679b67d..ae23b1d9cc 100644 --- a/setuptools/_distutils/command/build_clib.py +++ b/setuptools/_distutils/command/build_clib.py @@ -153,10 +153,7 @@ def get_library_names(self): if not self.libraries: return None - lib_names = [] - for lib_name, build_info in self.libraries: - lib_names.append(lib_name) - return lib_names + return [lib_name for lib_name, build_info in self.libraries] def get_source_files(self): self.check_library_list(self.libraries) diff --git a/setuptools/_distutils/command/build_ext.py b/setuptools/_distutils/command/build_ext.py index b48f462626..53451da356 100644 --- a/setuptools/_distutils/command/build_ext.py +++ b/setuptools/_distutils/command/build_ext.py @@ -207,30 +207,27 @@ def finalize_options(self): # noqa: C901 self.library_dirs.append(sys.base_exec_prefix) # Use the .lib files for the correct architecture - if self.plat_name == 'win32': - suffix = 'win32' - else: - # win-amd64 - suffix = self.plat_name[4:] + suffix = 'win32' if self.plat_name == 'win32' else self.plat_name[4:] new_lib = os.path.join(sys.exec_prefix, 'PCbuild') if suffix: new_lib = os.path.join(new_lib, suffix) self.library_dirs.append(new_lib) - # For extensions under Cygwin, Python's library directory must be - # appended to library_dirs if sys.platform[:6] == 'cygwin': - if not sysconfig.python_build: + if sysconfig.python_build: + # building python standard extensions + self.library_dirs.append('.') + + else: # building third party extensions self.library_dirs.append( os.path.join( - sys.prefix, "lib", "python" + get_python_version(), "config" + sys.prefix, + "lib", + f"python{get_python_version()}", + "config", ) ) - else: - # building python standard extensions - self.library_dirs.append('.') - # For building extensions with a shared Python library, # Python's library directory must be appended to library_dirs # See Issues: #1600860, #4366 @@ -257,11 +254,7 @@ def finalize_options(self): # noqa: C901 if self.undef: self.undef = self.undef.split(',') - if self.swig_opts is None: - self.swig_opts = [] - else: - self.swig_opts = self.swig_opts.split(' ') - + self.swig_opts = [] if self.swig_opts is None else self.swig_opts.split(' ') # Finally add the user include and library directories if requested if self.user: user_include = os.path.join(USER_BASE, "include") @@ -344,7 +337,7 @@ def run(self): # noqa: C901 # Now actually compile and link everything. self.build_extensions() - def check_extensions_list(self, extensions): # noqa: C901 + def check_extensions_list(self, extensions): # noqa: C901 """Ensure that the list of extensions (presumably provided as a command option 'extensions') is valid, i.e. it is a list of Extension objects. We also support the old-style list of 2-tuples, @@ -416,14 +409,11 @@ def check_extensions_list(self, extensions): # noqa: C901 "'def_file' element of build info dict " "no longer supported" ) - # Non-trivial stuff: 'macros' split into 'define_macros' - # and 'undef_macros'. - macros = build_info.get('macros') - if macros: + if macros := build_info.get('macros'): ext.define_macros = [] ext.undef_macros = [] for macro in macros: - if not (isinstance(macro, tuple) and len(macro) in (1, 2)): + if not (isinstance(macro, tuple) and len(macro) in {1, 2}): raise DistutilsSetupError( "'macros' element of build info dict " "must be 1- or 2-tuple" @@ -450,13 +440,7 @@ def get_outputs(self): # can probably assume that it *isn't*!). self.check_extensions_list(self.extensions) - # And build the list of output (built) filenames. Note that this - # ignores the 'inplace' flag, and assumes everything goes in the - # "build" tree. - outputs = [] - for ext in self.extensions: - outputs.append(self.get_ext_fullpath(ext.name)) - return outputs + return [self.get_ext_fullpath(ext.name) for ext in self.extensions] def build_extensions(self): # First, sanity-check the 'extensions' list @@ -499,7 +483,7 @@ def _filter_build_errors(self, ext): except (CCompilerError, DistutilsError, CompileError) as e: if not ext.optional: raise - self.warn('building extension "{}" failed: {}'.format(ext.name, e)) + self.warn(f'building extension "{ext.name}" failed: {e}') def build_extension(self, ext): sources = ext.sources @@ -612,7 +596,7 @@ def swig_sources(self, sources, extension): for source in sources: (base, ext) = os.path.splitext(source) if ext == ".i": # SWIG interface file - new_sources.append(base + '_wrap' + target_ext) + new_sources.append(f'{base}_wrap{target_ext}') swig_sources.append(source) swig_targets[source] = new_sources[-1] else: @@ -629,9 +613,7 @@ def swig_sources(self, sources, extension): # Do not override commandline arguments if not self.swig_opts: - for o in extension.swig_opts: - swig_cmd.append(o) - + swig_cmd.extend(iter(extension.swig_opts)) for source in swig_sources: target = swig_targets[source] log.info("swigging %s to %s", source, target) @@ -683,7 +665,7 @@ def get_ext_fullpath(self, ext_name): # the inplace option requires to find the package directory # using the build_py command for that - package = '.'.join(modpath[0:-1]) + package = '.'.join(modpath[:-1]) build_py = self.get_finalized_command('build_py') package_dir = os.path.abspath(build_py.get_package_dir(package)) @@ -695,10 +677,7 @@ def get_ext_fullname(self, ext_name): """Returns the fullname of a given extension name. Adds the `package.` prefix""" - if self.package is None: - return ext_name - else: - return self.package + '.' + ext_name + return ext_name if self.package is None else f'{self.package}.{ext_name}' def get_ext_filename(self, ext_name): r"""Convert the name of an extension (eg. "foo.bar") into the name @@ -725,14 +704,14 @@ def get_export_symbols(self, ext): except UnicodeEncodeError: suffix = 'U_' + name.encode('punycode').replace(b'-', b'_').decode('ascii') else: - suffix = "_" + name + suffix = f"_{name}" - initfunc_name = "PyInit" + suffix + initfunc_name = f"PyInit{suffix}" if initfunc_name not in ext.export_symbols: ext.export_symbols.append(initfunc_name) return ext.export_symbols - def get_libraries(self, ext): # noqa: C901 + def get_libraries(self, ext): # noqa: C901 """Return the list of libraries to link against when building a shared extension. On most platforms, this is just 'ext.libraries'; on Windows, we add the Python library (eg. python20.dll). @@ -748,7 +727,7 @@ def get_libraries(self, ext): # noqa: C901 if not isinstance(self.compiler, MSVCCompiler): template = "python%d%d" if self.debug: - template = template + '_d' + template += '_d' pythonlib = template % ( sys.hexversion >> 24, (sys.hexversion >> 16) & 0xFF, @@ -783,6 +762,6 @@ def get_libraries(self, ext): # noqa: C901 if link_libpython: ldversion = get_config_var('LDVERSION') - return ext.libraries + ['python' + ldversion] + return ext.libraries + [f'python{ldversion}'] return ext.libraries + py37compat.pythonlib() diff --git a/setuptools/_distutils/command/build_py.py b/setuptools/_distutils/command/build_py.py index d9df95922f..f75c2c3f5e 100644 --- a/setuptools/_distutils/command/build_py.py +++ b/setuptools/_distutils/command/build_py.py @@ -151,37 +151,30 @@ def get_package_dir(self, package): path = package.split('.') if not self.package_dir: - if path: - return os.path.join(*path) + return os.path.join(*path) if path else '' + tail = [] + while path: + try: + pdir = self.package_dir['.'.join(path)] + except KeyError: + tail.insert(0, path[-1]) + del path[-1] else: - return '' + tail.insert(0, pdir) + return os.path.join(*tail) else: - tail = [] - while path: - try: - pdir = self.package_dir['.'.join(path)] - except KeyError: - tail.insert(0, path[-1]) - del path[-1] - else: - tail.insert(0, pdir) - return os.path.join(*tail) - else: - # Oops, got all the way through 'path' without finding a - # match in package_dir. If package_dir defines a directory - # for the root (nameless) package, then fallback on it; - # otherwise, we might as well have not consulted - # package_dir at all, as we just use the directory implied - # by 'tail' (which should be the same as the original value - # of 'path' at this point). - pdir = self.package_dir.get('') - if pdir is not None: - tail.insert(0, pdir) - - if tail: - return os.path.join(*tail) - else: - return '' + # Oops, got all the way through 'path' without finding a + # match in package_dir. If package_dir defines a directory + # for the root (nameless) package, then fallback on it; + # otherwise, we might as well have not consulted + # package_dir at all, as we just use the directory implied + # by 'tail' (which should be the same as the original value + # of 'path' at this point). + pdir = self.package_dir.get('') + if pdir is not None: + tail.insert(0, pdir) + + return os.path.join(*tail) if tail else '' def check_package(self, package, package_dir): # Empty dir name means current directory, which we can probably @@ -190,9 +183,7 @@ def check_package(self, package, package_dir): # circumvent them. if package_dir != "": if not os.path.exists(package_dir): - raise DistutilsFileError( - "package directory '%s' does not exist" % package_dir - ) + raise DistutilsFileError(f"package directory '{package_dir}' does not exist") if not os.path.isdir(package_dir): raise DistutilsFileError( "supposed package directory '%s' exists, " @@ -228,7 +219,7 @@ def find_package_modules(self, package, package_dir): module = os.path.splitext(os.path.basename(f))[0] modules.append((package, module, f)) else: - self.debug_print("excluding %s" % setup_script) + self.debug_print(f"excluding {setup_script}") return modules def find_modules(self): @@ -257,7 +248,7 @@ def find_modules(self): # - don't check for __init__.py in directory for empty package for module in self.py_modules: path = module.split('.') - package = '.'.join(path[0:-1]) + package = '.'.join(path[:-1]) module_base = path[-1] try: @@ -275,7 +266,7 @@ def find_modules(self): # XXX perhaps we should also check for just .pyc files # (so greedy closed-source bastards can distribute Python # modules too) - module_file = os.path.join(package_dir, module_base + ".py") + module_file = os.path.join(package_dir, f"{module_base}.py") if not self.check_module(module, module_file): continue @@ -303,7 +294,7 @@ def get_source_files(self): return [module[-1] for module in self.find_all_modules()] def get_module_outfile(self, build_dir, package, module): - outfile_path = [build_dir] + list(package) + [module + ".py"] + outfile_path = [build_dir] + list(package) + [f"{module}.py"] return os.path.join(*outfile_path) def get_outputs(self, include_bytecode=1): diff --git a/setuptools/_distutils/command/build_scripts.py b/setuptools/_distutils/command/build_scripts.py index 1a4d67f492..4c98fe9843 100644 --- a/setuptools/_distutils/command/build_scripts.py +++ b/setuptools/_distutils/command/build_scripts.py @@ -95,7 +95,7 @@ def _copy_script(self, script, outfiles, updated_files): # noqa: C901 else: first_line = f.readline() if not first_line: - self.warn("%s is an empty file (skipping)" % script) + self.warn(f"{script} is an empty file (skipping)") return shebang_match = shebang_pattern.match(first_line) @@ -109,14 +109,10 @@ def _copy_script(self, script, outfiles, updated_files): # noqa: C901 else: executable = os.path.join( sysconfig.get_config_var("BINDIR"), - "python%s%s" - % ( - sysconfig.get_config_var("VERSION"), - sysconfig.get_config_var("EXE"), - ), + f'python{sysconfig.get_config_var("VERSION")}{sysconfig.get_config_var("EXE")}', ) post_interp = shebang_match.group(1) or '' - shebang = "#!" + executable + post_interp + "\n" + shebang = f"#!{executable}{post_interp}" + "\n" self._validate_shebang(shebang, f.encoding) with open(outfile, "w", encoding=f.encoding) as outf: outf.write(shebang) diff --git a/setuptools/_distutils/command/check.py b/setuptools/_distutils/command/check.py index 575e49fb4b..0675f23ee8 100644 --- a/setuptools/_distutils/command/check.py +++ b/setuptools/_distutils/command/check.py @@ -99,23 +99,19 @@ def check_metadata(self): """ metadata = self.distribution.metadata - missing = [] - for attr in 'name', 'version': - if not getattr(metadata, attr, None): - missing.append(attr) - - if missing: - self.warn("missing required meta-data: %s" % ', '.join(missing)) + if missing := [ + attr + for attr in ('name', 'version') + if not getattr(metadata, attr, None) + ]: + self.warn(f"missing required meta-data: {', '.join(missing)}") def check_restructuredtext(self): """Checks if the long string fields are reST-compliant.""" data = self.distribution.get_long_description() for warning in self._check_rst_data(data): line = warning[-1].get('line') - if line is None: - warning = warning[1] - else: - warning = '{} (line {})'.format(warning[1], line) + warning = warning[1] if line is None else f'{warning[1]} (line {line})' self.warn(warning) def _check_rst_data(self, data): @@ -144,8 +140,6 @@ def _check_rst_data(self, data): try: parser.parse(data, document) except AttributeError as e: - reporter.messages.append( - (-1, 'Could not finish the parsing: %s.' % e, '', {}) - ) + reporter.messages.append((-1, f'Could not finish the parsing: {e}.', '', {})) return reporter.messages diff --git a/setuptools/_distutils/command/config.py b/setuptools/_distutils/command/config.py index 494d97d16f..7f49162be3 100644 --- a/setuptools/_distutils/command/config.py +++ b/setuptools/_distutils/command/config.py @@ -101,7 +101,7 @@ def _check_compiler(self): self.compiler.set_library_dirs(self.library_dirs) def _gen_temp_sourcefile(self, body, headers, lang): - filename = "_configtest" + LANG_EXT[lang] + filename = f"_configtest{LANG_EXT[lang]}" with open(filename, "w") as file: if headers: for header in headers: @@ -122,7 +122,7 @@ def _preprocess(self, body, headers, include_dirs, lang): def _compile(self, body, headers, include_dirs, lang): src = self._gen_temp_sourcefile(body, headers, lang) if self.dump_source: - dump_file(src, "compiling '%s':" % src) + dump_file(src, f"compiling '{src}':") (obj,) = self.compiler.object_filenames([src]) self.temp_files.extend([src, obj]) self.compiler.compile([src], include_dirs=include_dirs) @@ -314,12 +314,12 @@ def check_func( self._check_compiler() body = [] if decl: - body.append("int %s ();" % func) + body.append(f"int {func} ();") body.append("int main () {") if call: - body.append(" %s();" % func) + body.append(f" {func}();") else: - body.append(" %s;" % func) + body.append(f" {func};") body.append("}") body = "\n".join(body) + "\n" diff --git a/setuptools/_distutils/command/install.py b/setuptools/_distutils/command/install.py index a7ac4e6077..61416c4cda 100644 --- a/setuptools/_distutils/command/install.py +++ b/setuptools/_distutils/command/install.py @@ -121,10 +121,7 @@ def _load_schemes(): def _get_implementation(): - if hasattr(sys, 'pypy_version_info'): - return 'PyPy' - else: - return 'Python' + return 'PyPy' if hasattr(sys, 'pypy_version_info') else 'Python' def _select_scheme(ob, name): @@ -516,11 +513,11 @@ def dump_dirs(self, msg): return from ..fancy_getopt import longopt_xlate - log.debug(msg + ":") + log.debug(f"{msg}:") for opt in self.user_options: opt_name = opt[0] if opt_name[-1] == "=": - opt_name = opt_name[0:-1] + opt_name = opt_name[:-1] if opt_name in self.negative_opt: opt_name = self.negative_opt[opt_name] opt_name = opt_name.translate(longopt_xlate) @@ -571,9 +568,8 @@ def finalize_unix(self): self.prefix = os.path.normpath(sys.prefix) + _prefix_addition self.exec_prefix = os.path.normpath(sys.exec_prefix) + _prefix_addition - else: - if self.exec_prefix is None: - self.exec_prefix = self.prefix + elif self.exec_prefix is None: + self.exec_prefix = self.prefix self.install_base = self.prefix self.install_platbase = self.exec_prefix @@ -585,7 +581,7 @@ def finalize_other(self): if self.install_userbase is None: raise DistutilsPlatformError("User base directory is not specified") self.install_base = self.install_platbase = self.install_userbase - self.select_scheme(os.name + "_user") + self.select_scheme(f"{os.name}_user") elif self.home is not None: self.install_base = self.install_platbase = self.home self.select_scheme("posix_home") @@ -598,7 +594,7 @@ def finalize_other(self): self.select_scheme(os.name) except KeyError: raise DistutilsPlatformError( - "I don't know how to install stuff on '%s'" % os.name + f"I don't know how to install stuff on '{os.name}'" ) def select_scheme(self, name): @@ -608,7 +604,7 @@ def _expand_attrs(self, attrs): for attr in attrs: val = getattr(self, attr) if val is not None: - if os.name in ('posix', 'nt'): + if os.name in {'posix', 'nt'}: val = os.path.expanduser(val) val = subst_vars(val, self.config_vars) setattr(self, attr, val) @@ -634,7 +630,7 @@ def expand_dirs(self): def convert_paths(self, *names): """Call `convert_path` over `names`.""" for name in names: - attr = "install_" + name + attr = f"install_{name}" setattr(self, attr, convert_path(getattr(self, attr))) def handle_extra_path(self): @@ -675,7 +671,7 @@ def handle_extra_path(self): def change_roots(self, *names): """Change the install directories pointed by name using root.""" for name in names: - attr = "install_" + name + attr = f"install_{name}" setattr(self, attr, change_root(self.root, getattr(self, attr))) def create_home_path(self): @@ -685,7 +681,7 @@ def create_home_path(self): home = convert_path(os.path.expanduser("~")) for name, path in self.config_vars.items(): if str(path).startswith(home) and not os.path.isdir(path): - self.debug_print("os.makedirs('%s', 0o700)" % path) + self.debug_print(f"os.makedirs('{path}', 0o700)") os.makedirs(path, 0o700) # -- Command execution methods ------------------------------------- @@ -720,7 +716,7 @@ def run(self): self.execute( write_file, (self.record, outputs), - "writing list of installed files to '%s'" % self.record, + f"writing list of installed files to '{self.record}'", ) sys_path = map(os.path.normpath, sys.path) @@ -742,13 +738,11 @@ def run(self): def create_path_file(self): """Creates the .pth file""" - filename = os.path.join(self.install_libbase, self.path_file + ".pth") + filename = os.path.join(self.install_libbase, f"{self.path_file}.pth") if self.install_path_file: - self.execute( - write_file, (filename, [self.extra_dirs]), "creating %s" % filename - ) + self.execute(write_file, (filename, [self.extra_dirs]), f"creating {filename}") else: - self.warn("path file '%s' not created" % filename) + self.warn(f"path file '{filename}' not created") # -- Reporting methods --------------------------------------------- @@ -764,7 +758,7 @@ def get_outputs(self): outputs.append(filename) if self.path_file and self.install_path_file: - outputs.append(os.path.join(self.install_libbase, self.path_file + ".pth")) + outputs.append(os.path.join(self.install_libbase, f"{self.path_file}.pth")) return outputs diff --git a/setuptools/_distutils/command/install_egg_info.py b/setuptools/_distutils/command/install_egg_info.py index f3e8f3447d..89cdc31d45 100644 --- a/setuptools/_distutils/command/install_egg_info.py +++ b/setuptools/_distutils/command/install_egg_info.py @@ -47,11 +47,9 @@ def run(self): if os.path.isdir(target) and not os.path.islink(target): dir_util.remove_tree(target, dry_run=self.dry_run) elif os.path.exists(target): - self.execute(os.unlink, (self.target,), "Removing " + target) + self.execute(os.unlink, (self.target,), f"Removing {target}") elif not os.path.isdir(self.install_dir): - self.execute( - os.makedirs, (self.install_dir,), "Creating " + self.install_dir - ) + self.execute(os.makedirs, (self.install_dir,), f"Creating {self.install_dir}") log.info("Writing %s", target) if not self.dry_run: with open(target, 'w', encoding='UTF-8') as f: diff --git a/setuptools/_distutils/command/install_lib.py b/setuptools/_distutils/command/install_lib.py index be4c243321..60e59e4a66 100644 --- a/setuptools/_distutils/command/install_lib.py +++ b/setuptools/_distutils/command/install_lib.py @@ -114,9 +114,7 @@ def install(self): if os.path.isdir(self.build_dir): outfiles = self.copy_tree(self.build_dir, self.install_dir) else: - self.warn( - "'%s' does not exist -- no Python modules to install" % self.build_dir - ) + self.warn(f"'{self.build_dir}' does not exist -- no Python modules to install") return return outfiles @@ -162,11 +160,7 @@ def _mutate_outputs(self, has_any, build_cmd, cmd_option, output_dir): build_dir = getattr(build_cmd, cmd_option) prefix_len = len(build_dir) + len(os.sep) - outputs = [] - for file in build_files: - outputs.append(os.path.join(output_dir, file[prefix_len:])) - - return outputs + return [os.path.join(output_dir, file[prefix_len:]) for file in build_files] def _bytecode_filenames(self, py_filenames): bytecode_files = [] diff --git a/setuptools/_distutils/command/py37compat.py b/setuptools/_distutils/command/py37compat.py index aa0c0a7fcd..4d68a4fc3b 100644 --- a/setuptools/_distutils/command/py37compat.py +++ b/setuptools/_distutils/command/py37compat.py @@ -11,11 +11,7 @@ def _pythonlib_compat(): if not sysconfig.get_config_var('Py_ENABLED_SHARED'): return - yield 'python{}.{}{}'.format( - sys.hexversion >> 24, - (sys.hexversion >> 16) & 0xFF, - sysconfig.get_config_var('ABIFLAGS'), - ) + yield f"python{sys.hexversion >> 24}.{sys.hexversion >> 16 & 255}{sysconfig.get_config_var('ABIFLAGS')}" def compose(f1, f2): diff --git a/setuptools/_distutils/command/register.py b/setuptools/_distutils/command/register.py index c19aabb91f..995bc28daa 100644 --- a/setuptools/_distutils/command/register.py +++ b/setuptools/_distutils/command/register.py @@ -87,14 +87,14 @@ def _set_config(self): self.has_config = True else: if self.repository not in ('pypi', self.DEFAULT_REPOSITORY): - raise ValueError('%s not found in .pypirc' % self.repository) + raise ValueError(f'{self.repository} not found in .pypirc') if self.repository == 'pypi': self.repository = self.DEFAULT_REPOSITORY self.has_config = False def classifiers(self): '''Fetch the list of classifiers from the server.''' - url = self.repository + '?:action=list_classifiers' + url = f'{self.repository}?:action=list_classifiers' response = urllib.request.urlopen(url) log.info(self._read_pypi_response(response)) @@ -104,7 +104,7 @@ def verify_metadata(self): (code, result) = self.post_to_server(self.build_post_data('verify')) log.info('Server response (%s): %s', code, result) - def send_metadata(self): # noqa: C901 + def send_metadata(self): # noqa: C901 '''Send the metadata to the package index server. Well, do the following: @@ -174,7 +174,7 @@ def send_metadata(self): # noqa: C901 auth.add_password(self.realm, host, username, password) # send the info to the server and report the result code, result = self.post_to_server(self.build_post_data('submit'), auth) - self.announce('Server response ({}): {}'.format(code, result), logging.INFO) + self.announce(f'Server response ({code}): {result}', logging.INFO) # possibly save the login if code == 200: @@ -191,7 +191,7 @@ def send_metadata(self): # noqa: C901 logging.INFO, ) self.announce( - '(the login will be stored in %s)' % self._get_rc_file(), + f'(the login will be stored in {self._get_rc_file()})', logging.INFO, ) choice = 'X' @@ -226,8 +226,7 @@ def send_metadata(self): # noqa: C901 log.info('You will receive an email shortly.') log.info('Follow the instructions in it to ' 'complete registration.') elif choice == '3': - data = {':action': 'password_reset'} - data['email'] = '' + data = {':action': 'password_reset', 'email': ''} while not data['email']: data['email'] = input('Your email address: ') code, result = self.post_to_server(data) @@ -261,17 +260,14 @@ def build_post_data(self, action): data['metadata_version'] = '1.1' return data - def post_to_server(self, data, auth=None): # noqa: C901 + def post_to_server(self, data, auth=None): # noqa: C901 '''Post a query to the server, and return a string response.''' if 'name' in data: - self.announce( - 'Registering {} to {}'.format(data['name'], self.repository), - logging.INFO, - ) + self.announce(f"Registering {data['name']} to {self.repository}", logging.INFO) # Build up the MIME payload for the urllib2 POST data boundary = '--------------GHSKFJDLGDS7543FJKLFHRE75642756743254' sep_boundary = '\n--' + boundary - end_boundary = sep_boundary + '--' + end_boundary = f'{sep_boundary}--' body = io.StringIO() for key, value in data.items(): # handle multiple entries for the same name @@ -291,8 +287,7 @@ def post_to_server(self, data, auth=None): # noqa: C901 # build the Request headers = { - 'Content-type': 'multipart/form-data; boundary=%s; charset=utf-8' - % boundary, + 'Content-type': f'multipart/form-data; boundary={boundary}; charset=utf-8', 'Content-length': str(len(body)), } req = urllib.request.Request(self.repository, body, headers) diff --git a/setuptools/_distutils/command/sdist.py b/setuptools/_distutils/command/sdist.py index ac489726ca..cb2cb7042f 100644 --- a/setuptools/_distutils/command/sdist.py +++ b/setuptools/_distutils/command/sdist.py @@ -25,9 +25,10 @@ def show_formats(): from ..fancy_getopt import FancyGetopt from ..archive_util import ARCHIVE_FORMATS - formats = [] - for format in ARCHIVE_FORMATS.keys(): - formats.append(("formats=" + format, None, ARCHIVE_FORMATS[format][2])) + formats = [ + (f"formats={format}", None, ARCHIVE_FORMATS[format][2]) + for format in ARCHIVE_FORMATS.keys() + ] formats.sort() FancyGetopt(formats).print_help("List of available source distribution formats:") @@ -149,9 +150,8 @@ def finalize_options(self): self.ensure_string_list('formats') - bad_format = archive_util.check_archive_formats(self.formats) - if bad_format: - raise DistutilsOptionError("unknown archive format '%s'" % bad_format) + if bad_format := archive_util.check_archive_formats(self.formats): + raise DistutilsOptionError(f"unknown archive format '{bad_format}'") if self.dist_dir is None: self.dist_dir = "dist" @@ -285,11 +285,10 @@ def _add_defaults_standards(self): self.warn( "standard file not found: should have one of " + ', '.join(alts) ) + elif self._cs_path_exists(fn): + self.filelist.append(fn) else: - if self._cs_path_exists(fn): - self.filelist.append(fn) - else: - self.warn("standard file '%s' not found" % fn) + self.warn(f"standard file '{fn}' not found") def _add_defaults_optional(self): optional = ['tests/test*.py', 'test/test*.py', 'setup.cfg'] @@ -315,20 +314,21 @@ def _add_defaults_python(self): def _add_defaults_data_files(self): # getting distribution.data_files - if self.distribution.has_data_files(): - for item in self.distribution.data_files: - if isinstance(item, str): - # plain file - item = convert_path(item) - if os.path.isfile(item): - self.filelist.append(item) - else: - # a (dirname, filenames) tuple - dirname, filenames = item - for f in filenames: - f = convert_path(f) - if os.path.isfile(f): - self.filelist.append(f) + if not self.distribution.has_data_files(): + return + for item in self.distribution.data_files: + if isinstance(item, str): + # plain file + item = convert_path(item) + if os.path.isfile(item): + self.filelist.append(item) + else: + # a (dirname, filenames) tuple + dirname, filenames = item + for f in filenames: + f = convert_path(f) + if os.path.isfile(f): + self.filelist.append(f) def _add_defaults_ext(self): if self.distribution.has_ext_modules(): @@ -395,13 +395,9 @@ def prune_file_list(self): self.filelist.exclude_pattern(None, prefix=build.build_base) self.filelist.exclude_pattern(None, prefix=base_dir) - if sys.platform == 'win32': - seps = r'/|\\' - else: - seps = '/' - + seps = r'/|\\' if sys.platform == 'win32' else '/' vcs_dirs = ['RCS', 'CVS', r'\.svn', r'\.hg', r'\.git', r'\.bzr', '_darcs'] - vcs_ptrn = r'(^|{})({})({}).*'.format(seps, '|'.join(vcs_dirs), seps) + vcs_ptrn = f"(^|{seps})({'|'.join(vcs_dirs)})({seps}).*" self.filelist.exclude_pattern(vcs_ptrn, is_regex=1) def write_manifest(self): @@ -421,7 +417,7 @@ def write_manifest(self): self.execute( file_util.write_file, (self.manifest, content), - "writing manifest file '%s'" % self.manifest, + f"writing manifest file '{self.manifest}'", ) def _manifest_is_not_generated(self): @@ -474,10 +470,10 @@ def make_release_tree(self, base_dir, files): if hasattr(os, 'link'): # can make hard links on this system link = 'hard' - msg = "making hard links in %s..." % base_dir + msg = f"making hard links in {base_dir}..." else: # nope, have to copy link = None - msg = "copying files to %s..." % base_dir + msg = f"copying files to {base_dir}..." if not files: log.warning("no files to distribute -- empty manifest?") diff --git a/setuptools/_distutils/command/upload.py b/setuptools/_distutils/command/upload.py index caf15f04a6..256bf4be60 100644 --- a/setuptools/_distutils/command/upload.py +++ b/setuptools/_distutils/command/upload.py @@ -74,10 +74,10 @@ def upload_file(self, command, pyversion, filename): # noqa: C901 # Makes sure the repository URL is compliant schema, netloc, url, params, query, fragments = urlparse(self.repository) if params or query or fragments: - raise AssertionError("Incompatible url %s" % self.repository) + raise AssertionError(f"Incompatible url {self.repository}") if schema not in ('http', 'https'): - raise AssertionError("unsupported schema " + schema) + raise AssertionError(f"unsupported schema {schema}") # Sign if requested if self.sign: @@ -96,17 +96,13 @@ def upload_file(self, command, pyversion, filename): # noqa: C901 meta = self.distribution.metadata data = { - # action ':action': 'file_upload', 'protocol_version': '1', - # identify release 'name': meta.get_name(), 'version': meta.get_version(), - # file content 'content': (os.path.basename(filename), content), 'filetype': command, 'pyversion': pyversion, - # additional meta-data 'metadata_version': '1.0', 'summary': meta.get_description(), 'home_page': meta.get_url(), @@ -118,14 +114,12 @@ def upload_file(self, command, pyversion, filename): # noqa: C901 'platform': meta.get_platforms(), 'classifiers': meta.get_classifiers(), 'download_url': meta.get_download_url(), - # PEP 314 'provides': meta.get_provides(), 'requires': meta.get_requires(), 'obsoletes': meta.get_obsoletes(), + 'comment': '', } - data['comment'] = '' - # file content digests for digest_name, digest_cons in _FILE_CONTENT_DIGESTS.items(): if digest_cons is None: @@ -137,11 +131,11 @@ def upload_file(self, command, pyversion, filename): # noqa: C901 pass if self.sign: - with open(filename + ".asc", "rb") as f: - data['gpg_signature'] = (os.path.basename(filename) + ".asc", f.read()) + with open(f"{filename}.asc", "rb") as f: + data['gpg_signature'] = f"{os.path.basename(filename)}.asc", f.read() # set up the authentication - user_pass = (self.username + ":" + self.password).encode('ascii') + user_pass = f"{self.username}:{self.password}".encode('ascii') # The exact encoding of the authentication string is debated. # Anyway PyPI only accepts ascii for both username or password. auth = "Basic " + standard_b64encode(user_pass).decode('ascii') @@ -158,7 +152,7 @@ def upload_file(self, command, pyversion, filename): # noqa: C901 value = [value] for value in value: if type(value) is tuple: - title += '; filename="%s"' % value[0] + title += f'; filename="{value[0]}"' value = value[1] else: value = str(value).encode('utf-8') @@ -169,12 +163,12 @@ def upload_file(self, command, pyversion, filename): # noqa: C901 body.write(end_boundary) body = body.getvalue() - msg = "Submitting {} to {}".format(filename, self.repository) + msg = f"Submitting {filename} to {self.repository}" self.announce(msg, logging.INFO) # build the Request headers = { - 'Content-type': 'multipart/form-data; boundary=%s' % boundary, + 'Content-type': f'multipart/form-data; boundary={boundary}', 'Content-length': str(len(body)), 'Authorization': auth, } @@ -193,14 +187,12 @@ def upload_file(self, command, pyversion, filename): # noqa: C901 raise if status == 200: - self.announce( - 'Server response ({}): {}'.format(status, reason), logging.INFO - ) + self.announce(f'Server response ({status}): {reason}', logging.INFO) if self.show_response: text = self._read_pypi_response(result) msg = '\n'.join(('-' * 75, text, '-' * 75)) self.announce(msg, logging.INFO) else: - msg = 'Upload failed ({}): {}'.format(status, reason) + msg = f'Upload failed ({status}): {reason}' self.announce(msg, logging.ERROR) raise DistutilsError(msg) diff --git a/setuptools/_distutils/config.py b/setuptools/_distutils/config.py index 9a4044adaf..a05e855d37 100644 --- a/setuptools/_distutils/config.py +++ b/setuptools/_distutils/config.py @@ -44,11 +44,11 @@ def _store_pypirc(self, username, password): with os.fdopen(os.open(rc, os.O_CREAT | os.O_WRONLY, 0o600), 'w') as f: f.write(DEFAULT_PYPIRC % (username, password)) - def _read_pypirc(self): # noqa: C901 + def _read_pypirc(self): # noqa: C901 """Reads the .pypirc file.""" rc = self._get_rc_file() if os.path.exists(rc): - self.announce('Using PyPI login from %s' % rc) + self.announce(f'Using PyPI login from {rc}') repository = self.repository or self.DEFAULT_REPOSITORY config = RawConfigParser() @@ -62,7 +62,7 @@ def _read_pypirc(self): # noqa: C901 for server in index_servers.split('\n') if server.strip() != '' ] - if _servers == []: + if not _servers: # nothing set, let's try to get the default pypi if 'pypi' in sections: _servers = ['pypi'] @@ -71,9 +71,7 @@ def _read_pypirc(self): # noqa: C901 # an empty dict return {} for server in _servers: - current = {'server': server} - current['username'] = config.get(server, 'username') - + current = {'server': server, 'username': config.get(server, 'username')} # optional params for key, default in ( ('repository', self.DEFAULT_REPOSITORY), diff --git a/setuptools/_distutils/core.py b/setuptools/_distutils/core.py index 05d2971994..4d24d68ccd 100644 --- a/setuptools/_distutils/core.py +++ b/setuptools/_distutils/core.py @@ -93,7 +93,7 @@ def gen_usage(script_name): ) -def setup(**attrs): # noqa: C901 +def setup(**attrs): # noqa: C901 """The gateway to the Distutils: do everything your setup script needs to do, in a highly flexible and user-driven way. Briefly: create a Distribution instance; find and parse config files; parse the command @@ -147,9 +147,9 @@ class found in 'cmdclass' is used in place of the default, which is _setup_distribution = dist = klass(attrs) except DistutilsSetupError as msg: if 'name' not in attrs: - raise SystemExit("error in setup command: %s" % msg) + raise SystemExit(f"error in setup command: {msg}") else: - raise SystemExit("error in {} setup command: {}".format(attrs['name'], msg)) + raise SystemExit(f"error in {attrs['name']} setup command: {msg}") if _setup_stop_after == "init": return dist @@ -181,10 +181,7 @@ class found in 'cmdclass' is used in place of the default, which is return dist # And finally, run all the commands found on the command line. - if ok: - return run_commands(dist) - - return dist + return run_commands(dist) if ok else dist # setup () @@ -202,17 +199,16 @@ def run_commands(dist): except KeyboardInterrupt: raise SystemExit("interrupted") except OSError as exc: - if DEBUG: - sys.stderr.write("error: {}\n".format(exc)) - raise - else: - raise SystemExit("error: {}".format(exc)) + if not DEBUG: + raise SystemExit(f"error: {exc}") + sys.stderr.write(f"error: {exc}\n") + raise except (DistutilsError, CCompilerError) as msg: if DEBUG: raise else: - raise SystemExit("error: " + str(msg)) + raise SystemExit(f"error: {str(msg)}") return dist diff --git a/setuptools/_distutils/cygwinccompiler.py b/setuptools/_distutils/cygwinccompiler.py index 47efa377c5..6a15fb3a25 100644 --- a/setuptools/_distutils/cygwinccompiler.py +++ b/setuptools/_distutils/cygwinccompiler.py @@ -61,7 +61,7 @@ def get_msvcr(): try: return _msvcr_lookup[msc_ver] except KeyError: - raise ValueError("Unknown MS Compiler version %s " % msc_ver) + raise ValueError(f"Unknown MS Compiler version {msc_ver} ") _runtime_library_dirs_msg = ( @@ -87,28 +87,24 @@ def __init__(self, verbose=0, dry_run=0, force=0): super().__init__(verbose, dry_run, force) status, details = check_config_h() - self.debug_print( - "Python's GCC status: {} (details: {})".format(status, details) - ) + self.debug_print(f"Python's GCC status: {status} (details: {details})") if status is not CONFIG_H_OK: self.warn( - "Python's pyconfig.h doesn't seem to support your compiler. " - "Reason: %s. " - "Compiling may fail because of undefined preprocessor macros." % details + f"Python's pyconfig.h doesn't seem to support your compiler. Reason: {details}. Compiling may fail because of undefined preprocessor macros." ) self.cc = os.environ.get('CC', 'gcc') self.cxx = os.environ.get('CXX', 'g++') - self.linker_dll = self.cc shared_option = "-shared" + self.linker_dll = self.cc self.set_executables( - compiler='%s -mcygwin -O -Wall' % self.cc, - compiler_so='%s -mcygwin -mdll -O -Wall' % self.cc, - compiler_cxx='%s -mcygwin -O -Wall' % self.cxx, - linker_exe='%s -mcygwin' % self.cc, - linker_so=('{} -mcygwin {}'.format(self.linker_dll, shared_option)), + compiler=f'{self.cc} -mcygwin -O -Wall', + compiler_so=f'{self.cc} -mcygwin -mdll -O -Wall', + compiler_cxx=f'{self.cxx} -mcygwin -O -Wall', + linker_exe=f'{self.cc} -mcygwin', + linker_so=f'{self.linker_dll} -mcygwin {shared_option}', ) # Include the appropriate MSVC runtime library if Python was built @@ -194,13 +190,12 @@ def link( ) # generate the filenames for these files - def_file = os.path.join(temp_dir, dll_name + ".def") + def_file = os.path.join(temp_dir, f"{dll_name}.def") # Generate .def file - contents = ["LIBRARY %s" % os.path.basename(output_filename), "EXPORTS"] - for sym in export_symbols: - contents.append(sym) - self.execute(write_file, (def_file, contents), "writing %s" % def_file) + contents = [f"LIBRARY {os.path.basename(output_filename)}", "EXPORTS"] + contents.extend(iter(export_symbols)) + self.execute(write_file, (def_file, contents), f"writing {def_file}") # next add options for def-file @@ -270,17 +265,17 @@ class Mingw32CCompiler(CygwinCCompiler): def __init__(self, verbose=0, dry_run=0, force=0): super().__init__(verbose, dry_run, force) - shared_option = "-shared" - if is_cygwincc(self.cc): raise CCompilerError('Cygwin gcc cannot be used with --compiler=mingw32') + shared_option = "-shared" + self.set_executables( - compiler='%s -O -Wall' % self.cc, - compiler_so='%s -mdll -O -Wall' % self.cc, - compiler_cxx='%s -O -Wall' % self.cxx, - linker_exe='%s' % self.cc, - linker_so='{} {}'.format(self.linker_dll, shared_option), + compiler=f'{self.cc} -O -Wall', + compiler_so=f'{self.cc} -mdll -O -Wall', + compiler_cxx=f'{self.cxx} -O -Wall', + linker_exe=f'{self.cc}', + linker_so=f'{self.linker_dll} {shared_option}', ) def runtime_library_dir_option(self, dir): @@ -334,13 +329,13 @@ def check_config_h(): config_h = open(fn) try: if "__GNUC__" in config_h.read(): - return CONFIG_H_OK, "'%s' mentions '__GNUC__'" % fn + return CONFIG_H_OK, f"'{fn}' mentions '__GNUC__'" else: - return CONFIG_H_NOTOK, "'%s' does not mention '__GNUC__'" % fn + return CONFIG_H_NOTOK, f"'{fn}' does not mention '__GNUC__'" finally: config_h.close() except OSError as exc: - return (CONFIG_H_UNCERTAIN, "couldn't read '{}': {}".format(fn, exc.strerror)) + return CONFIG_H_UNCERTAIN, f"couldn't read '{fn}': {exc.strerror}" def is_cygwincc(cc): diff --git a/setuptools/_distutils/dir_util.py b/setuptools/_distutils/dir_util.py index 23dc3392a2..7b45bbf7eb 100644 --- a/setuptools/_distutils/dir_util.py +++ b/setuptools/_distutils/dir_util.py @@ -12,7 +12,7 @@ _path_created = {} -def mkpath(name, mode=0o777, verbose=1, dry_run=0): # noqa: C901 +def mkpath(name, mode=0o777, verbose=1, dry_run=0): # noqa: C901 """Create a directory and any missing ancestor directories. If the directory already exists (or if 'name' is the empty string, which @@ -75,9 +75,7 @@ def mkpath(name, mode=0o777, verbose=1, dry_run=0): # noqa: C901 os.mkdir(head, mode) except OSError as exc: if not (exc.errno == errno.EEXIST and os.path.isdir(head)): - raise DistutilsFileError( - "could not create '{}': {}".format(head, exc.args[-1]) - ) + raise DistutilsFileError(f"could not create '{head}': {exc.args[-1]}") created_dirs.append(head) _path_created[abs_head] = 1 @@ -94,11 +92,7 @@ def create_tree(base_dir, files, mode=0o777, verbose=1, dry_run=0): will be created if it doesn't already exist. 'mode', 'verbose' and 'dry_run' flags are as for 'mkpath()'. """ - # First get the list of directories to create - need_dir = set() - for file in files: - need_dir.add(os.path.join(base_dir, os.path.dirname(file))) - + need_dir = {os.path.join(base_dir, os.path.dirname(file)) for file in files} # Now create them for dir in sorted(need_dir): mkpath(dir, mode, verbose=verbose, dry_run=dry_run) @@ -136,16 +130,14 @@ def copy_tree( # noqa: C901 from distutils.file_util import copy_file if not dry_run and not os.path.isdir(src): - raise DistutilsFileError("cannot copy tree '%s': not a directory" % src) + raise DistutilsFileError(f"cannot copy tree '{src}': not a directory") try: names = os.listdir(src) except OSError as e: if dry_run: names = [] else: - raise DistutilsFileError( - "error listing files in '{}': {}".format(src, e.strerror) - ) + raise DistutilsFileError(f"error listing files in '{src}': {e.strerror}") if not dry_run: mkpath(dst, verbose=verbose) @@ -238,6 +230,6 @@ def ensure_relative(path): This is useful to make 'path' the second argument to os.path.join(). """ drive, path = os.path.splitdrive(path) - if path[0:1] == os.sep: + if path[:1] == os.sep: path = drive + path[1:] return path diff --git a/setuptools/_distutils/dist.py b/setuptools/_distutils/dist.py index 7c0f0e5b78..51472218c4 100644 --- a/setuptools/_distutils/dist.py +++ b/setuptools/_distutils/dist.py @@ -124,7 +124,7 @@ class Distribution: # -- Creation/initialization methods ------------------------------- - def __init__(self, attrs=None): # noqa: C901 + def __init__(self, attrs=None): # noqa: C901 """Construct a new Distribution instance: initialize all the attributes of a Distribution, and then use 'attrs' (a dictionary mapping attribute names to values) to assign some of those @@ -149,7 +149,7 @@ def __init__(self, attrs=None): # noqa: C901 # object in a sneaky and underhanded (but efficient!) way. self.metadata = DistributionMetadata() for basename in self.metadata._METHOD_BASENAMES: - method_name = "get_" + basename + method_name = f"get_{basename}" setattr(self, method_name, getattr(self.metadata, method_name)) # 'cmdclass' maps command names to class objects, so we @@ -254,14 +254,14 @@ def __init__(self, attrs=None): # noqa: C901 # Now work on the rest of the attributes. Any attribute that's # not already defined is invalid! for key, val in attrs.items(): - if hasattr(self.metadata, "set_" + key): - getattr(self.metadata, "set_" + key)(val) + if hasattr(self.metadata, f"set_{key}"): + getattr(self.metadata, f"set_{key}")(val) elif hasattr(self.metadata, key): setattr(self.metadata, key, val) elif hasattr(self, key): setattr(self, key, val) else: - msg = "Unknown distribution option: %s" % repr(key) + msg = f"Unknown distribution option: {repr(key)}" warnings.warn(msg) # no-user-cfg is handled before other command line args @@ -301,21 +301,21 @@ def dump_option_dicts(self, header=None, commands=None, indent=""): if header is not None: self.announce(indent + header) - indent = indent + " " + indent = f"{indent} " if not commands: - self.announce(indent + "no commands known yet") + self.announce(f"{indent}no commands known yet") return for cmd_name in commands: opt_dict = self.command_options.get(cmd_name) if opt_dict is None: - self.announce(indent + "no option dict for '%s' command" % cmd_name) + self.announce(f"{indent}no option dict for '{cmd_name}' command") else: - self.announce(indent + "option dict for '%s' command:" % cmd_name) + self.announce(f"{indent}option dict for '{cmd_name}' command:") out = pformat(opt_dict) for line in out.split('\n'): - self.announce(indent + " " + line) + self.announce(f"{indent} {line}") # -- Config file finding/parsing methods --------------------------- @@ -338,7 +338,7 @@ def find_config_files(self): files = [str(path) for path in self._gen_paths() if os.path.isfile(path)] if DEBUG: - self.announce("using config files: %s" % ', '.join(files)) + self.announce(f"using config files: {', '.join(files)}") return files @@ -347,10 +347,10 @@ def _gen_paths(self): sys_dir = pathlib.Path(sys.modules['distutils'].__file__).parent yield sys_dir / "distutils.cfg" - # The per-user config file - prefix = '.' * (os.name == 'posix') - filename = prefix + 'pydistutils.cfg' if self.want_user_cfg: + # The per-user config file + prefix = '.' * (os.name == 'posix') + filename = f'{prefix}pydistutils.cfg' yield pathlib.Path('~').expanduser() / filename # All platforms support local setup.cfg @@ -394,7 +394,7 @@ def parse_config_files(self, filenames=None): # noqa: C901 parser = ConfigParser() for filename in filenames: if DEBUG: - self.announce(" reading %s" % filename) + self.announce(f" reading {filename}") parser.read(filename) for section in parser.sections(): options = parser.options(section) @@ -484,7 +484,7 @@ def parse_command_line(self): # each command listed on the command line. if self.help: self._show_help( - parser, display_options=len(self.commands) == 0, commands=self.commands + parser, display_options=not self.commands, commands=self.commands ) return @@ -509,7 +509,7 @@ def _get_toplevel_options(self): ), ] - def _parse_command_opts(self, parser, args): # noqa: C901 + def _parse_command_opts(self, parser, args): # noqa: C901 """Parse the command-line options for a single command. 'parser' must be a FancyGetopt instance; 'args' must be the list of arguments, starting with the current command (whose options @@ -524,7 +524,7 @@ def _parse_command_opts(self, parser, args): # noqa: C901 # Pull the current command from the head of the command line command = args[0] if not command_re.match(command): - raise SystemExit("invalid command name '%s'" % command) + raise SystemExit(f"invalid command name '{command}'") self.commands.append(command) # Dig up the command class that implements this command, so we @@ -538,9 +538,7 @@ def _parse_command_opts(self, parser, args): # noqa: C901 # Require that the command class be derived from Command -- want # to be sure that the basic "command" interface is implemented. if not issubclass(cmd_class, Command): - raise DistutilsClassError( - "command class %s must subclass Command" % cmd_class - ) + raise DistutilsClassError(f"command class {cmd_class} must subclass Command") # Also make sure that the command object provides a list of its # known options. @@ -666,7 +664,7 @@ def _show_help(self, parser, global_options=1, display_options=1, commands=[]): ) else: parser.set_option_table(klass.user_options) - parser.print_help("Options for '%s' command:" % klass.__name__) + parser.print_help(f"Options for '{klass.__name__}' command:") print('') print(gen_usage(self.script_name)) @@ -692,14 +690,11 @@ def handle_display_options(self, option_order): # display that metadata in the order in which the user supplied the # metadata options. any_display_options = 0 - is_display_option = {} - for option in self.display_options: - is_display_option[option[0]] = 1 - + is_display_option = {option[0]: 1 for option in self.display_options} for opt, val in option_order: if val and is_display_option.get(opt): opt = translate_longopt(opt) - value = getattr(self.metadata, "get_" + opt)() + value = getattr(self.metadata, f"get_{opt}")() if opt in ('keywords', 'platforms'): print(','.join(value)) elif opt in ('classifiers', 'provides', 'requires', 'obsoletes'): @@ -714,7 +709,7 @@ def print_command_list(self, commands, header, max_length): """Print a subset of the list of all commands -- used by 'print_commands()'. """ - print(header + ":") + print(f"{header}:") for cmd in commands: klass = self.cmdclass.get(cmd) @@ -738,15 +733,8 @@ def print_commands(self): import distutils.command std_commands = distutils.command.__all__ - is_std = {} - for cmd in std_commands: - is_std[cmd] = 1 - - extra_commands = [] - for cmd in self.cmdclass.keys(): - if not is_std.get(cmd): - extra_commands.append(cmd) - + is_std = {cmd: 1 for cmd in std_commands} + extra_commands = [cmd for cmd in self.cmdclass.keys() if not is_std.get(cmd)] max_length = 0 for cmd in std_commands + extra_commands: if len(cmd) > max_length: @@ -769,15 +757,8 @@ def get_command_list(self): import distutils.command std_commands = distutils.command.__all__ - is_std = {} - for cmd in std_commands: - is_std[cmd] = 1 - - extra_commands = [] - for cmd in self.cmdclass.keys(): - if not is_std.get(cmd): - extra_commands.append(cmd) - + is_std = {cmd: 1 for cmd in std_commands} + extra_commands = [cmd for cmd in self.cmdclass.keys() if not is_std.get(cmd)] rv = [] for cmd in std_commands + extra_commands: klass = self.cmdclass.get(cmd) @@ -816,12 +797,11 @@ def get_command_class(self, command): Raises DistutilsModuleError if the expected module could not be found, or if that module does not define the expected class. """ - klass = self.cmdclass.get(command) - if klass: + if klass := self.cmdclass.get(command): return klass for pkgname in self.get_command_packages(): - module_name = "{}.{}".format(pkgname, command) + module_name = f"{pkgname}.{command}" klass_name = command try: @@ -834,14 +814,13 @@ def get_command_class(self, command): klass = getattr(module, klass_name) except AttributeError: raise DistutilsModuleError( - "invalid command '%s' (no class '%s' in module '%s')" - % (command, klass_name, module_name) + f"invalid command '{command}' (no class '{klass_name}' in module '{module_name}')" ) self.cmdclass[command] = klass return klass - raise DistutilsModuleError("invalid command '%s'" % command) + raise DistutilsModuleError(f"invalid command '{command}'") def get_command_obj(self, command, create=1): """Return the command object for 'command'. Normally this object @@ -853,26 +832,19 @@ def get_command_obj(self, command, create=1): if not cmd_obj and create: if DEBUG: self.announce( - "Distribution.get_command_obj(): " - "creating '%s' command object" % command + f"Distribution.get_command_obj(): creating '{command}' command object" ) klass = self.get_command_class(command) cmd_obj = self.command_obj[command] = klass(self) self.have_run[command] = 0 - # Set any options that were supplied in config files - # or on the command line. (NB. support for error - # reporting is lame here: any errors aren't reported - # until 'finalize_options()' is called, which means - # we won't report the source of the error.) - options = self.command_options.get(command) - if options: + if options := self.command_options.get(command): self._set_command_options(cmd_obj, options) return cmd_obj - def _set_command_options(self, command_obj, option_dict=None): # noqa: C901 + def _set_command_options(self, command_obj, option_dict=None): # noqa: C901 """Set the options for 'command_obj' from 'option_dict'. Basically this means copying elements of a dictionary ('option_dict') to attributes of an instance ('command'). @@ -886,10 +858,10 @@ def _set_command_options(self, command_obj, option_dict=None): # noqa: C901 option_dict = self.get_option_dict(command_name) if DEBUG: - self.announce(" setting options for '%s' command:" % command_name) + self.announce(f" setting options for '{command_name}' command:") for option, (source, value) in option_dict.items(): if DEBUG: - self.announce(" {} = {} (from {})".format(option, value, source)) + self.announce(f" {option} = {value} (from {source})") try: bool_opts = [translate_longopt(o) for o in command_obj.boolean_options] except AttributeError: @@ -909,8 +881,7 @@ def _set_command_options(self, command_obj, option_dict=None): # noqa: C901 setattr(command_obj, option, value) else: raise DistutilsOptionError( - "error in %s: command '%s' has no such option '%s'" - % (source, command_name, option) + f"error in {source}: command '{command_name}' has no such option '{option}'" ) except ValueError as msg: raise DistutilsOptionError(msg) @@ -1089,9 +1060,7 @@ def _read_field(name): def _read_list(name): values = msg.get_all(name, None) - if values == []: - return None - return values + return None if values == [] else values metadata_version = msg['metadata-version'] self.name = _read_field('name') @@ -1178,7 +1147,7 @@ def maybe_write(header, val): def _write_list(self, file, name, values): values = values or [] for value in values: - file.write('{}: {}\n'.format(name, value)) + file.write(f'{name}: {value}\n') # -- Metadata query methods ---------------------------------------- @@ -1189,7 +1158,7 @@ def get_version(self): return self.version or "0.0.0" def get_fullname(self): - return "{}-{}".format(self.get_name(), self.get_version()) + return f"{self.get_name()}-{self.get_version()}" def get_author(self): return self.author @@ -1281,7 +1250,4 @@ def fix_help_options(options): """Convert a 4-tuple 'help_options' list as found in various command classes to the 3-tuple form required by FancyGetopt. """ - new_options = [] - for help_tuple in options: - new_options.append(help_tuple[0:3]) - return new_options + return [help_tuple[:3] for help_tuple in options] diff --git a/setuptools/_distutils/extension.py b/setuptools/_distutils/extension.py index 6b8575de29..6b57b10712 100644 --- a/setuptools/_distutils/extension.py +++ b/setuptools/_distutils/extension.py @@ -127,10 +127,10 @@ def __init__( self.optional = optional # If there are unknown keyword options, warn about them - if len(kw) > 0: + if kw: options = [repr(option) for option in kw] options = ', '.join(sorted(options)) - msg = "Unknown Extension options: %s" % options + msg = f"Unknown Extension options: {options}" warnings.warn(msg) def __repr__(self): @@ -142,7 +142,7 @@ def __repr__(self): ) -def read_setup_file(filename): # noqa: C901 +def read_setup_file(filename): # noqa: C901 """Reads a Setup file and returns Extension instances.""" from distutils.sysconfig import parse_makefile, expand_makefile_vars, _variable_rx @@ -173,7 +173,7 @@ def read_setup_file(filename): # noqa: C901 continue if line[0] == line[-1] == "*": - file.warn("'%s' lines not handled yet" % line) + file.warn(f"'{line}' lines not handled yet") continue line = expand_makefile_vars(line, vars) @@ -196,7 +196,7 @@ def read_setup_file(filename): # noqa: C901 continue suffix = os.path.splitext(word)[1] - switch = word[0:2] + switch = word[:2] value = word[2:] if suffix in (".c", ".cc", ".cpp", ".cxx", ".c++", ".m", ".mm"): @@ -211,7 +211,7 @@ def read_setup_file(filename): # noqa: C901 if equals == -1: # bare "-DFOO" -- no value ext.define_macros.append((value, None)) else: # "-DFOO=blah" - ext.define_macros.append((value[0:equals], value[equals + 2 :])) + ext.define_macros.append((value[:equals], value[equals + 2 :])) elif switch == "-U": ext.undef_macros.append(value) elif switch == "-C": # only here 'cause makesetup has it! @@ -239,7 +239,7 @@ def read_setup_file(filename): # noqa: C901 # and append it to sources. Hmmmm. ext.extra_objects.append(word) else: - file.warn("unrecognized argument '%s'" % word) + file.warn(f"unrecognized argument '{word}'") extensions.append(ext) finally: diff --git a/setuptools/_distutils/fancy_getopt.py b/setuptools/_distutils/fancy_getopt.py index 3b887dc5a4..83156bc0a1 100644 --- a/setuptools/_distutils/fancy_getopt.py +++ b/setuptools/_distutils/fancy_getopt.py @@ -8,6 +8,7 @@ * options set attributes of a passed-in object """ + import sys import string import re @@ -19,10 +20,10 @@ # utilities, we use '-' in place of '_'. (The spirit of LISP lives on!) # The similarities to NAME are again not a coincidence... longopt_pat = r'[a-zA-Z](?:[a-zA-Z0-9-]*)' -longopt_re = re.compile(r'^%s$' % longopt_pat) +longopt_re = re.compile(f'^{longopt_pat}$') # For recognizing "negative alias" options, eg. "quiet=!verbose" -neg_alias_re = re.compile("^({})=!({})$".format(longopt_pat, longopt_pat)) +neg_alias_re = re.compile(f"^({longopt_pat})=!({longopt_pat})$") # This is used to translate long options to legitimate Python identifiers # (for use as attributes of some object). @@ -93,12 +94,11 @@ def set_option_table(self, option_table): def add_option(self, long_option, short_option=None, help_string=None): if long_option in self.option_index: raise DistutilsGetoptError( - "option conflict: already an option '%s'" % long_option + f"option conflict: already an option '{long_option}'" ) - else: - option = (long_option, short_option, help_string) - self.option_table.append(option) - self.option_index[long_option] = option + option = (long_option, short_option, help_string) + self.option_table.append(option) + self.option_index[long_option] = option def has_option(self, long_option): """Return true if the option table for this parser has an @@ -116,13 +116,11 @@ def _check_alias_dict(self, aliases, what): for alias, opt in aliases.items(): if alias not in self.option_index: raise DistutilsGetoptError( - ("invalid %s '%s': " "option '%s' not defined") - % (what, alias, alias) + f"invalid {what} '{alias}': option '{alias}' not defined" ) if opt not in self.option_index: raise DistutilsGetoptError( - ("invalid %s '%s': " "aliased option '%s' not defined") - % (what, alias, opt) + f"invalid {what} '{alias}': aliased option '{opt}' not defined" ) def set_aliases(self, alias): @@ -138,13 +136,13 @@ def set_negative_aliases(self, negative_alias): self._check_alias_dict(negative_alias, "negative alias") self.negative_alias = negative_alias - def _grok_option_table(self): # noqa: C901 + def _grok_option_table(self): # noqa: C901 """Populate the various data structures that keep tabs on the option table. Called by 'getopt()' before it can do anything worthwhile. """ - self.long_opts = [] self.short_opts = [] + self.long_opts = [] self.short2long.clear() self.repeat = {} @@ -162,14 +160,14 @@ def _grok_option_table(self): # noqa: C901 # Type- and value-check the option names if not isinstance(long, str) or len(long) < 2: raise DistutilsGetoptError( - ("invalid long option '%s': " "must be a string of length >= 2") - % long + f"invalid long option '{long}': must be a string of length >= 2" ) - if not ((short is None) or (isinstance(short, str) and len(short) == 1)): + if short is not None and ( + not isinstance(short, str) or len(short) != 1 + ): raise DistutilsGetoptError( - "invalid short option '%s': " - "must a single character or None" % short + f"invalid short option '{short}': must a single character or None" ) self.repeat[long] = repeat @@ -177,8 +175,8 @@ def _grok_option_table(self): # noqa: C901 if long[-1] == '=': # option takes an argument? if short: - short = short + ':' - long = long[0:-1] + short = f'{short}:' + long = long[:-1] self.takes_arg[long] = 1 else: # Is option is a "negative alias" for some other option (eg. @@ -187,8 +185,7 @@ def _grok_option_table(self): # noqa: C901 if alias_to is not None: if self.takes_arg[alias_to]: raise DistutilsGetoptError( - "invalid negative alias '%s': " - "aliased option '%s' takes a value" % (long, alias_to) + f"invalid negative alias '{long}': aliased option '{alias_to}' takes a value" ) self.long_opts[-1] = long # XXX redundant?! @@ -200,9 +197,7 @@ def _grok_option_table(self): # noqa: C901 if alias_to is not None: if self.takes_arg[long] != self.takes_arg[alias_to]: raise DistutilsGetoptError( - "invalid alias '%s': inconsistent with " - "aliased option '%s' (one of them takes a value, " - "the other doesn't" % (long, alias_to) + f"invalid alias '{long}': inconsistent with aliased option '{alias_to}' (one of them takes a value, the other doesn't" ) # Now enforce some bondage on the long option name, so we can @@ -211,8 +206,7 @@ def _grok_option_table(self): # noqa: C901 # '='. if not longopt_re.match(long): raise DistutilsGetoptError( - "invalid long option name '%s' " - "(must be letters, numbers, hyphens only" % long + f"invalid long option name '{long}' (must be letters, numbers, hyphens only" ) self.attr_name[long] = self.get_attr_name(long) @@ -220,7 +214,7 @@ def _grok_option_table(self): # noqa: C901 self.short_opts.append(short) self.short2long[short[0]] = long - def getopt(self, args=None, object=None): # noqa: C901 + def getopt(self, args=None, object=None): # noqa: C901 """Parse command-line options in args. Store as attributes on object. If 'args' is None or not supplied, uses 'sys.argv[1:]'. If @@ -254,14 +248,12 @@ def getopt(self, args=None, object=None): # noqa: C901 assert len(opt) > 2 and opt[:2] == '--' opt = opt[2:] - alias = self.alias.get(opt) - if alias: + if alias := self.alias.get(opt): opt = alias if not self.takes_arg[opt]: # boolean option? assert val == '', "boolean option can't have value" - alias = self.negative_alias.get(opt) - if alias: + if alias := self.negative_alias.get(opt): opt = alias val = 0 else: @@ -276,10 +268,7 @@ def getopt(self, args=None, object=None): # noqa: C901 self.option_order.append((opt, val)) # for opts - if created_object: - return args, object - else: - return args + return (args, object) if created_object else args def get_option_order(self): """Returns the list of (option, value) tuples processed by the @@ -291,7 +280,7 @@ def get_option_order(self): else: return self.option_order - def generate_help(self, header=None): # noqa: C901 + def generate_help(self, header=None): # noqa: C901 """Generate help text (a list of strings, one per suggested line of output) from the option table for this FancyGetopt object. """ @@ -305,9 +294,9 @@ def generate_help(self, header=None): # noqa: C901 short = option[1] ell = len(long) if long[-1] == '=': - ell = ell - 1 + ell -= 1 if short is not None: - ell = ell + 5 # " (-x)" where short == 'x' + ell += 5 if ell > max_opt: max_opt = ell @@ -338,16 +327,12 @@ def generate_help(self, header=None): # noqa: C901 line_width = 78 text_width = line_width - opt_width big_indent = ' ' * opt_width - if header: - lines = [header] - else: - lines = ['Option summary:'] - + lines = [header] if header else ['Option summary:'] for option in self.option_table: long, short, help = option[:3] text = wrap_text(help, text_width) if long[-1] == '=': - long = long[0:-1] + long = long[:-1] # Case 1: no short option at all (makes life easy) if short is None: @@ -356,17 +341,14 @@ def generate_help(self, header=None): # noqa: C901 else: lines.append(" --%-*s " % (max_opt, long)) - # Case 2: we have a short option, so we have to include it - # just after the long option else: - opt_names = "{} (-{})".format(long, short) + opt_names = f"{long} (-{short})" if text: lines.append(" --%-*s %s" % (max_opt, opt_names, text[0])) else: lines.append(" --%-*s" % opt_names) - for ell in text[1:]: - lines.append(big_indent + ell) + lines.extend(big_indent + ell for ell in text[1:]) return lines def print_help(self, header=None, file=None): @@ -423,7 +405,7 @@ def wrap_text(text, width): # chunk that's too big too fit on a line -- so we break # down and break it up at the line width if cur_len == 0: - cur_line.append(chunks[0][0:width]) + cur_line.append(chunks[0][:width]) chunks[0] = chunks[0][width:] # all-whitespace chunks at the end of a line can be discarded diff --git a/setuptools/_distutils/file_util.py b/setuptools/_distutils/file_util.py index 3f3e21b567..39e22d741c 100644 --- a/setuptools/_distutils/file_util.py +++ b/setuptools/_distutils/file_util.py @@ -11,7 +11,7 @@ _copy_action = {None: 'copying', 'hard': 'hard linking', 'sym': 'symbolically linking'} -def _copy_file_contents(src, dst, buffer_size=16 * 1024): # noqa: C901 +def _copy_file_contents(src, dst, buffer_size=16 * 1024): # noqa: C901 """Copy the file 'src' to 'dst'; both must be filenames. Any error opening either file, reading from 'src', or writing to 'dst', raises DistutilsFileError. Data is read/written in chunks of 'buffer_size' @@ -26,30 +26,24 @@ def _copy_file_contents(src, dst, buffer_size=16 * 1024): # noqa: C901 try: fsrc = open(src, 'rb') except OSError as e: - raise DistutilsFileError("could not open '{}': {}".format(src, e.strerror)) + raise DistutilsFileError(f"could not open '{src}': {e.strerror}") if os.path.exists(dst): try: os.unlink(dst) except OSError as e: - raise DistutilsFileError( - "could not delete '{}': {}".format(dst, e.strerror) - ) + raise DistutilsFileError(f"could not delete '{dst}': {e.strerror}") try: fdst = open(dst, 'wb') except OSError as e: - raise DistutilsFileError( - "could not create '{}': {}".format(dst, e.strerror) - ) + raise DistutilsFileError(f"could not create '{dst}': {e.strerror}") while True: try: buf = fsrc.read(buffer_size) except OSError as e: - raise DistutilsFileError( - "could not read from '{}': {}".format(src, e.strerror) - ) + raise DistutilsFileError(f"could not read from '{src}': {e.strerror}") if not buf: break @@ -57,9 +51,7 @@ def _copy_file_contents(src, dst, buffer_size=16 * 1024): # noqa: C901 try: fdst.write(buf) except OSError as e: - raise DistutilsFileError( - "could not write to '{}': {}".format(dst, e.strerror) - ) + raise DistutilsFileError(f"could not write to '{dst}': {e.strerror}") finally: if fdst: fdst.close() @@ -113,7 +105,7 @@ def copy_file( # noqa: C901 if not os.path.isfile(src): raise DistutilsFileError( - "can't copy '%s': doesn't exist or not a regular file" % src + f"can't copy '{src}': doesn't exist or not a regular file" ) if os.path.isdir(dst): @@ -130,7 +122,7 @@ def copy_file( # noqa: C901 try: action = _copy_action[link] except KeyError: - raise ValueError("invalid value '%s' for 'link' argument" % link) + raise ValueError(f"invalid value '{link}' for 'link' argument") if verbose >= 1: if os.path.basename(dst) == os.path.basename(src): @@ -164,18 +156,18 @@ def copy_file( # noqa: C901 if preserve_mode or preserve_times: st = os.stat(src) - # According to David Ascher , utime() should be done - # before chmod() (at least under NT). - if preserve_times: - os.utime(dst, (st[ST_ATIME], st[ST_MTIME])) - if preserve_mode: - os.chmod(dst, S_IMODE(st[ST_MODE])) + # According to David Ascher , utime() should be done + # before chmod() (at least under NT). + if preserve_times: + os.utime(dst, (st[ST_ATIME], st[ST_MTIME])) + if preserve_mode: + os.chmod(dst, S_IMODE(st[ST_MODE])) return (dst, 1) # XXX I suspect this is Unix-specific -- need porting help! -def move_file(src, dst, verbose=1, dry_run=0): # noqa: C901 +def move_file(src, dst, verbose=1, dry_run=0): # noqa: C901 """Move a file 'src' to 'dst'. If 'dst' is a directory, the file will be moved into it with the same name; otherwise, 'src' is just renamed to 'dst'. Return the new full name of the file. @@ -193,18 +185,18 @@ def move_file(src, dst, verbose=1, dry_run=0): # noqa: C901 return dst if not isfile(src): - raise DistutilsFileError("can't move '%s': not a regular file" % src) + raise DistutilsFileError(f"can't move '{src}': not a regular file") if isdir(dst): dst = os.path.join(dst, basename(src)) elif exists(dst): raise DistutilsFileError( - "can't move '{}': destination '{}' already exists".format(src, dst) + f"can't move '{src}': destination '{dst}' already exists" ) if not isdir(dirname(dst)): raise DistutilsFileError( - "can't move '{}': destination '{}' not a valid path".format(src, dst) + f"can't move '{src}': destination '{dst}' not a valid path" ) copy_it = False @@ -215,9 +207,7 @@ def move_file(src, dst, verbose=1, dry_run=0): # noqa: C901 if num == errno.EXDEV: copy_it = True else: - raise DistutilsFileError( - "couldn't move '{}' to '{}': {}".format(src, dst, msg) - ) + raise DistutilsFileError(f"couldn't move '{src}' to '{dst}': {msg}") if copy_it: copy_file(src, dst, verbose=verbose) diff --git a/setuptools/_distutils/filelist.py b/setuptools/_distutils/filelist.py index 6dadf923d7..3fee90de97 100644 --- a/setuptools/_distutils/filelist.py +++ b/setuptools/_distutils/filelist.py @@ -62,8 +62,7 @@ def sort(self): # Not a strict lexical sort! sortable_files = sorted(map(os.path.split, self.files)) self.files = [] - for sort_tuple in sortable_files: - self.files.append(os.path.join(*sort_tuple)) + self.files.extend(os.path.join(*sort_tuple) for sort_tuple in sortable_files) # Other miscellaneous utility methods @@ -83,25 +82,21 @@ def _parse_template_line(self, line): if action in ('include', 'exclude', 'global-include', 'global-exclude'): if len(words) < 2: - raise DistutilsTemplateError( - "'%s' expects ..." % action - ) + raise DistutilsTemplateError(f"'{action}' expects ...") patterns = [convert_path(w) for w in words[1:]] elif action in ('recursive-include', 'recursive-exclude'): if len(words) < 3: raise DistutilsTemplateError( - "'%s' expects ..." % action + f"'{action}' expects ..." ) dir = convert_path(words[1]) patterns = [convert_path(w) for w in words[2:]] elif action in ('graft', 'prune'): if len(words) != 2: - raise DistutilsTemplateError( - "'%s' expects a single " % action - ) + raise DistutilsTemplateError(f"'{action}' expects a single ") dir_pattern = convert_path(words[1]) else: - raise DistutilsTemplateError("unknown action '%s'" % action) + raise DistutilsTemplateError(f"unknown action '{action}'") return (action, patterns, dir, dir_pattern) @@ -159,7 +154,7 @@ def process_template_line(self, line): # noqa: C901 ) elif action == 'recursive-include': - self.debug_print("recursive-include {} {}".format(dir, ' '.join(patterns))) + self.debug_print(f"recursive-include {dir} {' '.join(patterns)}") for pattern in patterns: if not self.include_pattern(pattern, prefix=dir): msg = ( @@ -168,7 +163,7 @@ def process_template_line(self, line): # noqa: C901 log.warning(msg, pattern, dir) elif action == 'recursive-exclude': - self.debug_print("recursive-exclude {} {}".format(dir, ' '.join(patterns))) + self.debug_print(f"recursive-exclude {dir} {' '.join(patterns)}") for pattern in patterns: if not self.exclude_pattern(pattern, prefix=dir): log.warning( @@ -181,21 +176,19 @@ def process_template_line(self, line): # noqa: C901 ) elif action == 'graft': - self.debug_print("graft " + dir_pattern) + self.debug_print(f"graft {dir_pattern}") if not self.include_pattern(None, prefix=dir_pattern): log.warning("warning: no directories found matching '%s'", dir_pattern) elif action == 'prune': - self.debug_print("prune " + dir_pattern) + self.debug_print(f"prune {dir_pattern}") if not self.exclude_pattern(None, prefix=dir_pattern): log.warning( ("no previously-included directories found " "matching '%s'"), dir_pattern, ) else: - raise DistutilsInternalError( - "this cannot happen: invalid action '%s'" % action - ) + raise DistutilsInternalError(f"this cannot happen: invalid action '{action}'") # Filtering/selection methods @@ -227,7 +220,7 @@ def include_pattern(self, pattern, anchor=1, prefix=None, is_regex=0): # XXX docstring lying about what the special chars are? files_found = False pattern_re = translate_pattern(pattern, anchor, prefix, is_regex) - self.debug_print("include_pattern: applying regex r'%s'" % pattern_re.pattern) + self.debug_print(f"include_pattern: applying regex r'{pattern_re.pattern}'") # delayed loading of allfiles list if self.allfiles is None: @@ -235,7 +228,7 @@ def include_pattern(self, pattern, anchor=1, prefix=None, is_regex=0): for name in self.allfiles: if pattern_re.search(name): - self.debug_print(" adding " + name) + self.debug_print(f" adding {name}") self.files.append(name) files_found = True return files_found @@ -249,10 +242,10 @@ def exclude_pattern(self, pattern, anchor=1, prefix=None, is_regex=0): """ files_found = False pattern_re = translate_pattern(pattern, anchor, prefix, is_regex) - self.debug_print("exclude_pattern: applying regex r'%s'" % pattern_re.pattern) + self.debug_print(f"exclude_pattern: applying regex r'{pattern_re.pattern}'") for i in range(len(self.files) - 1, -1, -1): if pattern_re.search(self.files[i]): - self.debug_print(" removing " + self.files[i]) + self.debug_print(f" removing {self.files[i]}") del self.files[i] files_found = True return files_found @@ -341,11 +334,7 @@ def translate_pattern(pattern, anchor=1, prefix=None, is_regex=0): or just returned as-is (assumes it's a regex object). """ if is_regex: - if isinstance(pattern, str): - return re.compile(pattern) - else: - return pattern - + return re.compile(pattern) if isinstance(pattern, str) else pattern # ditch start and end characters start, _, end = glob_to_re('_').partition('_') @@ -363,9 +352,8 @@ def translate_pattern(pattern, anchor=1, prefix=None, is_regex=0): if os.sep == '\\': sep = r'\\' pattern_re = pattern_re[len(start) : len(pattern_re) - len(end)] - pattern_re = r'{}\A{}{}.*{}{}'.format(start, prefix_re, sep, pattern_re, end) - else: # no prefix -- respect anchor flag - if anchor: - pattern_re = r'{}\A{}'.format(start, pattern_re[len(start) :]) + pattern_re = f'{start}\A{prefix_re}{sep}.*{pattern_re}{end}' + elif anchor: + pattern_re = f'{start}\A{pattern_re[len(start):]}' return re.compile(pattern_re) diff --git a/setuptools/_distutils/msvc9compiler.py b/setuptools/_distutils/msvc9compiler.py index f9f9f2d844..d0261dfa91 100644 --- a/setuptools/_distutils/msvc9compiler.py +++ b/setuptools/_distutils/msvc9compiler.py @@ -75,16 +75,16 @@ class Reg: """Helper class to read values from the registry""" - def get_value(cls, path, key): + def get_value(self, path, key): for base in HKEYS: - d = cls.read_values(base, path) + d = self.read_values(base, path) if d and key in d: return d[key] raise KeyError(key) get_value = classmethod(get_value) - def read_keys(cls, base, key): + def read_keys(self, base, key): """Return list of registry keys.""" try: handle = RegOpenKeyEx(base, key) @@ -103,7 +103,7 @@ def read_keys(cls, base, key): read_keys = classmethod(read_keys) - def read_values(cls, base, key): + def read_values(self, base, key): """Return dict of registry keys and values. All names are converted to lowercase. @@ -120,20 +120,20 @@ def read_values(cls, base, key): except RegError: break name = name.lower() - d[cls.convert_mbcs(name)] = cls.convert_mbcs(value) + d[self.convert_mbcs(name)] = self.convert_mbcs(value) i += 1 return d read_values = classmethod(read_values) - def convert_mbcs(s): - dec = getattr(s, "decode", None) + def convert_mbcs(self): + dec = getattr(self, "decode", None) if dec is not None: try: - s = dec("mbcs") + self = dec("mbcs") except UnicodeError: pass - return s + return self convert_mbcs = staticmethod(convert_mbcs) @@ -145,7 +145,7 @@ def __init__(self, version): self.load_macros(version) def set_macro(self, macro, path, key): - self.macros["$(%s)" % macro] = Reg.get_value(path, key) + self.macros[f"$({macro})"] = Reg.get_value(path, key) def load_macros(self, version): self.set_macro("VCInstallDir", self.vsbase + r"\Setup\VC", "productdir") @@ -175,7 +175,7 @@ def load_macros(self, version): except RegError: continue key = RegEnumKey(h, 0) - d = Reg.get_value(base, r"{}\{}".format(p, key)) + d = Reg.get_value(base, f"{p}\{key}") self.macros["$(FrameworkVersion)"] = d["version"] def sub(self, s): @@ -200,14 +200,8 @@ def get_build_version(): if majorVersion >= 13: # v13 was skipped and should be v14 majorVersion += 1 - minorVersion = int(s[2:3]) / 10.0 - # I don't think paths are affected by minor version in version 6 - if majorVersion == 6: - minorVersion = 0 - if majorVersion >= 6: - return majorVersion + minorVersion - # else we don't know what version of the compiler this is - return None + minorVersion = 0 if majorVersion == 6 else int(s[2:3]) / 10.0 + return majorVersion + minorVersion if majorVersion >= 6 else None def normalize_and_reduce_paths(paths): @@ -232,8 +226,7 @@ def removeDuplicates(variable): for i in oldList: if i not in newList: newList.append(i) - newVariable = os.pathsep.join(newList) - return newVariable + return os.pathsep.join(newList) def find_vcvarsall(version): @@ -257,10 +250,10 @@ def find_vcvarsall(version): productdir = os.path.join(toolsdir, os.pardir, os.pardir, "VC") productdir = os.path.abspath(productdir) if not os.path.isdir(productdir): - log.debug("%s is not a valid directory" % productdir) + log.debug(f"{productdir} is not a valid directory") return None else: - log.debug("Env var %s is not set or invalid" % toolskey) + log.debug(f"Env var {toolskey} is not set or invalid") if not productdir: log.debug("No productdir found") return None @@ -281,7 +274,7 @@ def query_vcvarsall(version, arch="x86"): raise DistutilsPlatformError("Unable to find vcvarsall.bat") log.debug("Calling 'vcvarsall.bat %s' (version=%s)", arch, version) popen = subprocess.Popen( - '"{}" {} & set'.format(vcvarsall, arch), + f'"{vcvarsall}" {arch} & set', stdout=subprocess.PIPE, stderr=subprocess.PIPE, ) @@ -370,9 +363,7 @@ def initialize(self, plat_name=None): # noqa: C901 # sanity check for platforms to prevent obscure errors later. ok_plats = 'win32', 'win-amd64' if plat_name not in ok_plats: - raise DistutilsPlatformError( - "--plat-name must be one of {}".format(ok_plats) - ) + raise DistutilsPlatformError(f"--plat-name must be one of {ok_plats}") if ( "DISTUTILS_USE_SDK" in os.environ @@ -396,9 +387,7 @@ def initialize(self, plat_name=None): # noqa: C901 plat_spec = PLAT_TO_VCVARS[plat_name] else: # cross compile from win32 -> some 64bit - plat_spec = ( - PLAT_TO_VCVARS[get_platform()] + '_' + PLAT_TO_VCVARS[plat_name] - ) + plat_spec = f'{PLAT_TO_VCVARS[get_platform()]}_{PLAT_TO_VCVARS[plat_name]}' vc_env = query_vcvarsall(VERSION, plat_spec) @@ -418,8 +407,8 @@ def initialize(self, plat_name=None): # noqa: C901 self.lib = self.find_exe("lib.exe") self.rc = self.find_exe("rc.exe") # resource compiler self.mc = self.find_exe("mc.exe") # message compiler - # self.set_path_env_var('lib') - # self.set_path_env_var('include') + # self.set_path_env_var('lib') + # self.set_path_env_var('include') # extend the MSVC path with the current path try: @@ -477,12 +466,10 @@ def object_filenames(self, source_filenames, strip_dir=0, output_dir=''): # Better to raise an exception instead of silently continuing # and later complain about sources and targets having # different lengths - raise CompileError("Don't know how to compile %s" % src_name) + raise CompileError(f"Don't know how to compile {src_name}") if strip_dir: base = os.path.basename(base) - if ext in self._rc_extensions: - obj_names.append(os.path.join(output_dir, base + self.res_extension)) - elif ext in self._mc_extensions: + if ext in self._rc_extensions or ext in self._mc_extensions: obj_names.append(os.path.join(output_dir, base + self.res_extension)) else: obj_names.append(os.path.join(output_dir, base + self.obj_extension)) @@ -525,13 +512,13 @@ def compile( # noqa: C901 src = os.path.abspath(src) if ext in self._c_extensions: - input_opt = "/Tc" + src + input_opt = f"/Tc{src}" elif ext in self._cpp_extensions: - input_opt = "/Tp" + src + input_opt = f"/Tp{src}" elif ext in self._rc_extensions: # compile .RC to .RES file input_opt = src - output_opt = "/fo" + obj + output_opt = f"/fo{obj}" try: self.spawn([self.rc] + pp_opts + [output_opt] + [input_opt]) except DistutilsExecError as msg: @@ -555,20 +542,18 @@ def compile( # noqa: C901 # first compile .MC to .RC and .H file self.spawn([self.mc] + ['-h', h_dir, '-r', rc_dir] + [src]) base, _ = os.path.splitext(os.path.basename(src)) - rc_file = os.path.join(rc_dir, base + '.rc') + rc_file = os.path.join(rc_dir, f'{base}.rc') # then compile .RC to .RES file - self.spawn([self.rc] + ["/fo" + obj] + [rc_file]) + self.spawn([self.rc] + [f"/fo{obj}"] + [rc_file]) except DistutilsExecError as msg: raise CompileError(msg) continue else: # how to handle this file? - raise CompileError( - "Don't know how to compile {} to {}".format(src, obj) - ) + raise CompileError(f"Don't know how to compile {src} to {obj}") - output_opt = "/Fo" + obj + output_opt = f"/Fo{obj}" try: self.spawn( [self.cc] @@ -591,9 +576,7 @@ def create_static_lib( output_filename = self.library_filename(output_libname, output_dir=output_dir) if self._need_link(objects, output_filename): - lib_args = objects + ['/OUT:' + output_filename] - if debug: - pass # XXX what goes here? + lib_args = objects + [f'/OUT:{output_filename}'] try: self.spawn([self.lib] + lib_args) except DistutilsExecError as msg: @@ -635,22 +618,16 @@ def link( # noqa: C901 if self._need_link(objects, output_filename): if target_desc == CCompiler.EXECUTABLE: - if debug: - ldflags = self.ldflags_shared_debug[1:] - else: - ldflags = self.ldflags_shared[1:] + ldflags = self.ldflags_shared_debug[1:] if debug else self.ldflags_shared[1:] else: - if debug: - ldflags = self.ldflags_shared_debug - else: - ldflags = self.ldflags_shared - - export_opts = [] - for sym in export_symbols or []: - export_opts.append("/EXPORT:" + sym) - + ldflags = self.ldflags_shared_debug if debug else self.ldflags_shared + export_opts = [f"/EXPORT:{sym}" for sym in export_symbols or []] ld_args = ( - ldflags + lib_opts + export_opts + objects + ['/OUT:' + output_filename] + ldflags + + lib_opts + + export_opts + + objects + + [f'/OUT:{output_filename}'] ) # The MSVC linker generates .lib and .exp files, which cannot be @@ -664,7 +641,7 @@ def link( # noqa: C901 os.path.basename(output_filename) ) implib_file = os.path.join(build_temp, self.library_filename(dll_name)) - ld_args.append('/IMPLIB:' + implib_file) + ld_args.append(f'/IMPLIB:{implib_file}') self.manifest_setup_ldargs(output_filename, build_temp, ld_args) @@ -687,7 +664,7 @@ def link( # noqa: C901 mfinfo = self.manifest_get_embed_info(target_desc, ld_args) if mfinfo is not None: mffilename, mfid = mfinfo - out_arg = '-outputresource:{};{}'.format(output_filename, mfid) + out_arg = f'-outputresource:{output_filename};{mfid}' try: self.spawn(['mt.exe', '-nologo', '-manifest', mffilename, out_arg]) except DistutilsExecError as msg: @@ -703,9 +680,9 @@ def manifest_setup_ldargs(self, output_filename, build_temp, ld_args): # Ask the linker to generate the manifest in the temp dir, so # we can check it, and possibly embed it, later. temp_manifest = os.path.join( - build_temp, os.path.basename(output_filename) + ".manifest" + build_temp, f"{os.path.basename(output_filename)}.manifest" ) - ld_args.append('/MANIFESTFILE:' + temp_manifest) + ld_args.append(f'/MANIFESTFILE:{temp_manifest}') def manifest_get_embed_info(self, target_desc, ld_args): # If a manifest should be embedded, return a tuple of @@ -727,9 +704,7 @@ def manifest_get_embed_info(self, target_desc, ld_args): # Extension modules try and avoid any manifest if possible. mfid = 2 temp_manifest = self._remove_visual_c_ref(temp_manifest) - if temp_manifest is None: - return None - return temp_manifest, mfid + return None if temp_manifest is None else (temp_manifest, mfid) def _remove_visual_c_ref(self, manifest_file): try: @@ -778,7 +753,7 @@ def _remove_visual_c_ref(self, manifest_file): # ccompiler.py. def library_dir_option(self, dir): - return "/LIBPATH:" + dir + return f"/LIBPATH:{dir}" def runtime_library_dir_option(self, dir): raise DistutilsPlatformError( @@ -791,10 +766,7 @@ def library_option(self, lib): def find_library_file(self, dirs, lib, debug=0): # Prefer a debugging library if found (and requested), but deal # with it if we don't have one. - if debug: - try_names = [lib + "_d", lib] - else: - try_names = [lib] + try_names = [f"{lib}_d", lib] if debug else [lib] for dir in dirs: for name in try_names: libfile = os.path.join(dir, self.library_filename(name)) diff --git a/setuptools/_distutils/msvccompiler.py b/setuptools/_distutils/msvccompiler.py index c3823e257e..461fddd137 100644 --- a/setuptools/_distutils/msvccompiler.py +++ b/setuptools/_distutils/msvccompiler.py @@ -4,6 +4,7 @@ for the Microsoft Visual Studio. """ + # Written by Perry Stoll # hacked by Robin Becker and Thomas Heller to do a better job of # finding DevStudio (through the registry) @@ -52,8 +53,6 @@ "Make sure that Python modules winreg, " "win32api or win32con are installed." ) - pass - if _can_read_reg: HKEYS = ( hkey_mod.HKEY_USERS, @@ -128,9 +127,8 @@ def __init__(self, version): def set_macro(self, macro, path, key): for base in HKEYS: - d = read_values(base, path) - if d: - self.macros["$(%s)" % macro] = d[key] + if d := read_values(base, path): + self.macros[f"$({macro})"] = d[key] break def load_macros(self, version): @@ -159,7 +157,7 @@ def load_macros(self, version): except RegError: continue key = RegEnumKey(h, 0) - d = read_values(base, r"{}\{}".format(p, key)) + d = read_values(base, f"{p}\{key}") self.macros["$(FrameworkVersion)"] = d["version"] def sub(self, s): @@ -184,14 +182,8 @@ def get_build_version(): if majorVersion >= 13: # v13 was skipped and should be v14 majorVersion += 1 - minorVersion = int(s[2:3]) / 10.0 - # I don't think paths are affected by minor version in version 6 - if majorVersion == 6: - minorVersion = 0 - if majorVersion >= 6: - return majorVersion + minorVersion - # else we don't know what version of the compiler this is - return None + minorVersion = 0 if majorVersion == 6 else int(s[2:3]) / 10.0 + return majorVersion + minorVersion if majorVersion >= 6 else None def get_build_architecture(): @@ -263,10 +255,10 @@ def __init__(self, verbose=0, dry_run=0, force=0): self.__macros = MacroExpander(self.__version) else: self.__root = r"Software\Microsoft\Devstudio" - self.__product = "Visual Studio version %s" % self.__version + self.__product = f"Visual Studio version {self.__version}" else: # Win64. Assume this was built with the platform SDK - self.__product = "Microsoft SDK compiler %s" % (self.__version + 6) + self.__product = f"Microsoft SDK compiler {self.__version + 6}" self.initialized = False @@ -367,12 +359,10 @@ def object_filenames(self, source_filenames, strip_dir=0, output_dir=''): # Better to raise an exception instead of silently continuing # and later complain about sources and targets having # different lengths - raise CompileError("Don't know how to compile %s" % src_name) + raise CompileError(f"Don't know how to compile {src_name}") if strip_dir: base = os.path.basename(base) - if ext in self._rc_extensions: - obj_names.append(os.path.join(output_dir, base + self.res_extension)) - elif ext in self._mc_extensions: + if ext in self._rc_extensions or ext in self._mc_extensions: obj_names.append(os.path.join(output_dir, base + self.res_extension)) else: obj_names.append(os.path.join(output_dir, base + self.obj_extension)) @@ -415,13 +405,13 @@ def compile( # noqa: C901 src = os.path.abspath(src) if ext in self._c_extensions: - input_opt = "/Tc" + src + input_opt = f"/Tc{src}" elif ext in self._cpp_extensions: - input_opt = "/Tp" + src + input_opt = f"/Tp{src}" elif ext in self._rc_extensions: # compile .RC to .RES file input_opt = src - output_opt = "/fo" + obj + output_opt = f"/fo{obj}" try: self.spawn([self.rc] + pp_opts + [output_opt] + [input_opt]) except DistutilsExecError as msg: @@ -445,20 +435,18 @@ def compile( # noqa: C901 # first compile .MC to .RC and .H file self.spawn([self.mc] + ['-h', h_dir, '-r', rc_dir] + [src]) base, _ = os.path.splitext(os.path.basename(src)) - rc_file = os.path.join(rc_dir, base + '.rc') + rc_file = os.path.join(rc_dir, f'{base}.rc') # then compile .RC to .RES file - self.spawn([self.rc] + ["/fo" + obj] + [rc_file]) + self.spawn([self.rc] + [f"/fo{obj}"] + [rc_file]) except DistutilsExecError as msg: raise CompileError(msg) continue else: # how to handle this file? - raise CompileError( - "Don't know how to compile {} to {}".format(src, obj) - ) + raise CompileError(f"Don't know how to compile {src} to {obj}") - output_opt = "/Fo" + obj + output_opt = f"/Fo{obj}" try: self.spawn( [self.cc] @@ -481,9 +469,7 @@ def create_static_lib( output_filename = self.library_filename(output_libname, output_dir=output_dir) if self._need_link(objects, output_filename): - lib_args = objects + ['/OUT:' + output_filename] - if debug: - pass # XXX what goes here? + lib_args = objects + [f'/OUT:{output_filename}'] try: self.spawn([self.lib] + lib_args) except DistutilsExecError as msg: @@ -525,22 +511,16 @@ def link( # noqa: C901 if self._need_link(objects, output_filename): if target_desc == CCompiler.EXECUTABLE: - if debug: - ldflags = self.ldflags_shared_debug[1:] - else: - ldflags = self.ldflags_shared[1:] + ldflags = self.ldflags_shared_debug[1:] if debug else self.ldflags_shared[1:] else: - if debug: - ldflags = self.ldflags_shared_debug - else: - ldflags = self.ldflags_shared - - export_opts = [] - for sym in export_symbols or []: - export_opts.append("/EXPORT:" + sym) - + ldflags = self.ldflags_shared_debug if debug else self.ldflags_shared + export_opts = [f"/EXPORT:{sym}" for sym in export_symbols or []] ld_args = ( - ldflags + lib_opts + export_opts + objects + ['/OUT:' + output_filename] + ldflags + + lib_opts + + export_opts + + objects + + [f'/OUT:{output_filename}'] ) # The MSVC linker generates .lib and .exp files, which cannot be @@ -555,7 +535,7 @@ def link( # noqa: C901 implib_file = os.path.join( os.path.dirname(objects[0]), self.library_filename(dll_name) ) - ld_args.append('/IMPLIB:' + implib_file) + ld_args.append(f'/IMPLIB:{implib_file}') if extra_preargs: ld_args[:0] = extra_preargs @@ -576,7 +556,7 @@ def link( # noqa: C901 # ccompiler.py. def library_dir_option(self, dir): - return "/LIBPATH:" + dir + return f"/LIBPATH:{dir}" def runtime_library_dir_option(self, dir): raise DistutilsPlatformError( @@ -589,10 +569,7 @@ def library_option(self, lib): def find_library_file(self, dirs, lib, debug=0): # Prefer a debugging library if found (and requested), but deal # with it if we don't have one. - if debug: - try_names = [lib + "_d", lib] - else: - try_names = [lib] + try_names = [f"{lib}_d", lib] if debug else [lib] for dir in dirs: for name in try_names: libfile = os.path.join(dir, self.library_filename(name)) @@ -635,7 +612,7 @@ def get_msvc_paths(self, path, platform='x86'): if not _can_read_reg: return [] - path = path + " dirs" + path = f"{path} dirs" if self.__version >= 7: key = r"{}\{:0.1f}\VC\VC_OBJECTS_PLATFORM_INFO\Win32\Directories".format( self.__root, @@ -648,8 +625,7 @@ def get_msvc_paths(self, path, platform='x86'): ) for base in HKEYS: - d = read_values(base, key) - if d: + if d := read_values(base, key): if self.__version >= 7: return self.__macros.sub(d[path]).split(";") else: diff --git a/setuptools/_distutils/py38compat.py b/setuptools/_distutils/py38compat.py index 59224e71e5..ab12119fa5 100644 --- a/setuptools/_distutils/py38compat.py +++ b/setuptools/_distutils/py38compat.py @@ -5,4 +5,4 @@ def aix_platform(osname, version, release): return _aix_support.aix_platform() except ImportError: pass - return "{}-{}.{}".format(osname, version, release) + return f"{osname}-{version}.{release}" diff --git a/setuptools/_distutils/spawn.py b/setuptools/_distutils/spawn.py index afefe525ef..8379cb3584 100644 --- a/setuptools/_distutils/spawn.py +++ b/setuptools/_distutils/spawn.py @@ -15,7 +15,7 @@ from ._log import log -def spawn(cmd, search_path=1, verbose=0, dry_run=0, env=None): # noqa: C901 +def spawn(cmd, search_path=1, verbose=0, dry_run=0, env=None): # noqa: C901 """Run another program, specified as a command list 'cmd', in a new process. 'cmd' is just the argument list for the new process, ie. @@ -49,8 +49,7 @@ def spawn(cmd, search_path=1, verbose=0, dry_run=0, env=None): # noqa: C901 if sys.platform == 'darwin': from distutils.util import MACOSX_VERSION_VAR, get_macosx_target_ver - macosx_target_ver = get_macosx_target_ver() - if macosx_target_ver: + if macosx_target_ver := get_macosx_target_ver(): env[MACOSX_VERSION_VAR] = macosx_target_ver try: @@ -80,22 +79,22 @@ def find_executable(executable, path=None): """ _, ext = os.path.splitext(executable) if (sys.platform == 'win32') and (ext != '.exe'): - executable = executable + '.exe' + executable = f'{executable}.exe' if os.path.isfile(executable): return executable if path is None: path = os.environ.get('PATH', None) - if path is None: - try: - path = os.confstr("CS_PATH") - except (AttributeError, ValueError): - # os.confstr() or CS_PATH is not available - path = os.defpath - # bpo-35755: Don't use os.defpath if the PATH environment variable is - # set to an empty string + # bpo-35755: Don't use os.defpath if the PATH environment variable is + # set to an empty string + if path is None: + try: + path = os.confstr("CS_PATH") + except (AttributeError, ValueError): + # os.confstr() or CS_PATH is not available + path = os.defpath # PATH='' doesn't match, whereas PATH=':' looks in the current directory if not path: return None diff --git a/setuptools/_distutils/sysconfig.py b/setuptools/_distutils/sysconfig.py index a40a7231b3..ffc09f0a74 100644 --- a/setuptools/_distutils/sysconfig.py +++ b/setuptools/_distutils/sysconfig.py @@ -9,6 +9,7 @@ Email: """ + import os import re import sys @@ -32,13 +33,12 @@ # set for cross builds if "_PYTHON_PROJECT_BASE" in os.environ: project_base = os.path.abspath(os.environ["_PYTHON_PROJECT_BASE"]) +elif sys.executable: + project_base = os.path.dirname(os.path.abspath(sys.executable)) else: - if sys.executable: - project_base = os.path.dirname(os.path.abspath(sys.executable)) - else: - # sys.executable can be empty if argv[0] has been changed and Python is - # unable to retrieve the real program name - project_base = os.getcwd() + # sys.executable can be empty if argv[0] has been changed and Python is + # unable to retrieve the real program name + project_base = os.getcwd() def _is_python_source_dir(d): @@ -207,10 +207,7 @@ def _get_python_inc_nt(prefix, spec_prefix, plat_specific): # allow this behavior to be monkey-patched. Ref pypa/distutils#2. def _posix_lib(standard_lib, libpython, early_prefix, prefix): - if standard_lib: - return libpython - else: - return os.path.join(libpython, "site-packages") + return libpython if standard_lib else os.path.join(libpython, "site-packages") def get_python_lib(plat_specific=0, standard_lib=0, prefix=None): @@ -267,108 +264,106 @@ def get_python_lib(plat_specific=0, standard_lib=0, prefix=None): ) -def customize_compiler(compiler): # noqa: C901 +def customize_compiler(compiler): # noqa: C901 """Do any platform-specific customization of a CCompiler instance. Mainly needed on Unix, so we can plug in the information that varies across Unices and is stored in Python's Makefile. """ - if compiler.compiler_type == "unix": - if sys.platform == "darwin": - # Perform first-time customization of compiler-related - # config vars on OS X now that we know we need a compiler. - # This is primarily to support Pythons from binary - # installers. The kind and paths to build tools on - # the user system may vary significantly from the system - # that Python itself was built on. Also the user OS - # version and build tools may not support the same set - # of CPU architectures for universal builds. - global _config_vars - # Use get_config_var() to ensure _config_vars is initialized. - if not get_config_var('CUSTOMIZED_OSX_COMPILER'): - import _osx_support - - _osx_support.customize_compiler(_config_vars) - _config_vars['CUSTOMIZED_OSX_COMPILER'] = 'True' - - ( - cc, - cxx, - cflags, - ccshared, - ldshared, - shlib_suffix, - ar, - ar_flags, - ) = get_config_vars( - 'CC', - 'CXX', - 'CFLAGS', - 'CCSHARED', - 'LDSHARED', - 'SHLIB_SUFFIX', - 'AR', - 'ARFLAGS', - ) + if compiler.compiler_type != "unix": + return + if sys.platform == "darwin": + # Perform first-time customization of compiler-related + # config vars on OS X now that we know we need a compiler. + # This is primarily to support Pythons from binary + # installers. The kind and paths to build tools on + # the user system may vary significantly from the system + # that Python itself was built on. Also the user OS + # version and build tools may not support the same set + # of CPU architectures for universal builds. + global _config_vars + # Use get_config_var() to ensure _config_vars is initialized. + if not get_config_var('CUSTOMIZED_OSX_COMPILER'): + import _osx_support + + _osx_support.customize_compiler(_config_vars) + _config_vars['CUSTOMIZED_OSX_COMPILER'] = 'True' + + ( + cc, + cxx, + cflags, + ccshared, + ldshared, + shlib_suffix, + ar, + ar_flags, + ) = get_config_vars( + 'CC', + 'CXX', + 'CFLAGS', + 'CCSHARED', + 'LDSHARED', + 'SHLIB_SUFFIX', + 'AR', + 'ARFLAGS', + ) - if 'CC' in os.environ: - newcc = os.environ['CC'] - if 'LDSHARED' not in os.environ and ldshared.startswith(cc): - # If CC is overridden, use that as the default - # command for LDSHARED as well - ldshared = newcc + ldshared[len(cc) :] - cc = newcc - if 'CXX' in os.environ: - cxx = os.environ['CXX'] - if 'LDSHARED' in os.environ: - ldshared = os.environ['LDSHARED'] - if 'CPP' in os.environ: - cpp = os.environ['CPP'] - else: - cpp = cc + " -E" # not always - if 'LDFLAGS' in os.environ: - ldshared = ldshared + ' ' + os.environ['LDFLAGS'] - if 'CFLAGS' in os.environ: - cflags = cflags + ' ' + os.environ['CFLAGS'] - ldshared = ldshared + ' ' + os.environ['CFLAGS'] - if 'CPPFLAGS' in os.environ: - cpp = cpp + ' ' + os.environ['CPPFLAGS'] - cflags = cflags + ' ' + os.environ['CPPFLAGS'] - ldshared = ldshared + ' ' + os.environ['CPPFLAGS'] - if 'AR' in os.environ: - ar = os.environ['AR'] - if 'ARFLAGS' in os.environ: - archiver = ar + ' ' + os.environ['ARFLAGS'] - else: - archiver = ar + ' ' + ar_flags - - cc_cmd = cc + ' ' + cflags - compiler.set_executables( - preprocessor=cpp, - compiler=cc_cmd, - compiler_so=cc_cmd + ' ' + ccshared, - compiler_cxx=cxx, - linker_so=ldshared, - linker_exe=cc, - archiver=archiver, - ) + if 'CC' in os.environ: + newcc = os.environ['CC'] + if 'LDSHARED' not in os.environ and ldshared.startswith(cc): + # If CC is overridden, use that as the default + # command for LDSHARED as well + ldshared = newcc + ldshared[len(cc) :] + cc = newcc + if 'CXX' in os.environ: + cxx = os.environ['CXX'] + if 'LDSHARED' in os.environ: + ldshared = os.environ['LDSHARED'] + cpp = os.environ.get('CPP', f"{cc} -E") + if 'LDFLAGS' in os.environ: + ldshared = f'{ldshared} ' + os.environ['LDFLAGS'] + if 'CFLAGS' in os.environ: + cflags = f'{cflags} ' + os.environ['CFLAGS'] + ldshared = f'{ldshared} ' + os.environ['CFLAGS'] + if 'CPPFLAGS' in os.environ: + cpp = f'{cpp} ' + os.environ['CPPFLAGS'] + cflags = f'{cflags} ' + os.environ['CPPFLAGS'] + ldshared = f'{ldshared} ' + os.environ['CPPFLAGS'] + if 'AR' in os.environ: + ar = os.environ['AR'] + if 'ARFLAGS' in os.environ: + archiver = f'{ar} ' + os.environ['ARFLAGS'] + else: + archiver = f'{ar} {ar_flags}' + + cc_cmd = f'{cc} {cflags}' + compiler.set_executables( + preprocessor=cpp, + compiler=cc_cmd, + compiler_so=f'{cc_cmd} {ccshared}', + compiler_cxx=cxx, + linker_so=ldshared, + linker_exe=cc, + archiver=archiver, + ) - if 'RANLIB' in os.environ and compiler.executables.get('ranlib', None): - compiler.set_executables(ranlib=os.environ['RANLIB']) + if 'RANLIB' in os.environ and compiler.executables.get('ranlib', None): + compiler.set_executables(ranlib=os.environ['RANLIB']) - compiler.shared_lib_extension = shlib_suffix + compiler.shared_lib_extension = shlib_suffix def get_config_h_filename(): """Return full pathname of installed pyconfig.h file.""" - if python_build: - if os.name == "nt": - inc_dir = os.path.join(_sys_home or project_base, "PC") - else: - inc_dir = _sys_home or project_base - return os.path.join(inc_dir, 'pyconfig.h') - else: + if not python_build: return sysconfig.get_config_h_filename() + inc_dir = ( + os.path.join(_sys_home or project_base, "PC") + if os.name == "nt" + else _sys_home or project_base + ) + return os.path.join(inc_dir, 'pyconfig.h') def get_makefile_filename(): @@ -393,7 +388,7 @@ def parse_config_h(fp, g=None): _findvar2_rx = re.compile(r"\${([A-Za-z][A-Za-z0-9_]*)}") -def parse_makefile(fn, g=None): # noqa: C901 +def parse_makefile(fn, g=None): # noqa: C901 """Parse a Makefile-style file. A dictionary containing name/value pairs is returned. If an @@ -415,8 +410,7 @@ def parse_makefile(fn, g=None): # noqa: C901 line = fp.readline() if line is None: # eof break - m = _variable_rx.match(line) - if m: + if m := _variable_rx.match(line): n, v = m.group(1, 2) v = v.strip() # `$$' is a literal `$' in make @@ -443,8 +437,7 @@ def parse_makefile(fn, g=None): # noqa: C901 while notdone: for name in list(notdone): value = notdone[name] - m = _findvar1_rx.search(value) or _findvar2_rx.search(value) - if m: + if m := _findvar1_rx.search(value) or _findvar2_rx.search(value): n = m.group(1) found = True if n in done: @@ -460,11 +453,11 @@ def parse_makefile(fn, g=None): # noqa: C901 if name.startswith('PY_') and name[3:] in renamed_variables: item = "" - elif 'PY_' + n in notdone: + elif f'PY_{n}' in notdone: found = False else: - item = str(done['PY_' + n]) + item = str(done[f'PY_{n}']) else: done[n] = item = "" if found: @@ -517,10 +510,9 @@ def expand_makefile_vars(s, vars): # according to make's variable expansion semantics. while True: - m = _findvar1_rx.search(s) or _findvar2_rx.search(s) - if m: + if m := _findvar1_rx.search(s) or _findvar2_rx.search(s): (beg, end) = m.span() - s = s[0:beg] + vars.get(m.group(1)) + s[end:] + s = s[:beg] + vars.get(m.group(1)) + s[end:] else: break return s diff --git a/setuptools/_distutils/tests/py38compat.py b/setuptools/_distutils/tests/py38compat.py index 211d3a6c50..819fcf4935 100644 --- a/setuptools/_distutils/tests/py38compat.py +++ b/setuptools/_distutils/tests/py38compat.py @@ -12,7 +12,7 @@ try: from test.support.warnings_helper import check_warnings -except (ModuleNotFoundError, ImportError): +except ImportError: from test.support import check_warnings @@ -24,7 +24,7 @@ skip_unless_symlink, temp_dir, ) -except (ModuleNotFoundError, ImportError): +except ImportError: from test.support import ( rmtree, EnvironmentVarGuard, @@ -39,7 +39,7 @@ DirsOnSysPath, CleanImport, ) -except (ModuleNotFoundError, ImportError): +except ImportError: from test.support import ( DirsOnSysPath, CleanImport, diff --git a/setuptools/_distutils/tests/support.py b/setuptools/_distutils/tests/support.py index fd4b11bf75..d6a42c9588 100644 --- a/setuptools/_distutils/tests/support.py +++ b/setuptools/_distutils/tests/support.py @@ -112,12 +112,11 @@ def fixup_build_ext(cmd): runshared = sysconfig.get_config_var('RUNSHARED') if runshared is None: cmd.library_dirs = ['.'] + elif sys.platform == 'darwin': + cmd.library_dirs = [] else: - if sys.platform == 'darwin': - cmd.library_dirs = [] - else: - name, equals, value = runshared.partition('=') - cmd.library_dirs = [d for d in value.split(os.pathsep) if d] + name, equals, value = runshared.partition('=') + cmd.library_dirs = [d for d in value.split(os.pathsep) if d] def combine_markers(cls): diff --git a/setuptools/_distutils/tests/test_archive_util.py b/setuptools/_distutils/tests/test_archive_util.py index 89c415d761..845583acea 100644 --- a/setuptools/_distutils/tests/test_archive_util.py +++ b/setuptools/_distutils/tests/test_archive_util.py @@ -148,7 +148,7 @@ def test_tarfile_vs_tar(self): os.chdir(old_dir) # check if the compressed tarball was created - tarball = base_name + '.tar.gz' + tarball = f'{base_name}.tar.gz' assert os.path.exists(tarball) # now create another tarball using `tar` @@ -176,7 +176,7 @@ def test_tarfile_vs_tar(self): make_tarball(base_name, 'dist', compress=None) finally: os.chdir(old_dir) - tarball = base_name + '.tar' + tarball = f'{base_name}.tar' assert os.path.exists(tarball) # now for a dry_run @@ -187,7 +187,7 @@ def test_tarfile_vs_tar(self): make_tarball(base_name, 'dist', compress=None, dry_run=True) finally: os.chdir(old_dir) - tarball = base_name + '.tar' + tarball = f'{base_name}.tar' assert os.path.exists(tarball) @pytest.mark.skipif("not find_executable('compress')") @@ -204,7 +204,7 @@ def test_compress_deprecated(self): make_tarball(base_name, 'dist', compress='compress') finally: os.chdir(old_dir) - tarball = base_name + '.tar.Z' + tarball = f'{base_name}.tar.Z' assert os.path.exists(tarball) assert len(w.warnings) == 1 @@ -231,7 +231,7 @@ def test_make_zipfile(self): make_zipfile(base_name, 'dist') # check if the compressed tarball was created - tarball = base_name + '.zip' + tarball = f'{base_name}.zip' assert os.path.exists(tarball) with zipfile.ZipFile(tarball) as zf: assert sorted(zf.namelist()) == self._zip_created_files @@ -256,7 +256,7 @@ def fake_zipfile(*a, **kw): with path.Path(tmpdir): make_zipfile(base_name, 'dist') - tarball = base_name + '.zip' + tarball = f'{base_name}.zip' assert called == [((tarball, "w"), {'compression': zipfile.ZIP_STORED})] assert os.path.exists(tarball) with zipfile.ZipFile(tarball) as zf: diff --git a/setuptools/_distutils/tests/test_bdist.py b/setuptools/_distutils/tests/test_bdist.py index af330a06e7..d85f79ad38 100644 --- a/setuptools/_distutils/tests/test_bdist.py +++ b/setuptools/_distutils/tests/test_bdist.py @@ -43,4 +43,4 @@ def test_skip_build(self): if getattr(subcmd, '_unsupported', False): # command is not supported on this build continue - assert subcmd.skip_build, '%s should take --skip-build from bdist' % name + assert subcmd.skip_build, f'{name} should take --skip-build from bdist' diff --git a/setuptools/_distutils/tests/test_bdist_dumb.py b/setuptools/_distutils/tests/test_bdist_dumb.py index 6fb50c4b8e..7c73b8326e 100644 --- a/setuptools/_distutils/tests/test_bdist_dumb.py +++ b/setuptools/_distutils/tests/test_bdist_dumb.py @@ -63,7 +63,7 @@ def test_simple_built(self): # see what we have dist_created = os.listdir(os.path.join(pkg_dir, 'dist')) - base = "{}.{}.zip".format(dist.get_fullname(), cmd.plat_name) + base = f"{dist.get_fullname()}.{cmd.plat_name}.zip" assert dist_created == [base] @@ -77,5 +77,5 @@ def test_simple_built(self): contents = sorted(filter(None, map(os.path.basename, contents))) wanted = ['foo-0.1-py%s.%s.egg-info' % sys.version_info[:2], 'foo.py'] if not sys.dont_write_bytecode: - wanted.append('foo.%s.pyc' % sys.implementation.cache_tag) + wanted.append(f'foo.{sys.implementation.cache_tag}.pyc') assert contents == sorted(wanted) diff --git a/setuptools/_distutils/tests/test_build.py b/setuptools/_distutils/tests/test_build.py index 66d8af50ac..7e86726b72 100644 --- a/setuptools/_distutils/tests/test_build.py +++ b/setuptools/_distutils/tests/test_build.py @@ -23,18 +23,18 @@ def test_finalize_options(self): # build_platlib is 'build/lib.platform-cache_tag[-pydebug]' # examples: # build/lib.macosx-10.3-i386-cpython39 - plat_spec = '.{}-{}'.format(cmd.plat_name, sys.implementation.cache_tag) + plat_spec = f'.{cmd.plat_name}-{sys.implementation.cache_tag}' if hasattr(sys, 'gettotalrefcount'): assert cmd.build_platlib.endswith('-pydebug') plat_spec += '-pydebug' - wanted = os.path.join(cmd.build_base, 'lib' + plat_spec) + wanted = os.path.join(cmd.build_base, f'lib{plat_spec}') assert cmd.build_platlib == wanted # by default, build_lib = build_purelib assert cmd.build_lib == cmd.build_purelib # build_temp is build/temp. - wanted = os.path.join(cmd.build_base, 'temp' + plat_spec) + wanted = os.path.join(cmd.build_base, f'temp{plat_spec}') assert cmd.build_temp == wanted # build_scripts is build/scripts-x.x diff --git a/setuptools/_distutils/tests/test_build_clib.py b/setuptools/_distutils/tests/test_build_clib.py index b5a392a85f..0930a454e3 100644 --- a/setuptools/_distutils/tests/test_build_clib.py +++ b/setuptools/_distutils/tests/test_build_clib.py @@ -74,12 +74,15 @@ def test_build_libraries(self): pkg_dir, dist = self.create_dist() cmd = build_clib(dist) + + class FakeCompiler: - def compile(*args, **kw): + def compile(self, **kw): pass create_static_lib = compile + cmd.compiler = FakeCompiler() # build_libraries is also doing a bit of typo checking @@ -87,7 +90,7 @@ def compile(*args, **kw): with pytest.raises(DistutilsSetupError): cmd.build_libraries(lib) - lib = [('name', {'sources': list()})] + lib = [('name', {'sources': []})] cmd.build_libraries(lib) lib = [('name', {'sources': tuple()})] diff --git a/setuptools/_distutils/tests/test_build_ext.py b/setuptools/_distutils/tests/test_build_ext.py index cb61ad7455..4574a825a8 100644 --- a/setuptools/_distutils/tests/test_build_ext.py +++ b/setuptools/_distutils/tests/test_build_ext.py @@ -221,7 +221,7 @@ def test_finalize_options(self): # make sure cmd.library_dirs is turned into a list # if it's a string cmd = self.build_ext(dist) - cmd.library_dirs = 'my_lib_dir%sother_lib_dir' % os.pathsep + cmd.library_dirs = f'my_lib_dir{os.pathsep}other_lib_dir' cmd.finalize_options() assert 'my_lib_dir' in cmd.library_dirs assert 'other_lib_dir' in cmd.library_dirs @@ -229,7 +229,7 @@ def test_finalize_options(self): # make sure rpath is turned into a list # if it's a string cmd = self.build_ext(dist) - cmd.rpath = 'one%stwo' % os.pathsep + cmd.rpath = f'one{os.pathsep}two' cmd.finalize_options() assert cmd.rpath == ['one', 'two'] @@ -433,14 +433,14 @@ def test_ext_fullpath(self): cmd.distribution.package_dir = {'': 'src'} cmd.distribution.packages = ['lxml', 'lxml.html'] curdir = os.getcwd() - wanted = os.path.join(curdir, 'src', 'lxml', 'etree' + ext) + wanted = os.path.join(curdir, 'src', 'lxml', f'etree{ext}') path = cmd.get_ext_fullpath('lxml.etree') assert wanted == path # building lxml.etree not inplace cmd.inplace = 0 cmd.build_lib = os.path.join(curdir, 'tmpdir') - wanted = os.path.join(curdir, 'tmpdir', 'lxml', 'etree' + ext) + wanted = os.path.join(curdir, 'tmpdir', 'lxml', f'etree{ext}') path = cmd.get_ext_fullpath('lxml.etree') assert wanted == path @@ -449,13 +449,13 @@ def test_ext_fullpath(self): build_py.package_dir = {} cmd.distribution.packages = ['twisted', 'twisted.runner.portmap'] path = cmd.get_ext_fullpath('twisted.runner.portmap') - wanted = os.path.join(curdir, 'tmpdir', 'twisted', 'runner', 'portmap' + ext) + wanted = os.path.join(curdir, 'tmpdir', 'twisted', 'runner', f'portmap{ext}') assert wanted == path # building twisted.runner.portmap inplace cmd.inplace = 1 path = cmd.get_ext_fullpath('twisted.runner.portmap') - wanted = os.path.join(curdir, 'twisted', 'runner', 'portmap' + ext) + wanted = os.path.join(curdir, 'twisted', 'runner', f'portmap{ext}') assert wanted == path @pytest.mark.skipif('platform.system() != "Darwin"') @@ -477,11 +477,7 @@ def test_deployment_target_too_low(self): @pytest.mark.skipif('platform.system() != "Darwin"') @pytest.mark.usefixtures('save_env') def test_deployment_target_higher_ok(self): - # Issue 9516: Test that an extension module can be compiled with a - # deployment target higher than that of the interpreter: the ext - # module may depend on some newer OS feature. - deptarget = sysconfig.get_config_var('MACOSX_DEPLOYMENT_TARGET') - if deptarget: + if deptarget := sysconfig.get_config_var('MACOSX_DEPLOYMENT_TARGET'): # increment the minor version number (i.e. 10.6 -> 10.7) deptarget = [int(x) for x in deptarget.split('.')] deptarget[-1] += 1 @@ -517,7 +513,7 @@ def _try_compile_deployment_target(self, operator, target): # get the deployment target that the interpreter was built with target = sysconfig.get_config_var('MACOSX_DEPLOYMENT_TARGET') - target = tuple(map(int, target.split('.')[0:2])) + target = tuple(map(int, target.split('.')[:2])) # format the target value as defined in the Apple # Availability Macros. We can't use the macro names since # at least one value we test with will not exist yet. @@ -526,15 +522,9 @@ def _try_compile_deployment_target(self, operator, target): target = '%02d%01d0' % target else: # for 10.10 and beyond -> "10nn00" - if len(target) >= 2: - target = '%02d%02d00' % target - else: - # 11 and later can have no minor version (11 instead of 11.0) - target = '%02d0000' % target + target = '%02d%02d00' % target if len(target) >= 2 else '%02d0000' % target deptarget_ext = Extension( - 'deptarget', - [deptarget_c], - extra_compile_args=['-DTARGET={}'.format(target)], + 'deptarget', [deptarget_c], extra_compile_args=[f'-DTARGET={target}'] ) dist = Distribution({'name': 'deptarget', 'ext_modules': [deptarget_ext]}) dist.package_dir = self.tmp_dir diff --git a/setuptools/_distutils/tests/test_build_py.py b/setuptools/_distutils/tests/test_build_py.py index 3bef9d79ec..4f90aafa84 100644 --- a/setuptools/_distutils/tests/test_build_py.py +++ b/setuptools/_distutils/tests/test_build_py.py @@ -57,7 +57,7 @@ def test_package_data(self): assert not os.path.exists(pycache_dir) else: pyc_files = os.listdir(pycache_dir) - assert "__init__.%s.pyc" % sys.implementation.cache_tag in pyc_files + assert f"__init__.{sys.implementation.cache_tag}.pyc" in pyc_files def test_empty_package_dir(self): # See bugs #1668596/#1720897 @@ -100,7 +100,7 @@ def test_byte_compile(self): found = os.listdir(cmd.build_lib) assert sorted(found) == ['__pycache__', 'boiledeggs.py'] found = os.listdir(os.path.join(cmd.build_lib, '__pycache__')) - assert found == ['boiledeggs.%s.pyc' % sys.implementation.cache_tag] + assert found == [f'boiledeggs.{sys.implementation.cache_tag}.pyc'] @pytest.mark.skipif('sys.dont_write_bytecode') def test_byte_compile_optimized(self): diff --git a/setuptools/_distutils/tests/test_build_scripts.py b/setuptools/_distutils/tests/test_build_scripts.py index 1a5753c772..b2aefa5a80 100644 --- a/setuptools/_distutils/tests/test_build_scripts.py +++ b/setuptools/_distutils/tests/test_build_scripts.py @@ -46,8 +46,6 @@ def get_build_scripts_cmd(self, target, scripts): return build_scripts(dist) def write_sample_scripts(self, dir): - expected = [] - expected.append("script1.py") self.write_script( dir, "script1.py", @@ -57,19 +55,17 @@ def write_sample_scripts(self, dir): "pass\n" ), ) - expected.append("script2.py") self.write_script( dir, "script2.py", ("#!/usr/bin/python\n" "# bogus script w/ Python sh-bang\n" "pass\n"), ) - expected.append("shell.sh") self.write_script( dir, "shell.sh", ("#!/bin/sh\n" "# bogus shell script w/ sh-bang\n" "exit 0\n"), ) - return expected + return ["script1.py", "script2.py", "shell.sh"] def write_script(self, dir, name, text): f = open(os.path.join(dir, name), "w") diff --git a/setuptools/_distutils/tests/test_check.py b/setuptools/_distutils/tests/test_check.py index 6d240b8b2b..aad21fc2c8 100644 --- a/setuptools/_distutils/tests/test_check.py +++ b/setuptools/_distutils/tests/test_check.py @@ -84,7 +84,7 @@ def test_check_author_maintainer(self): # (the spec allows these fields to take the form "Name ") metadata = { 'url': 'xxx', - kind + '_email': 'Name ', + f'{kind}_email': 'Name ', 'name': 'xxx', 'version': 'xxx', } @@ -92,13 +92,13 @@ def test_check_author_maintainer(self): assert cmd._warnings == 0 # the check should not warn if only email is given - metadata[kind + '_email'] = 'name@email.com' + metadata[f'{kind}_email'] = 'name@email.com' cmd = self._run(metadata) assert cmd._warnings == 0 # the check should not warn if only the name is given metadata[kind] = "Name" - del metadata[kind + '_email'] + del metadata[f'{kind}_email'] cmd = self._run(metadata) assert cmd._warnings == 0 diff --git a/setuptools/_distutils/tests/test_clean.py b/setuptools/_distutils/tests/test_clean.py index 157b60a1e9..0b830e27c1 100644 --- a/setuptools/_distutils/tests/test_clean.py +++ b/setuptools/_distutils/tests/test_clean.py @@ -37,7 +37,7 @@ def test_simple_run(self): # make sure the files where removed for name, path in dirs: - assert not os.path.exists(path), '%s was not removed' % path + assert not os.path.exists(path), f'{path} was not removed' # let's run the command again (should spit warnings but succeed) cmd.all = 1 diff --git a/setuptools/_distutils/tests/test_config_cmd.py b/setuptools/_distutils/tests/test_config_cmd.py index e72a7c5ff8..db6c79ff5b 100644 --- a/setuptools/_distutils/tests/test_config_cmd.py +++ b/setuptools/_distutils/tests/test_config_cmd.py @@ -24,7 +24,7 @@ def _info(self, msg, *args): self._logs.append(line) def test_dump_file(self): - this_file = os.path.splitext(__file__)[0] + '.py' + this_file = f'{os.path.splitext(__file__)[0]}.py' f = open(this_file) try: numlines = len(f.readlines()) @@ -60,9 +60,9 @@ def test_finalize_options(self): # on options pkg_dir, dist = self.create_dist() cmd = config(dist) - cmd.include_dirs = 'one%stwo' % os.pathsep + cmd.include_dirs = f'one{os.pathsep}two' cmd.libraries = 'one' - cmd.library_dirs = 'three%sfour' % os.pathsep + cmd.library_dirs = f'three{os.pathsep}four' cmd.ensure_finalized() assert cmd.include_dirs == ['one', 'two'] diff --git a/setuptools/_distutils/tests/test_dist.py b/setuptools/_distutils/tests/test_dist.py index 30a6f9ff2e..3df5a0d9ce 100644 --- a/setuptools/_distutils/tests/test_dist.py +++ b/setuptools/_distutils/tests/test_dist.py @@ -149,7 +149,7 @@ def test_venv_install_options(self, tmp_path): with mock.patch.multiple(sys, prefix='/a', base_prefix='/b'): d = self.create_distribution([file]) - for key in result_dict.keys(): + for key in result_dict: assert key not in d.command_options.get('install', {}) def test_command_packages_configfile(self, tmp_path, clear_argv): @@ -202,7 +202,7 @@ def _warn(msg): } ) - assert len(warns) == 0 + assert not warns assert 'options' not in dir(dist) def test_finalize_options(self): diff --git a/setuptools/_distutils/tests/test_file_util.py b/setuptools/_distutils/tests/test_file_util.py index 9f44f91dfa..1c0cdcdd74 100644 --- a/setuptools/_distutils/tests/test_file_util.py +++ b/setuptools/_distutils/tests/test_file_util.py @@ -34,7 +34,7 @@ def test_move_file_verbosity(self, caplog): move_file(self.target, self.source, verbose=0) move_file(self.source, self.target, verbose=1) - wanted = ['moving {} -> {}'.format(self.source, self.target)] + wanted = [f'moving {self.source} -> {self.target}'] assert caplog.messages == wanted # back to original state @@ -44,7 +44,7 @@ def test_move_file_verbosity(self, caplog): # now the target is a dir os.mkdir(self.target_dir) move_file(self.source, self.target_dir, verbose=1) - wanted = ['moving {} -> {}'.format(self.source, self.target_dir)] + wanted = [f'moving {self.source} -> {self.target_dir}'] assert caplog.messages == wanted def test_move_file_exception_unpacking_rename(self): @@ -75,7 +75,7 @@ def test_copy_file_hard_link(self): try: os.link(self.source, self.target) except OSError as e: - self.skipTest('os.link: %s' % e) + self.skipTest(f'os.link: {e}') else: unlink(self.target) st = os.stat(self.source) diff --git a/setuptools/_distutils/tests/test_install.py b/setuptools/_distutils/tests/test_install.py index 3f525db42a..146705df32 100644 --- a/setuptools/_distutils/tests/test_install.py +++ b/setuptools/_distutils/tests/test_install.py @@ -206,7 +206,7 @@ def test_record(self): found = [os.path.basename(line) for line in content.splitlines()] expected = [ 'hello.py', - 'hello.%s.pyc' % sys.implementation.cache_tag, + f'hello.{sys.implementation.cache_tag}.pyc', 'sayhi', 'UNKNOWN-0.0.0-py%s.%s.egg-info' % sys.version_info[:2], ] diff --git a/setuptools/_distutils/tests/test_msvccompiler.py b/setuptools/_distutils/tests/test_msvccompiler.py index f63537b8e5..6c07853486 100644 --- a/setuptools/_distutils/tests/test_msvccompiler.py +++ b/setuptools/_distutils/tests/test_msvccompiler.py @@ -87,7 +87,7 @@ def test_concurrent_safe(self): command = [sys.executable, '-c', inner_cmd] threads = [ - CheckThread(target=compiler.spawn, args=[command]) for n in range(100) + CheckThread(target=compiler.spawn, args=[command]) for _ in range(100) ] for thread in threads: thread.start() diff --git a/setuptools/_distutils/tests/test_sdist.py b/setuptools/_distutils/tests/test_sdist.py index fdb768e73f..9c8cd58134 100644 --- a/setuptools/_distutils/tests/test_sdist.py +++ b/setuptools/_distutils/tests/test_sdist.py @@ -127,7 +127,7 @@ def test_prune_file_list(self): 'somecode/', 'somecode/__init__.py', ] - assert sorted(content) == ['fake-1.0/' + x for x in expected] + assert sorted(content) == [f'fake-1.0/{x}' for x in expected] @pytest.mark.usefixtures('needs_zlib') @pytest.mark.skipif("not find_executable('tar')") @@ -239,7 +239,7 @@ def test_add_defaults(self): 'somecode/doc.dat', 'somecode/doc.txt', ] - assert sorted(content) == ['fake-1.0/' + x for x in expected] + assert sorted(content) == [f'fake-1.0/{x}' for x in expected] # checking the MANIFEST f = open(join(self.tmp_dir, 'MANIFEST')) diff --git a/setuptools/_distutils/tests/test_spawn.py b/setuptools/_distutils/tests/test_spawn.py index 08a34ee2b8..ee4b0f7de9 100644 --- a/setuptools/_distutils/tests/test_spawn.py +++ b/setuptools/_distutils/tests/test_spawn.py @@ -50,7 +50,7 @@ def test_find_executable(self, tmp_path): program_noeext = 'program' # Give the temporary program an ".exe" suffix for all. # It's needed on Windows and not harmful on other platforms. - program = program_noeext + ".exe" + program = f"{program_noeext}.exe" program_path = tmp_path / program program_path.write_text("") @@ -73,7 +73,7 @@ def test_find_executable(self, tmp_path): assert rv == program # test non-existent program - dont_exist_program = "dontexist_" + program + dont_exist_program = f"dontexist_{program}" rv = find_executable(dont_exist_program, path=tmp_dir) assert rv is None diff --git a/setuptools/_distutils/tests/test_sysconfig.py b/setuptools/_distutils/tests/test_sysconfig.py index bfeaf9a6b9..27f6b911d6 100644 --- a/setuptools/_distutils/tests/test_sysconfig.py +++ b/setuptools/_distutils/tests/test_sysconfig.py @@ -257,7 +257,7 @@ def test_customize_compiler_before_get_config_vars(self, tmp_path): universal_newlines=True, ) outs, errs = p.communicate() - assert 0 == p.returncode, "Subprocess failed: " + outs + assert 0 == p.returncode, f"Subprocess failed: {outs}" def test_parse_config_h(self): config_h = sysconfig.get_config_h_filename() diff --git a/setuptools/_distutils/tests/test_unixccompiler.py b/setuptools/_distutils/tests/test_unixccompiler.py index a018442459..f2e6c4fc7e 100644 --- a/setuptools/_distutils/tests/test_unixccompiler.py +++ b/setuptools/_distutils/tests/test_unixccompiler.py @@ -64,9 +64,7 @@ def test_runtime_libdir_option(self): # noqa: C901 def make_darwin_gcv(syscfg_macosx_ver): def gcv(var): - if var == darwin_ver_var: - return syscfg_macosx_ver - return "xxx" + return syscfg_macosx_ver if var == darwin_ver_var else "xxx" return gcv @@ -93,9 +91,7 @@ def do_darwin_test(syscfg_macosx_ver, env_macosx_ver, expected_flag): if expected_flag is not None: assert self.cc.rpath_foo() == expected_flag, msg else: - with pytest.raises( - DistutilsPlatformError, match=darwin_ver_var + r' mismatch' - ): + with pytest.raises(DistutilsPlatformError, match=f'{darwin_ver_var} mismatch'): self.cc.rpath_foo() # Restore @@ -222,9 +218,7 @@ def gcv(v): return 'gcc-4.2' def gcvs(*args, _orig=sysconfig.get_config_vars): - if args: - return list(map(sysconfig.get_config_var, args)) - return _orig() + return list(map(sysconfig.get_config_var, args)) if args else _orig() sysconfig.get_config_var = gcv sysconfig.get_config_vars = gcvs @@ -251,24 +245,22 @@ def gcv(v): return 'gcc-4.2' def gcvs(*args, _orig=sysconfig.get_config_vars): - if args: - return list(map(sysconfig.get_config_var, args)) - return _orig() + return list(map(sysconfig.get_config_var, args)) if args else _orig() sysconfig.get_config_var = gcv sysconfig.get_config_vars = gcvs - with mock.patch.object( - self.cc, 'spawn', return_value=None - ) as mock_spawn, mock.patch.object( - self.cc, '_need_link', return_value=True - ), mock.patch.object( - self.cc, 'mkpath', return_value=None - ), EnvironmentVarGuard() as env: + with (mock.patch.object( + self.cc, 'spawn', return_value=None + ) as mock_spawn, mock.patch.object( + self.cc, '_need_link', return_value=True + ), mock.patch.object( + self.cc, 'mkpath', return_value=None + ), EnvironmentVarGuard() as env): env['CC'] = 'ccache my_cc' env['CXX'] = 'my_cxx' del env['LDSHARED'] sysconfig.customize_compiler(self.cc) - assert self.cc.linker_so[0:2] == ['ccache', 'my_cc'] + assert self.cc.linker_so[:2] == ['ccache', 'my_cc'] self.cc.link(None, [], 'a.out', target_lang='c++') call_args = mock_spawn.call_args[0][0] expected = ['my_cxx', '-bundle', '-undefined', 'dynamic_lookup'] @@ -285,9 +277,7 @@ def gcv(v): return 'gcc-4.2' def gcvs(*args, _orig=sysconfig.get_config_vars): - if args: - return list(map(sysconfig.get_config_var, args)) - return _orig() + return list(map(sysconfig.get_config_var, args)) if args else _orig() sysconfig.get_config_var = gcv sysconfig.get_config_vars = gcvs diff --git a/setuptools/_distutils/tests/test_upload.py b/setuptools/_distutils/tests/test_upload.py index af113b8b6e..b17901e3a3 100644 --- a/setuptools/_distutils/tests/test_upload.py +++ b/setuptools/_distutils/tests/test_upload.py @@ -45,10 +45,7 @@ class FakeOpen: def __init__(self, url, msg=None, code=None): self.url = url - if not isinstance(url, str): - self.req = url - else: - self.req = None + self.req = url if not isinstance(url, str) else None self.msg = msg or 'OK' self.code = code or 200 diff --git a/setuptools/_distutils/tests/test_util.py b/setuptools/_distutils/tests/test_util.py index 070a277069..c798c21046 100644 --- a/setuptools/_distutils/tests/test_util.py +++ b/setuptools/_distutils/tests/test_util.py @@ -112,9 +112,7 @@ def _isabs(path): os.path.isabs = _isabs def _splitdrive(path): - if path.startswith('c:'): - return ('', path.replace('c:', '')) - return ('', path) + return ('', path.replace('c:', '')) if path.startswith('c:') else ('', path) os.path.splitdrive = _splitdrive diff --git a/setuptools/_distutils/tests/test_version.py b/setuptools/_distutils/tests/test_version.py index ff52ea4683..1c82ba5568 100644 --- a/setuptools/_distutils/tests/test_version.py +++ b/setuptools/_distutils/tests/test_version.py @@ -48,20 +48,14 @@ def test_cmp_strict(self): if wanted is ValueError: continue else: - raise AssertionError( - ("cmp(%s, %s) " "shouldn't raise ValueError") % (v1, v2) - ) - assert res == wanted, 'cmp({}, {}) should be {}, got {}'.format( - v1, v2, wanted, res - ) + raise AssertionError(f"cmp({v1}, {v2}) shouldn't raise ValueError") + assert res == wanted, f'cmp({v1}, {v2}) should be {wanted}, got {res}' res = StrictVersion(v1)._cmp(v2) - assert res == wanted, 'cmp({}, {}) should be {}, got {}'.format( - v1, v2, wanted, res - ) + assert res == wanted, f'cmp({v1}, {v2}) should be {wanted}, got {res}' res = StrictVersion(v1)._cmp(object()) assert ( res is NotImplemented - ), 'cmp({}, {}) should be NotImplemented, got {}'.format(v1, v2, res) + ), f'cmp({v1}, {v2}) should be NotImplemented, got {res}' def test_cmp(self): versions = ( @@ -77,14 +71,10 @@ def test_cmp(self): for v1, v2, wanted in versions: res = LooseVersion(v1)._cmp(LooseVersion(v2)) - assert res == wanted, 'cmp({}, {}) should be {}, got {}'.format( - v1, v2, wanted, res - ) + assert res == wanted, f'cmp({v1}, {v2}) should be {wanted}, got {res}' res = LooseVersion(v1)._cmp(v2) - assert res == wanted, 'cmp({}, {}) should be {}, got {}'.format( - v1, v2, wanted, res - ) + assert res == wanted, f'cmp({v1}, {v2}) should be {wanted}, got {res}' res = LooseVersion(v1)._cmp(object()) assert ( res is NotImplemented - ), 'cmp({}, {}) should be NotImplemented, got {}'.format(v1, v2, res) + ), f'cmp({v1}, {v2}) should be NotImplemented, got {res}' diff --git a/setuptools/_distutils/text_file.py b/setuptools/_distutils/text_file.py index 36f947e51c..87a01012ab 100644 --- a/setuptools/_distutils/text_file.py +++ b/setuptools/_distutils/text_file.py @@ -95,9 +95,9 @@ def __init__(self, filename=None, file=None, **options): setattr(self, opt, self.default_options[opt]) # sanity check client option hash - for opt in options.keys(): + for opt in options: if opt not in self.default_options: - raise KeyError("invalid TextFile option '%s'" % opt) + raise KeyError(f"invalid TextFile option '{opt}'") if file is None: self.open(filename) @@ -128,10 +128,9 @@ def close(self): file.close() def gen_error(self, msg, line=None): - outmsg = [] if line is None: line = self.current_line - outmsg.append(self.filename + ", ") + outmsg = [f"{self.filename}, "] if isinstance(line, (list, tuple)): outmsg.append("lines %d-%d: " % tuple(line)) else: @@ -140,7 +139,7 @@ def gen_error(self, msg, line=None): return "".join(outmsg) def error(self, msg, line=None): - raise ValueError("error: " + self.gen_error(msg, line)) + raise ValueError(f"error: {self.gen_error(msg, line)}") def warn(self, msg, line=None): """Print (to stderr) a warning message tied to the current logical @@ -150,9 +149,9 @@ def warn(self, msg, line=None): the current line number; it may be a list or tuple to indicate a range of physical lines, or an integer for a single physical line.""" - sys.stderr.write("warning: " + self.gen_error(msg, line) + "\n") + sys.stderr.write(f"warning: {self.gen_error(msg, line)}" + "\n") - def readline(self): # noqa: C901 + def readline(self): # noqa: C901 """Read and return a single logical line from the current file (or from an internal buffer if lines have previously been "unread" with 'unreadline()'). If the 'join_lines' option is true, this @@ -192,8 +191,6 @@ def readline(self): # noqa: C901 if pos == -1: # no "#" -- no comments pass - # It's definitely a comment -- either "#" is the first - # character, or it's elsewhere and unescaped. elif pos == 0 or line[pos - 1] != "\\": # Have to preserve the trailing newline, because it's # the job of a later step (rstrip_ws) to remove it -- @@ -201,8 +198,8 @@ def readline(self): # noqa: C901 # (NB. this means that if the final line is all comment # and has no trailing newline, we will think that it's # EOF; I think that's OK.) - eol = (line[-1] == '\n') and '\n' or '' - line = line[0:pos] + eol + eol = '\n' if line[-1] == '\n' else '' + line = line[:pos] + eol # If all that's left is whitespace, then skip line # *now*, before we try to join it to 'buildup_line' -- @@ -232,17 +229,16 @@ def readline(self): # noqa: C901 self.current_line[1] = self.current_line[1] + 1 else: self.current_line = [self.current_line, self.current_line + 1] - # just an ordinary line, read it as usual - else: - if line is None: # eof - return None + elif line is None: # eof + return None + else: # still have to be careful about incrementing the line number! - if isinstance(self.current_line, list): - self.current_line = self.current_line[1] + 1 - else: - self.current_line = self.current_line + 1 - + self.current_line = ( + self.current_line[1] + 1 + if isinstance(self.current_line, list) + else self.current_line + 1 + ) # strip whitespace however the client wants (leading and # trailing, or one or the other, or neither) if self.lstrip_ws and self.rstrip_ws: @@ -263,7 +259,7 @@ def readline(self): # noqa: C901 continue if line[-2:] == '\\\n': - buildup_line = line[0:-2] + '\n' + buildup_line = line[:-2] + '\n' continue # well, I guess there's some actual content there: return it diff --git a/setuptools/_distutils/unixccompiler.py b/setuptools/_distutils/unixccompiler.py index bd8db9ac3f..85eaae8140 100644 --- a/setuptools/_distutils/unixccompiler.py +++ b/setuptools/_distutils/unixccompiler.py @@ -274,7 +274,7 @@ def link( # ccompiler.py. def library_dir_option(self, dir): - return "-L" + dir + return f"-L{dir}" def _is_gcc(self): cc_var = sysconfig.get_config_var("CC") @@ -300,16 +300,13 @@ def runtime_library_dir_option(self, dir): macosx_target_ver = get_macosx_target_ver() if macosx_target_ver and split_version(macosx_target_ver) >= [10, 5]: - return "-Wl,-rpath," + dir + return f"-Wl,-rpath,{dir}" else: # no support for -rpath on earlier macOS versions - return "-L" + dir + return f"-L{dir}" elif sys.platform[:7] == "freebsd": - return "-Wl,-rpath=" + dir + return f"-Wl,-rpath={dir}" elif sys.platform[:5] == "hp-ux": - return [ - "-Wl,+s" if self._is_gcc() else "+s", - "-L" + dir, - ] + return ["-Wl,+s" if self._is_gcc() else "+s", f"-L{dir}"] # For all compilers, `-Wl` is the presumed way to # pass a compiler option to the linker and `-R` is @@ -317,12 +314,12 @@ def runtime_library_dir_option(self, dir): if sysconfig.get_config_var("GNULD") == "yes": # GNU ld needs an extra option to get a RUNPATH # instead of just an RPATH. - return "-Wl,--enable-new-dtags,-R" + dir + return f"-Wl,--enable-new-dtags,-R{dir}" else: - return "-Wl,-R" + dir + return f"-Wl,-R{dir}" def library_option(self, lib): - return "-l" + lib + return f"-l{lib}" @staticmethod def _library_root(dir): diff --git a/setuptools/_distutils/util.py b/setuptools/_distutils/util.py index 7ae914f7ee..0d9162367d 100644 --- a/setuptools/_distutils/util.py +++ b/setuptools/_distutils/util.py @@ -79,8 +79,7 @@ def get_macosx_target_ver_from_syscfg(): if _syscfg_macosx_ver is None: from distutils import sysconfig - ver = sysconfig.get_config_var(MACOSX_VERSION_VAR) or '' - if ver: + if ver := sysconfig.get_config_var(MACOSX_VERSION_VAR) or '': _syscfg_macosx_ver = ver return _syscfg_macosx_ver @@ -93,9 +92,7 @@ def get_macosx_target_ver(): variable. If neither source has a value, then None is returned""" syscfg_ver = get_macosx_target_ver_from_syscfg() - env_ver = os.environ.get(MACOSX_VERSION_VAR) - - if env_ver: + if env_ver := os.environ.get(MACOSX_VERSION_VAR): # Validate overridden version against sysconfig version, if have both. # Ensure that the deployment target of the build process is not less # than 10.3 if the interpreter was built for 10.3 or later. This @@ -108,9 +105,8 @@ def get_macosx_target_ver(): and split_version(env_ver) < [10, 3] ): my_msg = ( - '$' + MACOSX_VERSION_VAR + ' mismatch: ' - 'now "%s" but "%s" during configure; ' - 'must use 10.3 or later' % (env_ver, syscfg_ver) + f'${MACOSX_VERSION_VAR}' + + f' mismatch: now "{env_ver}" but "{syscfg_ver}" during configure; must use 10.3 or later' ) raise DistutilsPlatformError(my_msg) return env_ver @@ -136,16 +132,14 @@ def convert_path(pathname): if not pathname: return pathname if pathname[0] == '/': - raise ValueError("path '%s' cannot be absolute" % pathname) + raise ValueError(f"path '{pathname}' cannot be absolute") if pathname[-1] == '/': - raise ValueError("path '%s' cannot end with '/'" % pathname) + raise ValueError(f"path '{pathname}' cannot end with '/'") paths = pathname.split('/') while '.' in paths: paths.remove('.') - if not paths: - return os.curdir - return os.path.join(*paths) + return os.curdir if not paths else os.path.join(*paths) # convert_path () @@ -157,18 +151,18 @@ def change_root(new_root, pathname): Otherwise, it requires making 'pathname' relative and then joining the two, which is tricky on DOS/Windows and Mac OS. """ - if os.name == 'posix': - if not os.path.isabs(pathname): - return os.path.join(new_root, pathname) - else: - return os.path.join(new_root, pathname[1:]) - - elif os.name == 'nt': + if os.name == 'nt': (drive, path) = os.path.splitdrive(pathname) if path[0] == '\\': path = path[1:] return os.path.join(new_root, path) + elif os.name == 'posix': + return ( + os.path.join(new_root, pathname) + if not os.path.isabs(pathname) + else os.path.join(new_root, pathname[1:]) + ) raise DistutilsPlatformError(f"nothing known about platform '{os.name}'") @@ -302,7 +296,7 @@ def split_quoted(s): raise RuntimeError("this can't happen (bad char '%c')" % s[end]) if m is None: - raise ValueError("bad string (mismatched %s quotes?)" % s[end]) + raise ValueError(f"bad string (mismatched {s[end]} quotes?)") (beg, end) = m.span() s = s[:beg] + s[beg + 1 : end - 1] + s[end:] @@ -329,8 +323,8 @@ def execute(func, args, msg=None, verbose=0, dry_run=0): """ if msg is None: msg = "{}{!r}".format(func.__name__, args) - if msg[-2:] == ',)': # correct for singleton tuple - msg = msg[0:-2] + ')' + if msg.endswith(',)'): # correct for singleton tuple + msg = f'{msg[:-2]})' log.info(msg) if not dry_run: @@ -460,12 +454,8 @@ def byte_compile( # noqa: C901 cmd.extend(subprocess._optim_args_from_interpreter_flags()) cmd.append(script_name) spawn(cmd, dry_run=dry_run) - execute(os.remove, (script_name,), "removing %s" % script_name, dry_run=dry_run) + execute(os.remove, (script_name,), f"removing {script_name}", dry_run=dry_run) - # "Direct" byte-compilation: use the py_compile module to compile - # right here, right now. Note that the script generated in indirect - # mode simply calls 'byte_compile()' in direct mode, a weird sort of - # cross-process recursion. Hey, it works! else: from py_compile import compile diff --git a/setuptools/_distutils/version.py b/setuptools/_distutils/version.py index 74c40d7bfd..446bcdb667 100644 --- a/setuptools/_distutils/version.py +++ b/setuptools/_distutils/version.py @@ -60,37 +60,27 @@ def __init__(self, vstring=None): ) def __repr__(self): - return "{} ('{}')".format(self.__class__.__name__, str(self)) + return f"{self.__class__.__name__} ('{str(self)}')" def __eq__(self, other): c = self._cmp(other) - if c is NotImplemented: - return c - return c == 0 + return c if c is NotImplemented else c == 0 def __lt__(self, other): c = self._cmp(other) - if c is NotImplemented: - return c - return c < 0 + return c if c is NotImplemented else c < 0 def __le__(self, other): c = self._cmp(other) - if c is NotImplemented: - return c - return c <= 0 + return c if c is NotImplemented else c <= 0 def __gt__(self, other): c = self._cmp(other) - if c is NotImplemented: - return c - return c > 0 + return c if c is NotImplemented else c > 0 def __ge__(self, other): c = self._cmp(other) - if c is NotImplemented: - return c - return c >= 0 + return c if c is NotImplemented else c >= 0 # Interface for version-number classes -- must be implemented @@ -154,7 +144,7 @@ class StrictVersion(Version): def parse(self, vstring): match = self.version_re.match(vstring) if not match: - raise ValueError("invalid version number '%s'" % vstring) + raise ValueError(f"invalid version number '{vstring}'") (major, minor, patch, prerelease, prerelease_num) = match.group(1, 2, 4, 5, 6) @@ -163,14 +153,11 @@ def parse(self, vstring): else: self.version = tuple(map(int, [major, minor])) + (0,) - if prerelease: - self.prerelease = (prerelease[0], int(prerelease_num)) - else: - self.prerelease = None + self.prerelease = (prerelease[0], int(prerelease_num)) if prerelease else None def __str__(self): if self.version[2] == 0: - vstring = '.'.join(map(str, self.version[0:2])) + vstring = '.'.join(map(str, self.version[:2])) else: vstring = '.'.join(map(str, self.version)) @@ -189,11 +176,7 @@ def _cmp(self, other): # noqa: C901 if self.version != other.version: # numeric versions don't match # prerelease stuff doesn't matter - if self.version < other.version: - return -1 - else: - return 1 - + return -1 if self.version < other.version else 1 # have to compare prerelease # case 1: neither has prerelease; they're equal # case 2: self has prerelease, other doesn't; other is greater @@ -204,17 +187,15 @@ def _cmp(self, other): # noqa: C901 return 0 elif self.prerelease and not other.prerelease: return -1 - elif not self.prerelease and other.prerelease: + elif not self.prerelease: return 1 - elif self.prerelease and other.prerelease: + else: if self.prerelease == other.prerelease: return 0 elif self.prerelease < other.prerelease: return -1 else: return 1 - else: - assert False, "never get here" # end class StrictVersion @@ -327,18 +308,15 @@ def parse(self, vstring): self.vstring = vstring components = [x for x in self.component_re.split(vstring) if x and x != '.'] for i, obj in enumerate(components): - try: + with contextlib.suppress(ValueError): components[i] = int(obj) - except ValueError: - pass - self.version = components def __str__(self): return self.vstring def __repr__(self): - return "LooseVersion ('%s')" % str(self) + return f"LooseVersion ('{str(self)}')" def _cmp(self, other): if isinstance(other, str): diff --git a/setuptools/_distutils/versionpredicate.py b/setuptools/_distutils/versionpredicate.py index d6c0c007aa..25d11a9b52 100644 --- a/setuptools/_distutils/versionpredicate.py +++ b/setuptools/_distutils/versionpredicate.py @@ -115,8 +115,7 @@ def __init__(self, versionPredicateStr): if not match: raise ValueError("bad package name in %r" % versionPredicateStr) self.name, paren = match.groups() - paren = paren.strip() - if paren: + if paren := paren.strip(): match = re_paren.match(paren) if not match: raise ValueError("expected parenthesized list: %r" % paren) @@ -128,21 +127,17 @@ def __init__(self, versionPredicateStr): self.pred = [] def __str__(self): - if self.pred: - seq = [cond + " " + str(ver) for cond, ver in self.pred] - return self.name + " (" + ", ".join(seq) + ")" - else: + if not self.pred: return self.name + seq = [f"{cond} {str(ver)}" for cond, ver in self.pred] + return f"{self.name} (" + ", ".join(seq) + ")" def satisfied_by(self, version): """True if version is compatible with all the predicates in self. The parameter version must be acceptable to the StrictVersion constructor. It may be either a string or StrictVersion. """ - for cond, ver in self.pred: - if not compmap[cond](version, ver): - return False - return True + return all(compmap[cond](version, ver) for cond, ver in self.pred) _provision_rx = None diff --git a/setuptools/_imp.py b/setuptools/_imp.py index 9d4ead0eb0..af51244fb0 100644 --- a/setuptools/_imp.py +++ b/setuptools/_imp.py @@ -30,7 +30,7 @@ def find_module(module, paths=None): """Just like 'imp.find_module()', but with package support""" spec = find_spec(module, paths) if spec is None: - raise ImportError("Can't find %s" % module) + raise ImportError(f"Can't find {module}") if not spec.has_location and hasattr(spec, 'submodule_search_locations'): spec = importlib.util.spec_from_loader('__init__.py', spec.loader) @@ -75,14 +75,14 @@ def find_module(module, paths=None): def get_frozen_object(module, paths=None): - spec = find_spec(module, paths) - if not spec: - raise ImportError("Can't find %s" % module) - return spec.loader.get_code(module) + if spec := find_spec(module, paths): + return spec.loader.get_code(module) + else: + raise ImportError(f"Can't find {module}") def get_module(module, paths, info): - spec = find_spec(module, paths) - if not spec: - raise ImportError("Can't find %s" % module) - return module_from_spec(spec) + if spec := find_spec(module, paths): + return module_from_spec(spec) + else: + raise ImportError(f"Can't find {module}") diff --git a/setuptools/_normalization.py b/setuptools/_normalization.py index 8d4731eb60..d72e6c750f 100644 --- a/setuptools/_normalization.py +++ b/setuptools/_normalization.py @@ -89,8 +89,7 @@ def best_effort_version(version: str) -> str: return safe_version(version) except packaging.version.InvalidVersion: v = version.replace(' ', '.') - match = _PEP440_FALLBACK.search(v) - if match: + if match := _PEP440_FALLBACK.search(v): safe = match["safe"] rest = v[len(safe) :] else: diff --git a/setuptools/_vendor/importlib_metadata/__init__.py b/setuptools/_vendor/importlib_metadata/__init__.py index 8864214375..5341a6b7bf 100644 --- a/setuptools/_vendor/importlib_metadata/__init__.py +++ b/setuptools/_vendor/importlib_metadata/__init__.py @@ -114,8 +114,7 @@ def read(text, filter_=None): lines = filter(filter_, map(str.strip, text.splitlines())) name = None for value in lines: - section_match = value.startswith('[') and value.endswith(']') - if section_match: + if section_match := value.startswith('[') and value.endswith(']'): name = value.strip('[]') continue yield Pair(name, value) @@ -739,7 +738,7 @@ def _search_paths(cls, name, paths): path.search(prepared) for path in map(FastPath, paths) ) - def invalidate_caches(cls): + def invalidate_caches(self): FastPath.__new__.cache_clear() diff --git a/setuptools/_vendor/importlib_resources/_adapters.py b/setuptools/_vendor/importlib_resources/_adapters.py index ea363d86a5..30bd38a8eb 100644 --- a/setuptools/_vendor/importlib_resources/_adapters.py +++ b/setuptools/_vendor/importlib_resources/_adapters.py @@ -35,7 +35,7 @@ def _io_wrapper(file, mode='r', *args, **kwargs): elif mode == 'rb': return file raise ValueError( - "Invalid mode value '{}', only 'r' and 'rb' are supported".format(mode) + f"Invalid mode value '{mode}', only 'r' and 'rb' are supported" ) @@ -118,7 +118,7 @@ class OrphanPath(abc.Traversable): """ def __init__(self, *path_parts): - if len(path_parts) < 1: + if not path_parts: raise ValueError('Need at least one path part to construct a path') self._path = path_parts diff --git a/setuptools/_vendor/importlib_resources/_common.py b/setuptools/_vendor/importlib_resources/_common.py index 3c6de1cfb2..01bf48ae53 100644 --- a/setuptools/_vendor/importlib_resources/_common.py +++ b/setuptools/_vendor/importlib_resources/_common.py @@ -67,9 +67,7 @@ def get_resource_reader(package: types.ModuleType) -> Optional[ResourceReader]: # TypeError. That seems terrible. spec = package.__spec__ reader = getattr(spec.loader, 'get_resource_reader', None) # type: ignore - if reader is None: - return None - return reader(spec.name) # type: ignore + return None if reader is None else reader(spec.name) @functools.singledispatch @@ -135,10 +133,8 @@ def _tempfile( del reader yield pathlib.Path(raw_path) finally: - try: + with contextlib.suppress(FileNotFoundError): _os_remove(raw_path) - except FileNotFoundError: - pass def _temp_file(path): diff --git a/setuptools/_vendor/jaraco/functools.py b/setuptools/_vendor/jaraco/functools.py index ebf7a36137..c5de01435c 100644 --- a/setuptools/_vendor/jaraco/functools.py +++ b/setuptools/_vendor/jaraco/functools.py @@ -204,7 +204,7 @@ def _special_method_cache(method, cache_wrapper): if name not in special_names: return - wrapper_name = '__cached' + name + wrapper_name = f'__cached{name}' def proxy(self, *args, **kwargs): if wrapper_name not in vars(self): @@ -369,7 +369,7 @@ def retry_call(func, cleanup=lambda: None, retries=0, trap=()): to propagate. """ attempts = itertools.count() if retries == float('inf') else range(retries) - for attempt in attempts: + for _ in attempts: try: return func() except trap: @@ -508,7 +508,7 @@ def save_method_args(method): @functools.wraps(method) def wrapper(self, *args, **kwargs): - attr_name = '_saved_' + method.__name__ + attr_name = f'_saved_{method.__name__}' attr = args_and_kwargs(args, kwargs) setattr(self, attr_name, attr) return method(self, *args, **kwargs) diff --git a/setuptools/_vendor/more_itertools/more.py b/setuptools/_vendor/more_itertools/more.py index e6fca4d47f..a15efb05db 100644 --- a/setuptools/_vendor/more_itertools/more.py +++ b/setuptools/_vendor/more_itertools/more.py @@ -351,10 +351,7 @@ def prepend(self, *items): self._cache.extendleft(reversed(items)) def __next__(self): - if self._cache: - return self._cache.popleft() - - return next(self._it) + return self._cache.popleft() if self._cache else next(self._it) def _get_slice(self, index): # Normalize the slice's arguments @@ -937,10 +934,7 @@ def __iter__(self): yield from self._cache.keys() def __getitem__(self, value): - if not self._validator(value): - return iter(()) - - return self._get_values(value) + return iter(()) if not self._validator(value) else self._get_values(value) def spy(iterable, n=1): @@ -1409,8 +1403,7 @@ def repeat_last(iterable, default=None): """ item = _marker - for item in iterable: - yield item + yield from iterable final = default if item is _marker else item yield from repeat(final) @@ -1941,7 +1934,9 @@ class numeric_range(abc.Sequence, abc.Hashable): def __init__(self, *args): argc = len(args) - if argc == 1: + if argc == 0: + raise TypeError(f'numeric_range expected at least 1 argument, got {argc}') + elif argc == 1: (self._stop,) = args self._start = type(self._stop)(0) self._step = type(self._stop - self._start)(1) @@ -1950,16 +1945,8 @@ def __init__(self, *args): self._step = type(self._stop - self._start)(1) elif argc == 3: self._start, self._stop, self._step = args - elif argc == 0: - raise TypeError( - 'numeric_range expected at least ' - '1 argument, got {}'.format(argc) - ) else: - raise TypeError( - 'numeric_range expected at most ' - '3 arguments, got {}'.format(argc) - ) + raise TypeError(f'numeric_range expected at most 3 arguments, got {argc}') self._zero = type(self._step)(0) if self._step == self._zero: @@ -1968,35 +1955,31 @@ def __init__(self, *args): self._init_len() def __bool__(self): - if self._growing: - return self._start < self._stop - else: - return self._start > self._stop + return self._start < self._stop if self._growing else self._start > self._stop def __contains__(self, elem): if self._growing: if self._start <= elem < self._stop: return (elem - self._start) % self._step == self._zero - else: - if self._start >= elem > self._stop: - return (self._start - elem) % (-self._step) == self._zero + elif self._start >= elem > self._stop: + return (self._start - elem) % (-self._step) == self._zero return False def __eq__(self, other): - if isinstance(other, numeric_range): - empty_self = not bool(self) - empty_other = not bool(other) - if empty_self or empty_other: - return empty_self and empty_other # True if both empty - else: - return ( - self._start == other._start - and self._step == other._step - and self._get_by_index(-1) == other._get_by_index(-1) - ) - else: + if not isinstance(other, numeric_range): return False + empty_self = not bool(self) + empty_other = not bool(other) + return ( + empty_self and empty_other + if empty_self or empty_other + else ( + self._start == other._start + and self._step == other._step + and self._get_by_index(-1) == other._get_by_index(-1) + ) + ) def __getitem__(self, key): if isinstance(key, int): @@ -2021,8 +2004,7 @@ def __getitem__(self, key): return numeric_range(start, stop, step) else: raise TypeError( - 'numeric range indices must be ' - 'integers or slices, not {}'.format(type(key).__name__) + f'numeric range indices must be integers or slices, not {type(key).__name__}' ) def __hash__(self): @@ -2062,13 +2044,9 @@ def __reduce__(self): def __repr__(self): if self._step == 1: - return "numeric_range({}, {})".format( - repr(self._start), repr(self._stop) - ) + return f"numeric_range({repr(self._start)}, {repr(self._stop)})" else: - return "numeric_range({}, {}, {})".format( - repr(self._start), repr(self._stop), repr(self._step) - ) + return f"numeric_range({repr(self._start)}, {repr(self._stop)}, {repr(self._step)})" def __reversed__(self): return iter( @@ -2086,13 +2064,12 @@ def index(self, value): q, r = divmod(value - self._start, self._step) if r == self._zero: return int(q) - else: - if self._start >= value > self._stop: - q, r = divmod(self._start - value, -self._step) - if r == self._zero: - return int(q) + elif self._start >= value > self._stop: + q, r = divmod(self._start - value, -self._step) + if r == self._zero: + return int(q) - raise ValueError("{} is not in numeric range".format(value)) + raise ValueError(f"{value} is not in numeric range") def _get_by_index(self, i): if i < 0: @@ -2292,10 +2269,7 @@ class islice_extended: def __init__(self, iterable, *args): it = iter(iterable) - if args: - self._iterable = _islice_helper(it, slice(*args)) - else: - self._iterable = it + self._iterable = _islice_helper(it, slice(*args)) if args else it def __iter__(self): return self @@ -2371,11 +2345,7 @@ def _islice_helper(it, s): # If start and stop are both negative they are comparable and # we can just slice. Otherwise we can adjust start to be negative # and then slice. - if start < 0: - i, j = start, stop - else: - i, j = min(start - len_iter, -1), None - + i, j = (start, stop) if start < 0 else (min(start - len_iter, -1), None) for index, item in list(cache)[i:j:step]: yield item else: @@ -2556,7 +2526,7 @@ def __len__(self): return len(self._target) def __repr__(self): - return '{}({})'.format(self.__class__.__name__, repr(self._target)) + return f'{self.__class__.__name__}({repr(self._target)})' class seekable: @@ -2647,10 +2617,7 @@ class seekable: def __init__(self, iterable, maxlen=None): self._source = iter(iterable) - if maxlen is None: - self._cache = [] - else: - self._cache = deque([], maxlen) + self._cache = [] if maxlen is None else deque([], maxlen) self._index = None def __iter__(self): @@ -3368,9 +3335,8 @@ def sample(iterable, k, weights=None): iterable = iter(iterable) if weights is None: return _sample_unweighted(iterable, k) - else: - weights = iter(weights) - return _sample_weighted(iterable, k, weights) + weights = iter(weights) + return _sample_weighted(iterable, k, weights) def is_sorted(iterable, key=None, reverse=False): @@ -3471,9 +3437,7 @@ def __next__(self): @property def done(self): - if self._future is None: - return False - return self._future.done() + return False if self._future is None else self._future.done() @property def result(self): diff --git a/setuptools/_vendor/more_itertools/recipes.py b/setuptools/_vendor/more_itertools/recipes.py index 521abd7c2c..56a4f1c99d 100644 --- a/setuptools/_vendor/more_itertools/recipes.py +++ b/setuptools/_vendor/more_itertools/recipes.py @@ -539,7 +539,7 @@ def random_combination_with_replacement(iterable, r): """ pool = tuple(iterable) n = len(pool) - indices = sorted(randrange(n) for i in range(r)) + indices = sorted(randrange(n) for _ in range(r)) return tuple(pool[i] for i in indices) diff --git a/setuptools/_vendor/ordered_set.py b/setuptools/_vendor/ordered_set.py index 14876000de..7270a79554 100644 --- a/setuptools/_vendor/ordered_set.py +++ b/setuptools/_vendor/ordered_set.py @@ -91,10 +91,7 @@ def __getitem__(self, index): return [self.items[i] for i in index] elif hasattr(index, "__index__") or isinstance(index, slice): result = self.items[index] - if isinstance(result, list): - return self.__class__(result) - else: - return result + return self.__class__(result) if isinstance(result, list) else result else: raise TypeError("Don't know how to index an OrderedSet by %r" % index) @@ -113,16 +110,7 @@ def copy(self): return self.__class__(self) def __getstate__(self): - if len(self) == 0: - # The state can't be an empty list. - # We need to return a truthy value, or else __setstate__ won't be run. - # - # This could have been done more gracefully by always putting the state - # in a tuple, but this way is backwards- and forwards- compatible with - # previous versions of OrderedSet. - return (None,) - else: - return list(self) + return (None, ) if len(self) == 0 else list(self) def __setstate__(self, state): if state == (None,): @@ -180,9 +168,7 @@ def update(self, sequence): for item in sequence: item_index = self.add(item) except TypeError: - raise ValueError( - "Argument needs to be an iterable, got %s" % type(sequence) - ) + raise ValueError(f"Argument needs to be an iterable, got {type(sequence)}") return item_index def index(self, key): @@ -274,7 +260,7 @@ def __reversed__(self): def __repr__(self): if not self: - return "%s()" % (self.__class__.__name__,) + return f"{self.__class__.__name__}()" return "%s(%r)" % (self.__class__.__name__, list(self)) def __eq__(self, other): @@ -386,9 +372,7 @@ def issubset(self, other): >>> OrderedSet([1, 2, 3]).issubset({1, 4, 3, 5}) False """ - if len(self) > len(other): # Fast check for obvious cases - return False - return all(item in other for item in self) + return False if len(self) > len(other) else all(item in other for item in self) def issuperset(self, other): """ @@ -402,9 +386,7 @@ def issuperset(self, other): >>> OrderedSet([1, 4, 3, 5]).issuperset({1, 2, 3}) False """ - if len(self) < len(other): # Fast check for obvious cases - return False - return all(item in self for item in other) + return False if len(self) < len(other) else all(item in self for item in other) def symmetric_difference(self, other): """ diff --git a/setuptools/_vendor/packaging/__init__.py b/setuptools/_vendor/packaging/__init__.py index 13cadc7f04..52f4c227ea 100644 --- a/setuptools/_vendor/packaging/__init__.py +++ b/setuptools/_vendor/packaging/__init__.py @@ -12,4 +12,4 @@ __email__ = "donald@stufft.io" __license__ = "BSD-2-Clause or Apache-2.0" -__copyright__ = "2014-2019 %s" % __author__ +__copyright__ = f"2014-2019 {__author__}" diff --git a/setuptools/_vendor/packaging/_manylinux.py b/setuptools/_vendor/packaging/_manylinux.py index 449c655be6..1db6fa82bf 100644 --- a/setuptools/_vendor/packaging/_manylinux.py +++ b/setuptools/_vendor/packaging/_manylinux.py @@ -161,9 +161,7 @@ def _parse_glibc_version(version_str: str) -> Tuple[int, int]: @functools.lru_cache() def _get_glibc_version() -> Tuple[int, int]: version_str = _glibc_version_string() - if version_str is None: - return (-1, -1) - return _parse_glibc_version(version_str) + return (-1, -1) if version_str is None else _parse_glibc_version(version_str) # From PEP 513, PEP 600 @@ -178,9 +176,7 @@ def _is_compatible(name: str, arch: str, version: _GLibCVersion) -> bool: return True if hasattr(_manylinux, "manylinux_compatible"): result = _manylinux.manylinux_compatible(version[0], version[1], arch) - if result is not None: - return bool(result) - return True + return bool(result) if result is not None else True if version == _GLibCVersion(2, 5): if hasattr(_manylinux, "manylinux1_compatible"): return bool(_manylinux.manylinux1_compatible) diff --git a/setuptools/_vendor/packaging/_musllinux.py b/setuptools/_vendor/packaging/_musllinux.py index 706ba600a9..0d4471d827 100644 --- a/setuptools/_vendor/packaging/_musllinux.py +++ b/setuptools/_vendor/packaging/_musllinux.py @@ -22,10 +22,10 @@ def _parse_musl_version(output: str) -> Optional[_MuslVersion]: lines = [n for n in (n.strip() for n in output.splitlines()) if n] if len(lines) < 2 or lines[0][:4] != "musl": return None - m = re.match(r"Version (\d+)\.(\d+)", lines[1]) - if not m: + if m := re.match(r"Version (\d+)\.(\d+)", lines[1]): + return _MuslVersion(major=int(m.group(1)), minor=int(m.group(2))) + else: return None - return _MuslVersion(major=int(m.group(1)), minor=int(m.group(2))) @functools.lru_cache() diff --git a/setuptools/_vendor/packaging/_parser.py b/setuptools/_vendor/packaging/_parser.py index 5a18b758fe..9138491ceb 100644 --- a/setuptools/_vendor/packaging/_parser.py +++ b/setuptools/_vendor/packaging/_parser.py @@ -318,10 +318,7 @@ def _parse_marker_var(tokenizer: Tokenizer) -> MarkerVar: def process_env_var(env_var: str) -> Variable: - if ( - env_var == "platform_python_implementation" - or env_var == "python_implementation" - ): + if env_var in {"platform_python_implementation", "python_implementation"}: return Variable("platform_python_implementation") else: return Variable(env_var) diff --git a/setuptools/_vendor/packaging/markers.py b/setuptools/_vendor/packaging/markers.py index 8b98fca723..ddbab25c1a 100644 --- a/setuptools/_vendor/packaging/markers.py +++ b/setuptools/_vendor/packaging/markers.py @@ -85,10 +85,7 @@ def _format_marker( if isinstance(marker, list): inner = (_format_marker(m, first=False) for m in marker) - if first: - return " ".join(inner) - else: - return "(" + " ".join(inner) + ")" + return " ".join(inner) if first else "(" + " ".join(inner) + ")" elif isinstance(marker, tuple): return " ".join([m.serialize() for m in marker]) else: @@ -226,10 +223,7 @@ def __hash__(self) -> int: return hash((self.__class__.__name__, str(self))) def __eq__(self, other: Any) -> bool: - if not isinstance(other, Marker): - return NotImplemented - - return str(self) == str(other) + return str(self) == str(other) if isinstance(other, Marker) else NotImplemented def evaluate(self, environment: Optional[Dict[str, str]] = None) -> bool: """Evaluate a marker. diff --git a/setuptools/_vendor/packaging/requirements.py b/setuptools/_vendor/packaging/requirements.py index f34bfa85c8..dcc28b2e7a 100644 --- a/setuptools/_vendor/packaging/requirements.py +++ b/setuptools/_vendor/packaging/requirements.py @@ -42,9 +42,7 @@ def __init__(self, requirement_string: str) -> None: if parsed_url.scheme == "file": if urllib.parse.urlunparse(parsed_url) != parsed.url: raise InvalidRequirement("Invalid URL given") - elif not (parsed_url.scheme and parsed_url.netloc) or ( - not parsed_url.scheme and not parsed_url.netloc - ): + elif not (parsed_url.scheme and parsed_url.netloc): raise InvalidRequirement(f"Invalid URL: {parsed.url}") self.url: Optional[str] = parsed.url else: diff --git a/setuptools/_vendor/packaging/specifiers.py b/setuptools/_vendor/packaging/specifiers.py index ba8fe37b7f..70174b33f1 100644 --- a/setuptools/_vendor/packaging/specifiers.py +++ b/setuptools/_vendor/packaging/specifiers.py @@ -509,7 +509,7 @@ def _compare_greater_than(self, prospective: Version, spec_str: str) -> bool: return True def _compare_arbitrary(self, prospective: Version, spec: str) -> bool: - return str(prospective).lower() == str(spec).lower() + return str(prospective).lower() == spec.lower() def __contains__(self, item: Union[str, Version]) -> bool: """Return whether or not the item is contained in this specifier. @@ -608,11 +608,11 @@ def filter( ['1.3', '1.5a1'] """ - yielded = False found_prereleases = [] kw = {"prereleases": prereleases if prereleases is not None else True} + yielded = False # Attempt to iterate over all the values in the iterable and if any of # them match, yield them. for version in iterable: @@ -622,12 +622,12 @@ def filter( # If our version is a prerelease, and we were not set to allow # prereleases, then we'll store it for later in case nothing # else matches this specifier. - if parsed_version.is_prerelease and not ( - prereleases or self.prereleases + if ( + parsed_version.is_prerelease + and not prereleases + and not self.prereleases ): found_prereleases.append(version) - # Either this is not a prerelease, or we should have been - # accepting prereleases from the beginning. else: yielded = True yield version @@ -636,8 +636,7 @@ def filter( # any values, and if we have not and we have any prereleases stored up # then we will go ahead and yield the prereleases. if not yielded and found_prereleases: - for version in found_prereleases: - yield version + yield from found_prereleases _prefix_regex = re.compile(r"^([0-9]+)((?:a|b|c|rc)[0-9]+)$") @@ -646,8 +645,7 @@ def filter( def _version_split(version: str) -> List[str]: result: List[str] = [] for item in version.split("."): - match = _prefix_regex.search(item) - if match: + if match := _prefix_regex.search(item): result.extend(match.groups()) else: result.append(item) @@ -707,12 +705,9 @@ def __init__( # strip each item to remove leading/trailing whitespace. split_specifiers = [s.strip() for s in specifiers.split(",") if s.strip()] - # Parsed each individual specifier, attempting first to make it a - # Specifier. - parsed: Set[Specifier] = set() - for specifier in split_specifiers: - parsed.add(Specifier(specifier)) - + parsed: Set[Specifier] = { + Specifier(specifier) for specifier in split_specifiers + } # Turn our parsed specifiers into a frozen set and save them for later. self._specs = frozenset(parsed) @@ -730,12 +725,7 @@ def prereleases(self) -> Optional[bool]: # If we don't have any specifiers, and we don't have a forced value, # then we'll just return None since we don't know if this should have # pre-releases or not. - if not self._specs: - return None - - # Otherwise we'll see if any of the given specifiers accept - # prereleases, if any of them do we'll return True, otherwise False. - return any(s.prereleases for s in self._specs) + return None if not self._specs else any(s.prereleases for s in self._specs) @prereleases.setter def prereleases(self, value: bool) -> None: diff --git a/setuptools/_vendor/packaging/tags.py b/setuptools/_vendor/packaging/tags.py index 76d243414d..4abd3583b5 100644 --- a/setuptools/_vendor/packaging/tags.py +++ b/setuptools/_vendor/packaging/tags.py @@ -196,10 +196,7 @@ def cpython_tags( interpreter = f"cp{_version_nodot(python_version[:2])}" if abis is None: - if len(python_version) > 1: - abis = _cpython_abis(python_version, warn) - else: - abis = [] + abis = _cpython_abis(python_version, warn) if len(python_version) > 1 else [] abis = list(abis) # 'abi3' and 'none' are explicitly handled later. for explicit_abi in ("abi3", "none"): @@ -285,10 +282,7 @@ def generic_tags( interp_name = interpreter_name() interp_version = interpreter_version(warn=warn) interpreter = "".join([interp_name, interp_version]) - if abis is None: - abis = _generic_abi() - else: - abis = list(abis) + abis = _generic_abi() if abis is None else list(abis) platforms = list(platforms or platform_tags()) if "none" not in abis: abis.append("none") @@ -341,10 +335,7 @@ def _mac_arch(arch: str, is_32bit: bool = _32_BIT_INTERPRETER) -> str: if not is_32bit: return arch - if arch.startswith("ppc"): - return "ppc" - - return "i386" + return "ppc" if arch.startswith("ppc") else "i386" def _mac_binary_formats(version: MacVersion, cpu_arch: str) -> List[str]: @@ -411,12 +402,8 @@ def mac_platforms( version = cast("MacVersion", tuple(map(int, version_str.split(".")[:2]))) else: version = version - if arch is None: - arch = _mac_arch(cpu_arch) - else: - arch = arch - - if (10, 0) <= version and version < (11, 0): + arch = _mac_arch(cpu_arch) if arch is None else arch + if (10, 0) <= version < (11, 0): # Prior to Mac OS 11, each yearly release of Mac OS bumped the # "minor" version number. The major version was always 10. for minor_version in range(version[1], -1, -1): @@ -457,9 +444,9 @@ def mac_platforms( binary_format=binary_format, ) else: + binary_format = "universal2" for minor_version in range(16, 3, -1): compat_version = 10, minor_version - binary_format = "universal2" yield "macosx_{major}_{minor}_{binary_format}".format( major=compat_version[0], minor=compat_version[1], @@ -512,10 +499,7 @@ def interpreter_version(*, warn: bool = False) -> str: Returns the version of the running interpreter. """ version = _get_config_var("py_version_nodot", warn=warn) - if version: - version = str(version) - else: - version = _version_nodot(sys.version_info[:2]) + version = str(version) if version else _version_nodot(sys.version_info[:2]) return version @@ -540,7 +524,7 @@ def sys_tags(*, warn: bool = False) -> Iterator[Tag]: if interp_name == "pp": interp = "pp3" elif interp_name == "cp": - interp = "cp" + interpreter_version(warn=warn) + interp = f"cp{interpreter_version(warn=warn)}" else: interp = None yield from compatible_tags(interpreter=interp) diff --git a/setuptools/_vendor/packaging/version.py b/setuptools/_vendor/packaging/version.py index b30e8cbf84..048b201ca9 100644 --- a/setuptools/_vendor/packaging/version.py +++ b/setuptools/_vendor/packaging/version.py @@ -470,20 +470,13 @@ def _parse_letter_version( letter = "a" elif letter == "beta": letter = "b" - elif letter in ["c", "pre", "preview"]: + elif letter in {"c", "pre", "preview"}: letter = "rc" - elif letter in ["rev", "r"]: + elif letter in {"rev", "r"}: letter = "post" return letter, int(number) - if not letter and number: - # We assume if we are given a number, but we are not given a letter - # then this is using the implicit post release syntax (e.g. 1.0-1) - letter = "post" - - return letter, int(number) - - return None + return ("post", int(number)) if number else None _local_version_separators = re.compile(r"[\._-]") @@ -533,19 +526,9 @@ def _cmpkey( _pre = pre # Versions without a post segment should sort before those with one. - if post is None: - _post: PrePostDevType = NegativeInfinity - - else: - _post = post - + _post = NegativeInfinity if post is None else post # Versions without a development segment should sort after those with one. - if dev is None: - _dev: PrePostDevType = Infinity - - else: - _dev = dev - + _dev = Infinity if dev is None else dev if local is None: # Versions without a local segment should sort before those with one. _local: LocalType = NegativeInfinity diff --git a/setuptools/_vendor/tomli/_parser.py b/setuptools/_vendor/tomli/_parser.py index f1bb0aa19a..ba3dfe0e67 100644 --- a/setuptools/_vendor/tomli/_parser.py +++ b/setuptools/_vendor/tomli/_parser.py @@ -592,23 +592,23 @@ def parse_value( # noqa: C901 # IMPORTANT: order conditions based on speed of checking and likelihood # Basic strings - if char == '"': - if src.startswith('"""', pos): - return parse_multiline_str(src, pos, literal=False) - return parse_one_line_basic_str(src, pos) - - # Literal strings if char == "'": - if src.startswith("'''", pos): - return parse_multiline_str(src, pos, literal=True) - return parse_literal_str(src, pos) - - # Booleans - if char == "t": + return ( + parse_multiline_str(src, pos, literal=True) + if src.startswith("'''", pos) + else parse_literal_str(src, pos) + ) + elif char == "t": if src.startswith("true", pos): return pos + 4, True - if char == "f": - if src.startswith("false", pos): + elif char == '"': + return ( + parse_multiline_str(src, pos, literal=False) + if src.startswith('"""', pos) + else parse_one_line_basic_str(src, pos) + ) + if src.startswith("false", pos): + if char == "f": return pos + 5, False # Arrays @@ -619,23 +619,16 @@ def parse_value( # noqa: C901 if char == "{": return parse_inline_table(src, pos, parse_float) - # Dates and times - datetime_match = RE_DATETIME.match(src, pos) - if datetime_match: + if datetime_match := RE_DATETIME.match(src, pos): try: datetime_obj = match_to_datetime(datetime_match) except ValueError as e: raise suffixed_err(src, pos, "Invalid date or datetime") from e return datetime_match.end(), datetime_obj - localtime_match = RE_LOCALTIME.match(src, pos) - if localtime_match: + if localtime_match := RE_LOCALTIME.match(src, pos): return localtime_match.end(), match_to_localtime(localtime_match) - # Integers and "normal" floats. - # The regex will greedily match any type starting with a decimal - # char, so needs to be located after handling of dates and times. - number_match = RE_NUMBER.match(src, pos) - if number_match: + if number_match := RE_NUMBER.match(src, pos): return number_match.end(), match_to_number(number_match, parse_float) # Special floats @@ -657,10 +650,7 @@ def coord_repr(src: str, pos: Pos) -> str: if pos >= len(src): return "end of document" line = src.count("\n", 0, pos) + 1 - if line == 1: - column = pos + 1 - else: - column = pos - src.rindex("\n", 0, pos) + column = pos + 1 if line == 1 else pos - src.rindex("\n", 0, pos) return f"line {line}, column {column}" return TOMLDecodeError(f"{msg} (at {coord_repr(src, pos)})") diff --git a/setuptools/_vendor/typing_extensions.py b/setuptools/_vendor/typing_extensions.py index 9f1c7aa31e..42417d81f9 100644 --- a/setuptools/_vendor/typing_extensions.py +++ b/setuptools/_vendor/typing_extensions.py @@ -133,7 +133,7 @@ def __subclasscheck__(self, cls): class _FinalForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): item = typing._type_check(parameters, @@ -187,9 +187,7 @@ def __getitem__(self, item): def _eval_type(self, globalns, localns): new_tp = typing._eval_type(self.__type__, globalns, localns) - if new_tp == self.__type__: - return self - return type(self)(new_tp, _root=True) + return self if new_tp == self.__type__ else type(self)(new_tp, _root=True) def __repr__(self): r = super().__repr__() @@ -250,7 +248,7 @@ def IntVar(name): class _LiteralForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): return typing._GenericAlias(self, parameters) @@ -1289,7 +1287,7 @@ class AnnotatedMeta(typing.GenericMeta): def __new__(cls, name, bases, namespace, **kwargs): if any(b is not object for b in bases): - raise TypeError("Cannot subclass " + str(Annotated)) + raise TypeError(f"Cannot subclass {str(Annotated)}") return super().__new__(cls, name, bases, namespace, **kwargs) @property @@ -1324,10 +1322,7 @@ def _get_cons(self): tree = self._subs_tree() while isinstance(tree, tuple) and tree[0] is Annotated: tree = tree[1] - if isinstance(tree, tuple): - return tree[0] - else: - return tree + return tree[0] if isinstance(tree, tuple) else tree @typing._tp_cache def __getitem__(self, params): @@ -1453,9 +1448,7 @@ def get_origin(tp): if isinstance(tp, (typing._GenericAlias, GenericAlias, _BaseGenericAlias, ParamSpecArgs, ParamSpecKwargs)): return tp.__origin__ - if tp is typing.Generic: - return typing.Generic - return None + return typing.Generic if tp is typing.Generic else None def get_args(tp): """Get type arguments with all substitutions performed. @@ -1487,7 +1480,7 @@ def get_args(tp): elif sys.version_info[:2] >= (3, 9): class _TypeAliasForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' @_TypeAliasForm def TypeAlias(self, parameters): @@ -1506,7 +1499,7 @@ def TypeAlias(self, parameters): elif sys.version_info[:2] >= (3, 7): class _TypeAliasForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' TypeAlias = _TypeAliasForm('TypeAlias', doc="""Special marker indicating that an assignment should @@ -1800,7 +1793,7 @@ def Concatenate(self, parameters): elif sys.version_info[:2] >= (3, 7): class _ConcatenateForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): return _concatenate_getitem(self, parameters) @@ -1861,7 +1854,7 @@ def __getitem__(self, parameters): elif sys.version_info[:2] >= (3, 9): class _TypeGuardForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' @_TypeGuardForm def TypeGuard(self, parameters): @@ -1914,7 +1907,7 @@ def is_str(val: Union[str, float]): class _TypeGuardForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): item = typing._type_check(parameters, @@ -2026,9 +2019,7 @@ def __getitem__(self, item): def _eval_type(self, globalns, localns): new_tp = typing._eval_type(self.__type__, globalns, localns) - if new_tp == self.__type__: - return self - return type(self)(new_tp, _root=True) + return self if new_tp == self.__type__ else type(self)(new_tp, _root=True) def __repr__(self): r = super().__repr__() @@ -2142,7 +2133,7 @@ def __subclasscheck__(self, cls): elif sys.version_info[:2] >= (3, 9): class _ExtensionsSpecialForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' @_ExtensionsSpecialForm def Required(self, parameters): @@ -2184,11 +2175,10 @@ class Movie(TypedDict): elif sys.version_info[:2] >= (3, 7): class _RequiredForm(typing._SpecialForm, _root=True): def __repr__(self): - return 'typing_extensions.' + self._name + return f'typing_extensions.{self._name}' def __getitem__(self, parameters): - item = typing._type_check(parameters, - '{} accepts only single type'.format(self._name)) + item = typing._type_check(parameters, f'{self._name} accepts only single type') return typing._GenericAlias(self, (item,)) Required = _RequiredForm( @@ -2233,22 +2223,22 @@ def __init__(self, tp=None, **kwds): def __getitem__(self, item): cls = type(self) if self.__type__ is None: - return cls(typing._type_check(item, - '{} accepts only single type.'.format(cls.__name__[1:])), - _root=True) - raise TypeError('{} cannot be further subscripted' - .format(cls.__name__[1:])) + return cls( + typing._type_check( + item, f'{cls.__name__[1:]} accepts only single type.' + ), + _root=True, + ) + raise TypeError(f'{cls.__name__[1:]} cannot be further subscripted') def _eval_type(self, globalns, localns): new_tp = typing._eval_type(self.__type__, globalns, localns) - if new_tp == self.__type__: - return self - return type(self)(new_tp, _root=True) + return self if new_tp == self.__type__ else type(self)(new_tp, _root=True) def __repr__(self): r = super().__repr__() if self.__type__ is not None: - r += '[{}]'.format(typing._type_repr(self.__type__)) + r += f'[{typing._type_repr(self.__type__)}]' return r def __hash__(self): diff --git a/setuptools/_vendor/zipp.py b/setuptools/_vendor/zipp.py index 26b723c1fd..d6abd364af 100644 --- a/setuptools/_vendor/zipp.py +++ b/setuptools/_vendor/zipp.py @@ -93,7 +93,7 @@ def resolve_dir(self, name): as a directory (with the trailing slash). """ names = self._name_set() - dirname = name + '/' + dirname = f'{name}/' dir_match = name not in names and dirname in names return dirname if dir_match else name diff --git a/setuptools/archive_util.py b/setuptools/archive_util.py index 6b8460bd92..ef8e0b2b83 100644 --- a/setuptools/archive_util.py +++ b/setuptools/archive_util.py @@ -59,7 +59,7 @@ def unpack_archive(filename, extract_dir, progress_filter=default_filter, driver else: return else: - raise UnrecognizedFormat("Not a recognized archive type: %s" % filename) + raise UnrecognizedFormat(f"Not a recognized archive type: {filename}") def unpack_directory(filename, extract_dir, progress_filter=default_filter): @@ -68,7 +68,7 @@ def unpack_directory(filename, extract_dir, progress_filter=default_filter): Raises ``UnrecognizedFormat`` if `filename` is not a directory """ if not os.path.isdir(filename): - raise UnrecognizedFormat("%s is not a directory" % filename) + raise UnrecognizedFormat(f"{filename} is not a directory") paths = { filename: ('', extract_dir), @@ -98,7 +98,7 @@ def unpack_zipfile(filename, extract_dir, progress_filter=default_filter): """ if not zipfile.is_zipfile(filename): - raise UnrecognizedFormat("%s is not a zip file" % (filename,)) + raise UnrecognizedFormat(f"{filename} is not a zip file") with zipfile.ZipFile(filename) as z: _unpack_zipfile_obj(z, extract_dir, progress_filter) @@ -129,8 +129,7 @@ def _unpack_zipfile_obj(zipfile_obj, extract_dir, progress_filter=default_filter data = zipfile_obj.read(info.filename) with open(target, 'wb') as f: f.write(data) - unix_attributes = info.external_attr >> 16 - if unix_attributes: + if unix_attributes := info.external_attr >> 16: os.chmod(target, unix_attributes) @@ -146,10 +145,9 @@ def _resolve_tar_file_or_dir(tar_obj, tar_member_obj): linkpath = posixpath.normpath(linkpath) tar_member_obj = tar_obj._getmember(linkpath) - is_file_or_dir = tar_member_obj is not None and ( + if is_file_or_dir := tar_member_obj is not None and ( tar_member_obj.isfile() or tar_member_obj.isdir() - ) - if is_file_or_dir: + ): return tar_member_obj raise LookupError('Got unknown file type') @@ -195,7 +193,7 @@ def unpack_tarfile(filename, extract_dir, progress_filter=default_filter): tarobj = tarfile.open(filename) except tarfile.TarError as e: raise UnrecognizedFormat( - "%s is not a compressed or uncompressed tar file" % (filename,) + f"{filename} is not a compressed or uncompressed tar file" ) from e for member, final_dst in _iter_open_tar( @@ -203,13 +201,9 @@ def unpack_tarfile(filename, extract_dir, progress_filter=default_filter): extract_dir, progress_filter, ): - try: + with contextlib.suppress(tarfile.ExtractError): # XXX Ugh tarobj._extract_member(member, final_dst) - except tarfile.ExtractError: - # chown/chmod/mkfifo/mknode/makedev failed - pass - return True diff --git a/setuptools/build_meta.py b/setuptools/build_meta.py index 0a0abfdae0..e71892864a 100644 --- a/setuptools/build_meta.py +++ b/setuptools/build_meta.py @@ -254,10 +254,10 @@ def _editable_args(self, config_settings: _ConfigSettings) -> Iterator[str]: ['--mode', 'strict'] """ cfg = config_settings or {} - mode = cfg.get("editable-mode") or cfg.get("editable_mode") - if not mode: + if mode := cfg.get("editable-mode") or cfg.get("editable_mode"): + yield from ["--mode", str(mode)] + else: return - yield from ["--mode", str(mode)] def _arbitrary_args(self, config_settings: _ConfigSettings) -> Iterator[str]: """ @@ -344,7 +344,7 @@ def _find_info_directory(self, metadata_directory: str, suffix: str) -> Path: for parent, dirs, _ in os.walk(metadata_directory): candidates = [f for f in dirs if f.endswith(suffix)] - if len(candidates) != 0 or len(dirs) != 1: + if candidates or len(dirs) != 1: assert len(candidates) == 1, f"Multiple {suffix} directories found" return Path(parent, candidates[0]) diff --git a/setuptools/depends.py b/setuptools/depends.py index 42907d9bd4..2c87e5e046 100644 --- a/setuptools/depends.py +++ b/setuptools/depends.py @@ -32,7 +32,7 @@ def __init__( def full_name(self): """Return full package/distribution name, w/version""" if self.requested_version is not None: - return '%s-%s' % (self.name, self.requested_version) + return f'{self.name}-{self.requested_version}' return self.name def version_ok(self, version): @@ -78,9 +78,7 @@ def is_present(self, paths=None): def is_current(self, paths=None): """Return true if dependency is present and up-to-date on 'paths'""" version = self.get_version(paths) - if version is None: - return False - return self.version_ok(str(version)) + return False if version is None else self.version_ok(str(version)) def maybe_close(f): @@ -89,10 +87,7 @@ def empty(): yield return - if not f: - return empty() - - return contextlib.closing(f) + return empty() if not f else contextlib.closing(f) def get_module_constant(module, symbol, default=-1, paths=None): @@ -154,7 +149,7 @@ def extract_constant(code, symbol, default=-1): if op == LOAD_CONST: const = code.co_consts[arg] - elif arg == name_idx and (op == STORE_NAME or op == STORE_GLOBAL): + elif arg == name_idx and op in [STORE_NAME, STORE_GLOBAL]: return const else: const = default diff --git a/setuptools/discovery.py b/setuptools/discovery.py index 25962863b9..cefc5cb61b 100644 --- a/setuptools/discovery.py +++ b/setuptools/discovery.py @@ -331,9 +331,7 @@ def _root_dir(self) -> _Path: @property def _package_dir(self) -> Dict[str, str]: - if self.dist.package_dir is None: - return {} - return self.dist.package_dir + return {} if self.dist.package_dir is None else self.dist.package_dir def __call__(self, force=False, name=True, ignore_ext_modules=False): """Automatically discover missing configuration fields @@ -489,11 +487,10 @@ def analyse_name(self): log.debug("No `name` configuration, performing automatic discovery") - name = ( + if name := ( self._find_name_single_package_or_module() or self._find_name_from_packages() - ) - if name: + ): self.dist.metadata.name = name def _find_name_single_package_or_module(self) -> Optional[str]: @@ -514,8 +511,9 @@ def _find_name_from_packages(self) -> Optional[str]: packages = remove_stubs(sorted(self.dist.packages, key=len)) package_dir = self.dist.package_dir or {} - parent_pkg = find_parent_package(packages, package_dir, self._root_dir) - if parent_pkg: + if parent_pkg := find_parent_package( + packages, package_dir, self._root_dir + ): log.debug(f"Common parent package detected, name: {parent_pkg}") return parent_pkg diff --git a/setuptools/dist.py b/setuptools/dist.py index 0d35583dbc..05713ce53d 100644 --- a/setuptools/dist.py +++ b/setuptools/dist.py @@ -321,9 +321,7 @@ def _validate_metadata(self): for key in vars(self.metadata) if getattr(self.metadata, key, None) is not None } - missing = required - provided - - if missing: + if missing := required - provided: msg = f"Required package metadata is missing: {missing}" raise DistutilsSetupError(msg) @@ -367,9 +365,7 @@ def _finalize_requires(self): if self.extras_require: for extra in self.extras_require.keys(): - # Setuptools allows a weird ": syntax for extras - extra = extra.split(':')[0] - if extra: + if extra := extra.split(':')[0]: self.metadata.provides_extras.add(extra) def _normalize_requires(self): @@ -554,7 +550,7 @@ def make_option_lowercase(self, opt, section): return lowercase_opt # FIXME: 'Distribution._set_command_options' is too complex (14) - def _set_command_options(self, command_obj, option_dict=None): # noqa: C901 + def _set_command_options(self, command_obj, option_dict=None): # noqa: C901 """ Set the options for 'command_obj' from 'option_dict'. Basically this means copying elements of a dictionary ('option_dict') to @@ -571,10 +567,10 @@ def _set_command_options(self, command_obj, option_dict=None): # noqa: C901 option_dict = self.get_option_dict(command_name) if DEBUG: - self.announce(" setting options for '%s' command:" % command_name) + self.announce(f" setting options for '{command_name}' command:") for option, (source, value) in option_dict.items(): if DEBUG: - self.announce(" %s = %s (from %s)" % (option, value, source)) + self.announce(f" {option} = {value} (from {source})") try: bool_opts = [translate_longopt(o) for o in command_obj.boolean_options] except AttributeError: @@ -594,8 +590,7 @@ def _set_command_options(self, command_obj, option_dict=None): # noqa: C901 setattr(command_obj, option, value) else: raise DistutilsOptionError( - "error in %s: command '%s' has no such option '%s'" - % (source, command_name, option) + f"error in {source}: command '{command_name}' has no such option '{option}'" ) except ValueError as e: raise DistutilsOptionError(e) from e @@ -742,8 +737,7 @@ def include(self, **attrs): handle whatever special inclusion logic is needed. """ for k, v in attrs.items(): - include = getattr(self, '_include_' + k, None) - if include: + if include := getattr(self, f'_include_{k}', None): include(v) else: self._include_misc(k, v) @@ -751,7 +745,7 @@ def include(self, **attrs): def exclude_package(self, package): """Remove packages, modules, and extensions in named package""" - pfx = package + '.' + pfx = f'{package}.' if self.packages: self.packages = [ p for p in self.packages if p != package and not p.startswith(pfx) @@ -772,7 +766,7 @@ def exclude_package(self, package): def has_contents_for(self, package): """Return true if 'exclude_package(package)' would do something""" - pfx = package + '.' + pfx = f'{package}.' for p in self.iter_distribution_names(): if p == package or p.startswith(pfx): @@ -787,10 +781,10 @@ def _exclude_misc(self, name, value): try: old = getattr(self, name) except AttributeError as e: - raise DistutilsSetupError("%s: No such distribution setting" % name) from e + raise DistutilsSetupError(f"{name}: No such distribution setting") from e if old is not None and not isinstance(old, sequence): raise DistutilsSetupError( - name + ": this setting cannot be changed via include/exclude" + f"{name}: this setting cannot be changed via include/exclude" ) elif old: setattr(self, name, [item for item in old if item not in value]) @@ -803,12 +797,12 @@ def _include_misc(self, name, value): try: old = getattr(self, name) except AttributeError as e: - raise DistutilsSetupError("%s: No such distribution setting" % name) from e + raise DistutilsSetupError(f"{name}: No such distribution setting") from e if old is None: setattr(self, name, value) elif not isinstance(old, sequence): raise DistutilsSetupError( - name + ": this setting cannot be changed via include/exclude" + f"{name}: this setting cannot be changed via include/exclude" ) else: new = [item for item in value if item not in old] @@ -831,8 +825,7 @@ def exclude(self, **attrs): handle whatever special exclusion logic is needed. """ for k, v in attrs.items(): - exclude = getattr(self, '_exclude_' + k, None) - if exclude: + if exclude := getattr(self, f'_exclude_{k}', None): exclude(v) else: self._exclude_misc(k, v) diff --git a/setuptools/glob.py b/setuptools/glob.py index a184c0b643..4f806c4d9b 100644 --- a/setuptools/glob.py +++ b/setuptools/glob.py @@ -50,13 +50,13 @@ def _iglob(pathname, recursive): glob_in_dir = glob2 if recursive and _isrecursive(basename) else glob1 if not has_magic(pathname): - if basename: - if os.path.lexists(pathname): - yield pathname - else: - # Patterns ending with a slash should match only directories - if os.path.isdir(dirname): - yield pathname + if ( + basename + and os.path.lexists(pathname) + or not basename + and os.path.isdir(dirname) + ): + yield pathname return if not dirname: @@ -95,14 +95,11 @@ def glob1(dirname, pattern): def glob0(dirname, basename): - if not basename: - # `os.path.split()` returns an empty basename for paths ending with a - # directory separator. 'q*x/' should match only directories. - if os.path.isdir(dirname): - return [basename] - else: + if basename: if os.path.lexists(os.path.join(dirname, basename)): return [basename] + elif os.path.isdir(dirname): + return [basename] return [] @@ -147,10 +144,7 @@ def has_magic(s): def _isrecursive(pattern): - if isinstance(pattern, bytes): - return pattern == b'**' - else: - return pattern == '**' + return pattern == b'**' if isinstance(pattern, bytes) else pattern == '**' def escape(pathname): diff --git a/setuptools/installer.py b/setuptools/installer.py index e83f959a1b..c308785c0e 100644 --- a/setuptools/installer.py +++ b/setuptools/installer.py @@ -60,12 +60,10 @@ def _fetch_build_egg_no_warn(dist, req): # noqa: C901 # is too complex (16) # 'when using pip to install requirements.' ) quiet = 'PIP_QUIET' not in os.environ and 'PIP_VERBOSE' not in os.environ - if 'PIP_INDEX_URL' in os.environ: + if 'PIP_INDEX_URL' in os.environ or 'index_url' not in opts: index_url = None - elif 'index_url' in opts: - index_url = opts['index_url'][1] else: - index_url = None + index_url = opts['index_url'][1] find_links = ( _fixup_find_links(opts['find_links'][1])[:] if 'find_links' in opts else [] ) diff --git a/setuptools/msvc.py b/setuptools/msvc.py index aa69db5810..9ae3d65bc9 100644 --- a/setuptools/msvc.py +++ b/setuptools/msvc.py @@ -186,12 +186,12 @@ def _msvc14_get_vc_env(plat_spec): try: out = subprocess.check_output( - 'cmd /u /c "{}" {} && set'.format(vcvarsall, plat_spec), + f'cmd /u /c "{vcvarsall}" {plat_spec} && set', stderr=subprocess.STDOUT, ).decode('utf-16le', errors='replace') except subprocess.CalledProcessError as exc: raise distutils.errors.DistutilsPlatformError( - "Error executing {}".format(exc.cmd) + f"Error executing {exc.cmd}" ) from exc env = { @@ -837,7 +837,7 @@ def WindowsSdkLastVersion(self): return self._use_last_dir_name(join(self.WindowsSdkDir, 'lib')) @property # noqa: C901 - def WindowsSdkDir(self): # noqa: C901 # is too complex (12) # FIXME + def WindowsSdkDir(self): # noqa: C901 # is too complex (12) # FIXME """ Microsoft Windows SDK directory. @@ -849,15 +849,14 @@ def WindowsSdkDir(self): # noqa: C901 # is too complex (12) # FIXME sdkdir = '' for ver in self.WindowsSdkVersion: # Try to get it from registry - loc = join(self.ri.windows_sdk, 'v%s' % ver) + loc = join(self.ri.windows_sdk, f'v{ver}') sdkdir = self.ri.lookup(loc, 'installationfolder') if sdkdir: break if not sdkdir or not isdir(sdkdir): # Try to get "VC++ for Python" version from registry path = join(self.ri.vc_for_python, '%0.1f' % self.vc_ver) - install_base = self.ri.lookup(path, 'installdir') - if install_base: + if install_base := self.ri.lookup(path, 'installdir'): sdkdir = join(install_base, 'WinSDK') if not sdkdir or not isdir(sdkdir): # If fail, use default new path @@ -895,7 +894,7 @@ def WindowsSDKExecutablePath(self): arch = '' else: netfxver = 40 - hidex86 = True if self.vs_ver <= 12.0 else False + hidex86 = self.vs_ver <= 12.0 arch = self.pi.current_dir(x64=True, hidex86=hidex86) fx = 'WinSDK-NetFx%dTools%s' % (netfxver, arch.replace('\\', '-')) @@ -906,12 +905,11 @@ def WindowsSDKExecutablePath(self): regpaths += [join(self.ri.netfx_sdk, ver, fx)] for ver in self.WindowsSdkVersion: - regpaths += [join(self.ri.windows_sdk, 'v%sA' % ver, fx)] + regpaths += [join(self.ri.windows_sdk, f'v{ver}A', fx)] # Return installation folder from the more recent path for path in regpaths: - execpath = self.ri.lookup(path, 'installationfolder') - if execpath: + if execpath := self.ri.lookup(path, 'installationfolder'): return execpath @property @@ -942,8 +940,9 @@ def UniversalCRTSdkDir(self): # Find path of the more recent Kit for ver in vers: - sdkdir = self.ri.lookup(self.ri.windows_kits_roots, 'kitsroot%s' % ver) - if sdkdir: + if sdkdir := self.ri.lookup( + self.ri.windows_kits_roots, f'kitsroot{ver}' + ): return sdkdir or '' @property @@ -1209,7 +1208,7 @@ def VCLibraries(self): arch_subdir = self.pi.target_dir(x64=True) else: arch_subdir = self.pi.target_dir(hidex86=True) - paths = ['Lib%s' % arch_subdir, r'ATLMFC\Lib%s' % arch_subdir] + paths = [f'Lib{arch_subdir}', r'ATLMFC\Lib%s' % arch_subdir] if self.vs_ver >= 14.0: paths += [r'Lib\store%s' % arch_subdir] @@ -1243,10 +1242,9 @@ def VCTools(self): si = self.si tools = [join(si.VCInstallDir, 'VCPackages')] - forcex86 = True if self.vs_ver <= 10.0 else False - arch_subdir = self.pi.cross_dir(forcex86) - if arch_subdir: - tools += [join(si.VCInstallDir, 'Bin%s' % arch_subdir)] + forcex86 = self.vs_ver <= 10.0 + if arch_subdir := self.pi.cross_dir(forcex86): + tools += [join(si.VCInstallDir, f'Bin{arch_subdir}')] if self.vs_ver == 14.0: path = 'Bin%s' % self.pi.current_dir(hidex86=True) @@ -1280,13 +1278,13 @@ def OSLibraries(self): """ if self.vs_ver <= 10.0: arch_subdir = self.pi.target_dir(hidex86=True, x64=True) - return [join(self.si.WindowsSdkDir, 'Lib%s' % arch_subdir)] + return [join(self.si.WindowsSdkDir, f'Lib{arch_subdir}')] else: arch_subdir = self.pi.target_dir(x64=True) lib = join(self.si.WindowsSdkDir, 'lib') libver = self._sdk_subdir - return [join(lib, '%sum%s' % (libver, arch_subdir))] + return [join(lib, f'{libver}um{arch_subdir}')] @property def OSIncludes(self): @@ -1303,16 +1301,12 @@ def OSIncludes(self): if self.vs_ver <= 10.0: return [include, join(include, 'gl')] - else: - if self.vs_ver >= 14.0: - sdkver = self._sdk_subdir - else: - sdkver = '' - return [ - join(include, '%sshared' % sdkver), - join(include, '%sum' % sdkver), - join(include, '%swinrt' % sdkver), - ] + sdkver = self._sdk_subdir if self.vs_ver >= 14.0 else '' + return [ + join(include, f'{sdkver}shared'), + join(include, f'{sdkver}um'), + join(include, f'{sdkver}winrt'), + ] @property def OSLibpath(self): @@ -1379,7 +1373,7 @@ def _sdk_tools(self): if not self.pi.current_is_x86(): arch_subdir = self.pi.current_dir(x64=True) - path = 'Bin%s' % arch_subdir + path = f'Bin{arch_subdir}' yield join(self.si.WindowsSdkDir, path) if self.vs_ver in (10.0, 11.0): @@ -1394,7 +1388,7 @@ def _sdk_tools(self): path = join(self.si.WindowsSdkDir, 'Bin') arch_subdir = self.pi.current_dir(x64=True) sdkver = self.si.WindowsSdkLastVersion - yield join(path, '%s%s' % (sdkver, arch_subdir)) + yield join(path, f'{sdkver}{arch_subdir}') if self.si.WindowsSDKExecutablePath: yield self.si.WindowsSDKExecutablePath @@ -1422,10 +1416,7 @@ def SdkSetup(self): list of str paths """ - if self.vs_ver > 9.0: - return [] - - return [join(self.si.WindowsSdkDir, 'Setup')] + return [] if self.vs_ver > 9.0 else [join(self.si.WindowsSdkDir, 'Setup')] @property def FxTools(self): @@ -1556,7 +1547,7 @@ def UCRTLibraries(self): arch_subdir = self.pi.target_dir(x64=True) lib = join(self.si.UniversalCRTSdkDir, 'lib') ucrtver = self._ucrt_subdir - return [join(lib, '%sucrt%s' % (ucrtver, arch_subdir))] + return [join(lib, f'{ucrtver}ucrt{arch_subdir}')] @property def UCRTIncludes(self): @@ -1572,7 +1563,7 @@ def UCRTIncludes(self): return [] include = join(self.si.UniversalCRTSdkDir, 'include') - return [join(include, '%sucrt' % self._ucrt_subdir)] + return [join(include, f'{self._ucrt_subdir}ucrt')] @property def _ucrt_subdir(self): @@ -1597,10 +1588,7 @@ def FSharp(self): list of str paths """ - if 11.0 > self.vs_ver > 12.0: - return [] - - return [self.si.FSharpInstallDir] + return [] if 11.0 > self.vs_ver > 12.0 else [self.si.FSharpInstallDir] @property def VCRuntimeRedist(self): @@ -1728,7 +1716,7 @@ def _build_paths(self, name, spec_path_lists, exists): paths = itertools.chain(spec_paths, env_paths) extant_paths = list(filter(isdir, paths)) if exists else paths if not extant_paths: - msg = "%s environment variable is empty" % name.upper() + msg = f"{name.upper()} environment variable is empty" raise distutils.errors.DistutilsPlatformError(msg) unique_paths = unique_everseen(extant_paths) return pathsep.join(unique_paths) diff --git a/setuptools/package_index.py b/setuptools/package_index.py index 1e535bc747..fa7f95be41 100644 --- a/setuptools/package_index.py +++ b/setuptools/package_index.py @@ -114,8 +114,7 @@ def distros_for_url(url, metadata=None): base, fragment = egg_info_for_url(url) yield from distros_for_location(url, base, metadata) if fragment: - match = EGG_FRAGMENT.match(fragment) - if match: + if match := EGG_FRAGMENT.match(fragment): yield from interpret_distro_name( url, match.group(1), metadata, precedence=CHECKOUT_DIST ) @@ -230,8 +229,7 @@ def find_external_links(url, page): for tag in ("Home Page", "Download URL"): pos = page.find(tag) if pos != -1: - match = HREF.search(page, pos) - if match: + if match := HREF.search(page, pos): yield urllib.parse.urljoin(url, htmldecode(match.group(1))) @@ -278,9 +276,7 @@ def from_url(cls, url): if not fragment: return ContentChecker() match = cls.pattern.search(fragment) - if not match: - return ContentChecker() - return cls(**match.groupdict()) + return ContentChecker() if not match else cls(**match.groupdict()) def feed(self, block): self.hash.update(block) @@ -323,7 +319,7 @@ def add(self, dist): return super().add(dist) # FIXME: 'PackageIndex.process_url' is too complex (14) - def process_url(self, url, retrieve=False): # noqa: C901 + def process_url(self, url, retrieve=False): # noqa: C901 """Evaluate a URL as a possible download, and maybe retrieve it""" if url in self.scanned_urls and not retrieve: return @@ -353,7 +349,7 @@ def process_url(self, url, retrieve=False): # noqa: C901 if f is None: return if isinstance(f, urllib.error.HTTPError) and f.code == 401: - self.info("Authentication error: %s" % f.msg) + self.info(f"Authentication error: {f.msg}") self.fetched_urls[f.url] = True if 'html' not in f.headers.get('content-type', '').lower(): f.close() # not html, we can't process it @@ -387,8 +383,7 @@ def process_filename(self, fn, nested=False): for item in os.listdir(path): self.process_filename(os.path.join(path, item), True) - dists = distros_for_filename(fn) - if dists: + if dists := distros_for_filename(fn): self.debug("Found: %s", fn) list(map(self.add, dists)) @@ -469,7 +464,7 @@ def process_index(self, url, page): base, frag = egg_info_for_url(new_url) if base.endswith('.py') and not frag: if ver: - new_url += '#egg=%s-%s' % (pkg, ver) + new_url += f'#egg={pkg}-{ver}' else: self.need_version_info(url) self.scan_url(new_url) @@ -581,8 +576,7 @@ def download(self, spec, tmpdir): raised if a problem occurs during downloading. """ if not isinstance(spec, Requirement): - scheme = URL_SCHEME(spec) - if scheme: + if scheme := URL_SCHEME(spec): # It's a url, download it to tmpdir found = self._download_url(scheme.group(1), spec, tmpdir) base, fragment = egg_info_for_url(spec) @@ -684,9 +678,7 @@ def fetch(self, requirement, tmpdir, force_scan=False, source=False): object. """ dist = self.fetch_distribution(requirement, tmpdir, force_scan, source) - if dist is not None: - return dist.location - return None + return dist.location if dist is not None else None def gen_setup(self, filename, fragment, tmpdir): match = EGG_FRAGMENT.match(fragment) @@ -744,9 +736,7 @@ def _download_to(self, url, filename): checker = HashChecker.from_url(url) fp = self.open_url(url) if isinstance(fp, urllib.error.HTTPError): - raise DistutilsError( - "Can't download %s: %s %s" % (url, fp.code, fp.msg) - ) + raise DistutilsError(f"Can't download {url}: {fp.code} {fp.msg}") headers = fp.info() blocknum = 0 bs = self.dl_blocksize @@ -758,8 +748,7 @@ def _download_to(self, url, filename): self.reporthook(url, filename, blocknum, bs, size) with open(filename, 'wb') as tfp: while True: - block = fp.read(bs) - if block: + if block := fp.read(bs): checker.feed(block) tfp.write(block) blocknum += 1 @@ -786,16 +775,14 @@ def open_url(self, url, warning=None): # noqa: C901 # is too complex (12) if warning: self.warn(warning, msg) else: - raise DistutilsError('%s %s' % (url, msg)) from v + raise DistutilsError(f'{url} {msg}') from v except urllib.error.HTTPError as v: return v except urllib.error.URLError as v: if warning: self.warn(warning, v.reason) else: - raise DistutilsError( - "Download error for %s: %s" % (url, v.reason) - ) from v + raise DistutilsError(f"Download error for {url}: {v.reason}") from v except http.client.BadStatusLine as v: if warning: self.warn(warning, v.line) @@ -808,7 +795,7 @@ def open_url(self, url, warning=None): # noqa: C901 # is too complex (12) if warning: self.warn(warning, v) else: - raise DistutilsError("Download error for %s: %s" % (url, v)) from v + raise DistutilsError(f"Download error for {url}: {v}") from v def _download_url(self, scheme, url, tmpdir): # Determine download filename @@ -879,17 +866,11 @@ def _download_git(self, url, filename): url, rev = self._vcs_split_rev_from_url(url, pop_prefix=True) self.info("Doing git clone from %s to %s", url, filename) - os.system("git clone --quiet %s %s" % (url, filename)) + os.system(f"git clone --quiet {url} {filename}") if rev is not None: self.info("Checking out %s", rev) - os.system( - "git -C %s checkout --quiet %s" - % ( - filename, - rev, - ) - ) + os.system(f"git -C {filename} checkout --quiet {rev}") return filename @@ -898,17 +879,11 @@ def _download_hg(self, url, filename): url, rev = self._vcs_split_rev_from_url(url, pop_prefix=True) self.info("Doing hg clone from %s to %s", url, filename) - os.system("hg clone --quiet %s %s" % (url, filename)) + os.system(f"hg clone --quiet {url} {filename}") if rev is not None: self.info("Updating to %s", rev) - os.system( - "hg --cwd %s up -C -r %s -q" - % ( - filename, - rev, - ) - ) + os.system(f"hg --cwd {filename} up -C -r {rev} -q") return filename @@ -1053,14 +1028,13 @@ def open_with_auth(url, opener=urllib.request.urlopen): auth = None if not auth: - cred = PyPIConfig().find_credential(url) - if cred: + if cred := PyPIConfig().find_credential(url): auth = str(cred) info = cred.username, url log.info('Authenticating as %s for %s (from .pypirc)', *info) if auth: - auth = "Basic " + _encode_auth(auth) + auth = f"Basic {_encode_auth(auth)}" parts = scheme, address, path, params, query, frag new_url = urllib.parse.urlunparse(parts) request = urllib.request.Request(new_url) diff --git a/setuptools/sandbox.py b/setuptools/sandbox.py index 757074166a..ec15697e2e 100644 --- a/setuptools/sandbox.py +++ b/setuptools/sandbox.py @@ -369,9 +369,7 @@ def _mk_query(name): def wrap(self, *args, **kw): retval = original(*args, **kw) - if self._active: - return self._remap_output(name, retval) - return retval + return self._remap_output(name, retval) if self._active else retval return wrap @@ -393,16 +391,12 @@ def _remap_output(self, operation, path): def _remap_pair(self, operation, src, dst, *args, **kw): """Called for path pairs like rename, link, and symlink operations""" - return ( - self._remap_input(operation + '-from', src, *args, **kw), - self._remap_input(operation + '-to', dst, *args, **kw), - ) + return self._remap_input( + f'{operation}-from', src, *args, **kw + ), self._remap_input(f'{operation}-to', dst, *args, **kw) -if hasattr(os, 'devnull'): - _EXCEPTIONS = [os.devnull] -else: - _EXCEPTIONS = [] +_EXCEPTIONS = [os.devnull] if hasattr(os, 'devnull') else [] class DirectorySandbox(AbstractSandbox): diff --git a/setuptools/warnings.py b/setuptools/warnings.py index b3e252ca57..7f6026e626 100644 --- a/setuptools/warnings.py +++ b/setuptools/warnings.py @@ -74,8 +74,7 @@ def _format( ), (f"\nSee {see_url} for details." if see_url else None), ] - parts = [x for x in possible_parts if x] - if parts: + if parts := [x for x in possible_parts if x]: body = indent(_TEMPLATE.format(details="\n".join(parts)), _INDENT) return "\n".join([summary, "!!\n", body, "\n!!"]) return summary diff --git a/setuptools/wheel.py b/setuptools/wheel.py index 9861b5cf1c..ddce9bdc50 100644 --- a/setuptools/wheel.py +++ b/setuptools/wheel.py @@ -120,9 +120,9 @@ def install_as_egg(self, destination_eggdir): self._install_as_egg(destination_eggdir, zf) def _install_as_egg(self, destination_eggdir, zf): - dist_basename = '%s-%s' % (self.project_name, self.version) + dist_basename = f'{self.project_name}-{self.version}' dist_info = self.get_dist_info(zf) - dist_data = '%s.data' % dist_basename + dist_data = f'{dist_basename}.data' egg_info = os.path.join(destination_eggdir, 'EGG-INFO') self._convert_metadata(zf, destination_eggdir, dist_info, egg_info) @@ -143,7 +143,7 @@ def get_metadata(name): wheel_version = parse_version(wheel_metadata.get('Wheel-Version')) wheel_v1 = parse_version('1.0') <= wheel_version < parse_version('2.0dev0') if not wheel_v1: - raise ValueError('unsupported wheel format version: %s' % wheel_version) + raise ValueError(f'unsupported wheel format version: {wheel_version}') # Extract to target directory. _unpack_zipfile_obj(zf, destination_eggdir) # Convert metadata.