Skip to content

Commit

Permalink
Add module_getattr_for_deprecations
Browse files Browse the repository at this point in the history
  • Loading branch information
inducer committed Nov 21, 2024
1 parent 07c2013 commit ee69ae6
Showing 1 changed file with 34 additions and 0 deletions.
34 changes: 34 additions & 0 deletions pytools/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,7 @@
--------------------
.. autofunction:: deprecate_keyword
.. autofunction:: module_getattr_for_deprecations
Functions for dealing with (large) auxiliary files
--------------------------------------------------
Expand Down Expand Up @@ -219,6 +220,8 @@

# {{{ code maintenance

# Undocumented on purpose for now, unclear that this is a great idea, given
# that typing.deprecated exists.
class MovedFunctionDeprecationWrapper:
def __init__(self, f: F, deadline: int | str | None = None) -> None:
if deadline is None:
Expand Down Expand Up @@ -277,6 +280,37 @@ def inner_wrapper(*args, **kwargs):

return wrapper


def module_getattr_for_deprecations(
module_name: str,
depr_name_to_replacement_and_obj: Mapping[
str, tuple[str, object, str | int]
],
name: str
) -> object:
"""A helper to construct module-level :meth:`object.__getattr__` functions
so that deprecated names can still be found but raise a warning.
The typical usage pattern is as follows::
__getattr__ = partial(module_getattr_for_deprecations, __name__, {
"OldName": ("NewName", NewName, 2026),
})
"""

replacement_and_obj = depr_name_to_replacement_and_obj.get(name, None)
if replacement_and_obj is not None:
replacement, obj, deadline = replacement_and_obj
from warnings import warn

warn(f"'{module_name}.{name}' is deprecated. "
f"Use '{replacement}' instead. "
f"'{module_name}.{name}' will continue to work until {deadline}.",
DeprecationWarning, stacklevel=2)
return obj
else:
raise AttributeError(name)

# }}}


Expand Down

0 comments on commit ee69ae6

Please sign in to comment.