Skip to content

Commit 530f5da

Browse files
committed
importlib_metadata: define protocol for Distribution.metadata
Signed-off-by: Filipe Laíns <[email protected]>
1 parent 9aee90b commit 530f5da

File tree

3 files changed

+35
-2
lines changed

3 files changed

+35
-2
lines changed

importlib_metadata/__init__.py

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,13 +17,15 @@
1717
NullFinder,
1818
PyPy_repr,
1919
install,
20+
Protocol,
2021
)
2122

2223
from configparser import ConfigParser
2324
from contextlib import suppress
2425
from importlib import import_module
2526
from importlib.abc import MetaPathFinder
2627
from itertools import starmap
28+
from typing import Any, List, TypeVar, Union
2729

2830

2931
__all__ = [
@@ -166,6 +168,25 @@ def __repr__(self):
166168
return '<FileHash mode: {} value: {}>'.format(self.mode, self.value)
167169

168170

171+
_T = TypeVar("_T")
172+
173+
174+
class PackageMetadata(Protocol):
175+
def __len__(self) -> int:
176+
... # pragma: no cover
177+
178+
def __contains__(self, item: str) -> bool:
179+
... # pragma: no cover
180+
181+
def __getitem__(self, key: str) -> str:
182+
... # pragma: no cover
183+
184+
def get_all(self, name: str, failobj: _T = ...) -> Union[List[Any], _T]:
185+
"""
186+
Return all values associated with a possibly multi-valued key.
187+
"""
188+
189+
169190
class Distribution:
170191
"""A Python distribution package."""
171192

@@ -250,7 +271,7 @@ def _local(cls, root='.'):
250271
return PathDistribution(zipp.Path(meta.build_as_zip(builder)))
251272

252273
@property
253-
def metadata(self):
274+
def metadata(self) -> PackageMetadata:
254275
"""Return the parsed metadata for this Distribution.
255276
256277
The returned object will have keys that name the various bits of

importlib_metadata/_compat.py

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,18 @@
11
import sys
22

33

4-
__all__ = ['install', 'NullFinder', 'PyPy_repr']
4+
__all__ = ['install', 'NullFinder', 'PyPy_repr', 'Protocol']
5+
6+
7+
try:
8+
from typing import Protocol
9+
except ImportError: # pragma: no cover
10+
"""
11+
pytest-mypy complains here because:
12+
error: Incompatible import of "Protocol" (imported name has type
13+
"typing_extensions._SpecialForm", local name has type "typing._SpecialForm")
14+
"""
15+
from typing_extensions import Protocol # type: ignore
516

617

718
def install(cls):

setup.cfg

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ include_package_data = true
1919
python_requires = >=3.6
2020
install_requires =
2121
zipp>=0.5
22+
typing-extensions>=3.6.4; python_version < "3.8"
2223
setup_requires = setuptools_scm[toml] >= 3.4.1
2324

2425
[options.packages.find]

0 commit comments

Comments
 (0)