|
45 | 45 | SimplePath, |
46 | 46 | ) |
47 | 47 | from .compat import py311 |
| 48 | +from .compat.py314 import lazy_importer |
| 49 | + |
| 50 | +__lazy_modules__ = { |
| 51 | + 'csv', |
| 52 | + 'inspect', |
| 53 | + 'json', |
| 54 | + # 'zipfile' in the stdlib, which needs no overlay |
| 55 | + 'zipp.compat.overlay', |
| 56 | + f'{__name__}._adapters', |
| 57 | +} |
| 58 | +""" |
| 59 | +Imports to defer until first use (PEP 810). |
| 60 | +
|
| 61 | +Each of them costs more than the path that reads it is traveled, so |
| 62 | +deferring keeps that cost off every other caller. Stating it here rather |
| 63 | +than importing inside those functions leaves the dependencies visible. |
| 64 | +
|
| 65 | +Python 3.15 honors this declaration itself; earlier versions reach the |
| 66 | +same end through the context below. |
| 67 | +
|
| 68 | +The adapters are imported by member rather than as ``from . import |
| 69 | +_adapters``, which names this package as the module to defer and which |
| 70 | +no emulation can honor from inside the package itself. |
| 71 | +""" |
| 72 | + |
| 73 | +with lazy_importer(): |
| 74 | + import csv |
| 75 | + import inspect |
| 76 | + import json |
| 77 | + |
| 78 | + from zipp.compat.overlay import zipfile |
| 79 | + |
| 80 | + from ._adapters import Message |
48 | 81 |
|
49 | 82 | __all__ = [ |
50 | 83 | 'Distribution', |
@@ -599,10 +632,7 @@ def _has_metadata(self) -> bool: |
599 | 632 |
|
600 | 633 | @staticmethod |
601 | 634 | def _assemble_message(text: str) -> PackageMetadata: |
602 | | - # deferred for performance (python/cpython#109829) |
603 | | - from . import _adapters |
604 | | - |
605 | | - return _adapters.Message(email.message_from_string(text)) |
| 635 | + return Message(email.message_from_string(text)) |
606 | 636 |
|
607 | 637 | def _ensure_metadata_present(self, text: str | None) -> str: |
608 | 638 | if text is not None: |
@@ -663,10 +693,6 @@ def make_file(name, hash=None, size_str=None): |
663 | 693 |
|
664 | 694 | @pass_none |
665 | 695 | def make_files(lines): |
666 | | - # Delay csv import, since Distribution.files is not as widely used |
667 | | - # as other parts of importlib.metadata |
668 | | - import csv |
669 | | - |
670 | 696 | return starmap(make_file, csv.reader(lines)) |
671 | 697 |
|
672 | 698 | @pass_none |
@@ -788,9 +814,6 @@ def origin(self): |
788 | 814 | return self._load_json('direct_url.json') |
789 | 815 |
|
790 | 816 | def _load_json(self, filename): |
791 | | - # Deferred for performance (python/importlib_metadata#503) |
792 | | - import json |
793 | | - |
794 | 817 | return pass_none(json.loads)( |
795 | 818 | self.read_text(filename), |
796 | 819 | object_hook=lambda data: types.SimpleNamespace(**data), |
@@ -908,9 +931,6 @@ def children(self): |
908 | 931 | return [] |
909 | 932 |
|
910 | 933 | def zip_children(self): |
911 | | - # deferred for performance (python/importlib_metadata#502) |
912 | | - from zipp.compat.overlay import zipfile |
913 | | - |
914 | 934 | zip_path = zipfile.Path(self.root) |
915 | 935 | names = zip_path.root.namelist() |
916 | 936 | self.joinpath = zip_path.joinpath |
@@ -1296,9 +1316,6 @@ def _get_toplevel_name(name: IPackagePath) -> str: |
1296 | 1316 | >>> _get_toplevel_name(PackagePath('foo.dist-info')) |
1297 | 1317 | 'foo.dist-info' |
1298 | 1318 | """ |
1299 | | - # Defer import of inspect for performance (python/cpython#118761) |
1300 | | - import inspect |
1301 | | - |
1302 | 1319 | return _topmost(name) or inspect.getmodulename(name) or str(name) |
1303 | 1320 |
|
1304 | 1321 |
|
|
0 commit comments