Source code for typespecs.typing
__all__ = [
"del_metadata",
"get_annotation",
"get_annotations",
"get_metadata",
"get_subannotations",
"has_metadata",
"is_literal",
]
# standard library
from typing import Annotated, Any, Literal, TypeVar, overload
from typing import _strip_annotations # type: ignore
from warnings import warn
# dependencies
from typing_extensions import (
get_annotations as _get_annotations,
get_args,
get_origin,
)
# type hints
T = TypeVar("T")
[docs]
def get_annotation(annotation: Any, /, *, recursive: bool = False) -> Any:
"""Return metadata-stripped annotation.
Args:
annotation: Annotation to strip metadata from.
recursive: Whether to recursively strip metadata of sub-annotations.
Returns:
Metadata-stripped annotation.
"""
warn(
"This function will be deprecated in the next major version."
"Use ``del_metadata(annotation, recursive=recursive)`` instead.",
DeprecationWarning,
)
return del_metadata(annotation, recursive=recursive)
[docs]
def get_annotations(cls_or_obj: Any, /) -> dict[str, Any]:
"""Return annotations of given class or object.
If it is a class instance, this function tries to retrieve
the annotations from its class rather than the instance itself.
Args:
cls_or_obj: Class or object to inspect.
Returns:
Dictionary of annotations of the class or object.
"""
if isinstance(cls_or_obj, type):
return _get_annotations(cls_or_obj)
else:
return _get_annotations(type(cls_or_obj))
@overload
def get_metadata(annotation: Any, /, *, type: None = None) -> list[Any]: ...
@overload
def get_metadata(annotation: Any, /, *, type: type[T]) -> list[T]: ...
[docs]
def get_subannotations(annotation: Any, /) -> list[Any]:
"""Return sub-annotations of given annotation.
Args:
annotation: Annotation to inspect.
Returns:
List of sub-annotations of the annotation.
"""
if is_literal(annotation := del_metadata(annotation)):
return []
else:
return list(get_args(annotation))
[docs]
def is_literal(annotation: Any, /) -> bool:
"""Check if given annotation is a literal type.
Args:
annotation: Annotation to inspect.
Returns:
``True`` if the annotation is a literal type. ``False`` otherwise.
"""
return get_origin(annotation) is Literal