Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 32 additions & 6 deletions peps/pep-0810.rst
Original file line number Diff line number Diff line change
Expand Up @@ -324,12 +324,16 @@ Example with ``lazy from ... import``:
# Accessing 'loads' now reifies it (json already loaded, no re-import)
data = loads(result)

A module may contain a :data:`!__lazy_modules__` attribute, which is a
sequence of fully qualified module names (strings) to make *potentially lazy*
(as if the ``lazy`` keyword was used). This attribute is checked on each
``import`` statement to determine whether the import should be made
*potentially lazy*. When a module is made lazy this way, from-imports using
that module are also lazy, but not necessarily imports of sub-modules.
A module may define a :data:`!__lazy_modules__` variable in its global scope,
which specifies which module names should be made *potentially lazy* (as if the
``lazy`` keyword was used). This variable is checked on each ``import``
statement to determine whether the import should be made *potentially lazy*.
The check is performed by calling ``__contains__`` on the
:data:`!__lazy_modules__` object with a string containing the fully qualified
module name being imported. Typically, :data:`!__lazy_modules__` is a set of
fully qualified module name strings. When a module is made lazy this way,
from-imports using that module are also lazy, but not necessarily imports of
sub-modules.

The normal (non-lazy) import statement will check the global lazy imports
flag. If it is "all", all imports are *potentially lazy* (except for
Expand Down Expand Up @@ -1636,6 +1640,28 @@ From the discussion on :pep:`690` it is clear that this is a fairly
contentious idea, although perhaps once we have wide-spread use of lazy
imports this can be reconsidered.

Supporting ``__lazy_modules__ = ["*"]`` as built-in syntax
-----------------------------------------------------------

The suggestion to support ``__lazy_modules__ = ["*"]`` as a convenient way to
make all imports in a module lazy without explicit enumeration has been
considered. This approach was rejected because :data:`!__lazy_modules__` already
represents implicit action-at-a-distance behavior that is tolerated solely as a
backwards compatibility mechanism. Extending support to wildcard patterns would
significantly increase implementation complexity and invite scope creep into
pattern matching and globbing functionality. As :data:`!__lazy_modules__` is a
permanent language feature that cannot be removed in future versions, the design
prioritizes minimalism and restricts its scope to serving as a transitional tool
for backwards compatibility.

It is worth noting that the implementation performs membership checks by calling
``__contains__`` on the :data:`!__lazy_modules__` object. Consequently, users
requiring wildcard behavior may provide a custom object implementing
``__contains__`` to return ``True`` for all queries or other desired patterns.
This design provides the necessary flexibility for advanced use cases while
maintaining a simple, focused specification for the primary mechanism. If this PEP is accepted, adding
such helper objects to the standard library can be discussed in a future issue. Presently, it is out of scope for this PEP.

Disallowing lazy imports inside ``with`` blocks
------------------------------------------------

Expand Down