mirror of
https://github.com/python/cpython.git
synced 2025-11-02 19:12:55 +00:00
bpo-44246: Restore compatibility in entry_points (GH-26468)
* bpo-44246: Entry points performance improvements. From importlib_metadata 4.3.1. * bpo-44246: Sync with importlib_metadata 4.4
This commit is contained in:
parent
410b70d39d
commit
c34ed08d97
3 changed files with 125 additions and 1 deletions
|
|
@ -204,7 +204,100 @@ class EntryPoint(
|
||||||
return all(map(operator.eq, params.values(), attrs))
|
return all(map(operator.eq, params.values(), attrs))
|
||||||
|
|
||||||
|
|
||||||
class EntryPoints(tuple):
|
class DeprecatedList(list):
|
||||||
|
"""
|
||||||
|
Allow an otherwise immutable object to implement mutability
|
||||||
|
for compatibility.
|
||||||
|
|
||||||
|
>>> recwarn = getfixture('recwarn')
|
||||||
|
>>> dl = DeprecatedList(range(3))
|
||||||
|
>>> dl[0] = 1
|
||||||
|
>>> dl.append(3)
|
||||||
|
>>> del dl[3]
|
||||||
|
>>> dl.reverse()
|
||||||
|
>>> dl.sort()
|
||||||
|
>>> dl.extend([4])
|
||||||
|
>>> dl.pop(-1)
|
||||||
|
4
|
||||||
|
>>> dl.remove(1)
|
||||||
|
>>> dl += [5]
|
||||||
|
>>> dl + [6]
|
||||||
|
[1, 2, 5, 6]
|
||||||
|
>>> dl + (6,)
|
||||||
|
[1, 2, 5, 6]
|
||||||
|
>>> dl.insert(0, 0)
|
||||||
|
>>> dl
|
||||||
|
[0, 1, 2, 5]
|
||||||
|
>>> dl == [0, 1, 2, 5]
|
||||||
|
True
|
||||||
|
>>> dl == (0, 1, 2, 5)
|
||||||
|
True
|
||||||
|
>>> len(recwarn)
|
||||||
|
1
|
||||||
|
"""
|
||||||
|
|
||||||
|
_warn = functools.partial(
|
||||||
|
warnings.warn,
|
||||||
|
"EntryPoints list interface is deprecated. Cast to list if needed.",
|
||||||
|
DeprecationWarning,
|
||||||
|
stacklevel=2,
|
||||||
|
)
|
||||||
|
|
||||||
|
def __setitem__(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().__setitem__(*args, **kwargs)
|
||||||
|
|
||||||
|
def __delitem__(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().__delitem__(*args, **kwargs)
|
||||||
|
|
||||||
|
def append(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().append(*args, **kwargs)
|
||||||
|
|
||||||
|
def reverse(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().reverse(*args, **kwargs)
|
||||||
|
|
||||||
|
def extend(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().extend(*args, **kwargs)
|
||||||
|
|
||||||
|
def pop(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().pop(*args, **kwargs)
|
||||||
|
|
||||||
|
def remove(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().remove(*args, **kwargs)
|
||||||
|
|
||||||
|
def __iadd__(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().__iadd__(*args, **kwargs)
|
||||||
|
|
||||||
|
def __add__(self, other):
|
||||||
|
if not isinstance(other, tuple):
|
||||||
|
self._warn()
|
||||||
|
other = tuple(other)
|
||||||
|
return self.__class__(tuple(self) + other)
|
||||||
|
|
||||||
|
def insert(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().insert(*args, **kwargs)
|
||||||
|
|
||||||
|
def sort(self, *args, **kwargs):
|
||||||
|
self._warn()
|
||||||
|
return super().sort(*args, **kwargs)
|
||||||
|
|
||||||
|
def __eq__(self, other):
|
||||||
|
if not isinstance(other, tuple):
|
||||||
|
self._warn()
|
||||||
|
other = tuple(other)
|
||||||
|
|
||||||
|
return tuple(self).__eq__(other)
|
||||||
|
|
||||||
|
|
||||||
|
class EntryPoints(DeprecatedList):
|
||||||
"""
|
"""
|
||||||
An immutable collection of selectable EntryPoint objects.
|
An immutable collection of selectable EntryPoint objects.
|
||||||
"""
|
"""
|
||||||
|
|
@ -215,6 +308,14 @@ class EntryPoints(tuple):
|
||||||
"""
|
"""
|
||||||
Get the EntryPoint in self matching name.
|
Get the EntryPoint in self matching name.
|
||||||
"""
|
"""
|
||||||
|
if isinstance(name, int):
|
||||||
|
warnings.warn(
|
||||||
|
"Accessing entry points by index is deprecated. "
|
||||||
|
"Cast to tuple if needed.",
|
||||||
|
DeprecationWarning,
|
||||||
|
stacklevel=2,
|
||||||
|
)
|
||||||
|
return super().__getitem__(name)
|
||||||
try:
|
try:
|
||||||
return next(iter(self.select(name=name)))
|
return next(iter(self.select(name=name)))
|
||||||
except StopIteration:
|
except StopIteration:
|
||||||
|
|
|
||||||
|
|
@ -130,6 +130,22 @@ class APITests(
|
||||||
assert expected.category is DeprecationWarning
|
assert expected.category is DeprecationWarning
|
||||||
assert "Construction of dict of EntryPoints is deprecated" in str(expected)
|
assert "Construction of dict of EntryPoints is deprecated" in str(expected)
|
||||||
|
|
||||||
|
def test_entry_points_by_index(self):
|
||||||
|
"""
|
||||||
|
Prior versions of Distribution.entry_points would return a
|
||||||
|
tuple that allowed access by index.
|
||||||
|
Capture this now deprecated use-case
|
||||||
|
See python/importlib_metadata#300 and bpo-44246.
|
||||||
|
"""
|
||||||
|
eps = distribution('distinfo-pkg').entry_points
|
||||||
|
with warnings.catch_warnings(record=True) as caught:
|
||||||
|
eps[0]
|
||||||
|
|
||||||
|
# check warning
|
||||||
|
expected = next(iter(caught))
|
||||||
|
assert expected.category is DeprecationWarning
|
||||||
|
assert "Accessing entry points by index is deprecated" in str(expected)
|
||||||
|
|
||||||
def test_entry_points_groups_getitem(self):
|
def test_entry_points_groups_getitem(self):
|
||||||
# Prior versions of entry_points() returned a dict. Ensure
|
# Prior versions of entry_points() returned a dict. Ensure
|
||||||
# that callers using '.__getitem__()' are supported but warned to
|
# that callers using '.__getitem__()' are supported but warned to
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,7 @@
|
||||||
|
In ``importlib.metadata``, restore compatibility in the result from
|
||||||
|
``Distribution.entry_points`` (``EntryPoints``) to honor expectations in
|
||||||
|
older implementations and issuing deprecation warnings for these cases: A. ``EntryPoints`` objects are once again mutable, allowing for ``sort()``
|
||||||
|
and other list-based mutation operations. Avoid deprecation warnings by
|
||||||
|
casting to a mutable sequence (e.g. ``list(dist.entry_points).sort()``). B. ``EntryPoints`` results once again allow for access by index. To avoid
|
||||||
|
deprecation warnings, cast the result to a Sequence first (e.g.
|
||||||
|
``tuple(dist.entry_points)[0]``).
|
||||||
Loading…
Add table
Add a link
Reference in a new issue