diff --git a/CHANGES.rst b/CHANGES.rst index 0faf0a47..2f20b890 100644 --- a/CHANGES.rst +++ b/CHANGES.rst @@ -1,3 +1,10 @@ +v4.7.0 +====== + +* #330: In ``packages_distributions``, now infer top-level + names from ``.files()`` when a ``top-level.txt`` + (Setuptools-specific metadata) is not present. + v4.6.4 ====== diff --git a/importlib_metadata/__init__.py b/importlib_metadata/__init__.py index 82dcaf03..9bb06412 100644 --- a/importlib_metadata/__init__.py +++ b/importlib_metadata/__init__.py @@ -1013,6 +1013,18 @@ def packages_distributions() -> Mapping[str, List[str]]: """ pkg_to_dist = collections.defaultdict(list) for dist in distributions(): - for pkg in (dist.read_text('top_level.txt') or '').split(): + for pkg in _top_level_declared(dist) or _top_level_inferred(dist): pkg_to_dist[pkg].append(dist.metadata['Name']) return dict(pkg_to_dist) + + +def _top_level_declared(dist): + return (dist.read_text('top_level.txt') or '').split() + + +def _top_level_inferred(dist): + return { + f.parts[0] if len(f.parts) > 1 else f.with_suffix('').name + for f in dist.files + if f.suffix == ".py" + } diff --git a/prepare/example2/example2/__init__.py b/prepare/example2/example2/__init__.py new file mode 100644 index 00000000..de645c2e --- /dev/null +++ b/prepare/example2/example2/__init__.py @@ -0,0 +1,2 @@ +def main(): + return "example" diff --git a/prepare/example2/pyproject.toml b/prepare/example2/pyproject.toml new file mode 100644 index 00000000..011f4751 --- /dev/null +++ b/prepare/example2/pyproject.toml @@ -0,0 +1,10 @@ +[build-system] +build-backend = 'trampolim' +requires = ['trampolim'] + +[project] +name = 'example2' +version = '1.0.0' + +[project.scripts] +example = 'example2:main' diff --git a/tests/data/example2-1.0.0-py3-none-any.whl b/tests/data/example2-1.0.0-py3-none-any.whl new file mode 100644 index 00000000..5ca93657 Binary files /dev/null and b/tests/data/example2-1.0.0-py3-none-any.whl differ diff --git a/tests/fixtures.py b/tests/fixtures.py index 1b6c1753..c6e645f5 100644 --- a/tests/fixtures.py +++ b/tests/fixtures.py @@ -301,7 +301,7 @@ class ZipFixtures: def _fixture_on_path(self, filename): pkg_file = resources.files(self.root).joinpath(filename) file = self.resources.enter_context(resources.as_file(pkg_file)) - assert file.name.startswith('example-'), file.name + assert file.name.startswith('example'), file.name sys.path.insert(0, str(file)) self.resources.callback(sys.path.pop, 0) diff --git a/tests/test_main.py b/tests/test_main.py index e74435aa..081e9fa1 100644 --- a/tests/test_main.py +++ b/tests/test_main.py @@ -17,6 +17,7 @@ distributions, entry_points, metadata, + packages_distributions, version, ) @@ -282,3 +283,17 @@ def test_unicode_dir_on_sys_path(self): prefix=self.site_dir, ) list(distributions()) + + +class PackagesDistributionsTest(fixtures.ZipFixtures, unittest.TestCase): + def test_packages_distributions_example(self): + self._fixture_on_path('example-21.12-py3-none-any.whl') + assert packages_distributions()['example'] == ['example'] + + def test_packages_distributions_example2(self): + """ + Test packages_distributions on a wheel built + by trampolim. + """ + self._fixture_on_path('example2-1.0.0-py3-none-any.whl') + assert packages_distributions()['example2'] == ['example2']