bpo-38086: Sync importlib.metadata with importlib_metadata 0.21. (GH-15840)

https://gitlab.com/python-devs/importlib_metadata/-/tags/0.21
This commit is contained in:
Jason R. Coombs 2019-09-10 14:53:31 +01:00 committed by Brett Cannon
parent 97d7906e30
commit 17499d8270
8 changed files with 712 additions and 661 deletions

View file

@ -19,6 +19,7 @@ from itertools import starmap
__all__ = [
'Distribution',
'DistributionFinder',
'PackageNotFoundError',
'distribution',
'distributions',
@ -158,7 +159,7 @@ class Distribution:
metadata cannot be found.
"""
for resolver in cls._discover_resolvers():
dists = resolver(name)
dists = resolver(DistributionFinder.Context(name=name))
dist = next(dists, None)
if dist is not None:
return dist
@ -166,16 +167,33 @@ class Distribution:
raise PackageNotFoundError(name)
@classmethod
def discover(cls):
def discover(cls, **kwargs):
"""Return an iterable of Distribution objects for all packages.
Pass a ``context`` or pass keyword arguments for constructing
a context.
:context: A ``DistributionFinder.Context`` object.
:return: Iterable of Distribution objects for all packages.
"""
context = kwargs.pop('context', None)
if context and kwargs:
raise ValueError("cannot accept context and kwargs")
context = context or DistributionFinder.Context(**kwargs)
return itertools.chain.from_iterable(
resolver()
resolver(context)
for resolver in cls._discover_resolvers()
)
@staticmethod
def at(path):
"""Return a Distribution for the indicated metadata path
:param path: a string or path-like object
:return: a concrete Distribution instance for the path
"""
return PathDistribution(pathlib.Path(path))
@staticmethod
def _discover_resolvers():
"""Search the meta_path for resolvers."""
@ -215,7 +233,7 @@ class Distribution:
def files(self):
"""Files in this distribution.
:return: Iterable of PackagePath for this distribution or None
:return: List of PackagePath for this distribution or None
Result is `None` if the metadata file that enumerates files
(i.e. RECORD for dist-info or SOURCES.txt for egg-info) is
@ -231,7 +249,7 @@ class Distribution:
result.dist = self
return result
return file_lines and starmap(make_file, csv.reader(file_lines))
return file_lines and list(starmap(make_file, csv.reader(file_lines)))
def _read_files_distinfo(self):
"""
@ -251,7 +269,8 @@ class Distribution:
@property
def requires(self):
"""Generated requirements specified for this Distribution"""
return self._read_dist_info_reqs() or self._read_egg_info_reqs()
reqs = self._read_dist_info_reqs() or self._read_egg_info_reqs()
return reqs and list(reqs)
def _read_dist_info_reqs(self):
return self.metadata.get_all('Requires-Dist')
@ -312,15 +331,35 @@ class DistributionFinder(MetaPathFinder):
A MetaPathFinder capable of discovering installed distributions.
"""
class Context:
name = None
"""
Specific name for which a distribution finder should match.
"""
def __init__(self, **kwargs):
vars(self).update(kwargs)
@property
def path(self):
"""
The path that a distribution finder should search.
"""
return vars(self).get('path', sys.path)
@property
def pattern(self):
return '.*' if self.name is None else re.escape(self.name)
@abc.abstractmethod
def find_distributions(self, name=None, path=None):
def find_distributions(self, context=Context()):
"""
Find distributions.
Return an iterable of all Distribution instances capable of
loading the metadata for packages matching the ``name``
(or all names if not supplied) along the paths in the list
of directories ``path`` (defaults to sys.path).
loading the metadata for packages matching the ``context``,
a DistributionFinder.Context instance.
"""
@ -352,12 +391,12 @@ def distribution(package):
return Distribution.from_name(package)
def distributions():
def distributions(**kwargs):
"""Get all ``Distribution`` instances in the current environment.
:return: An iterable of ``Distribution`` instances.
"""
return Distribution.discover()
return Distribution.discover(**kwargs)
def metadata(package):