From d5b52923c195f788819bb29e757d09f1bc9453c6 Mon Sep 17 00:00:00 2001 From: Ihar Hrachyshka Date: Thu, 20 Mar 2025 17:12:58 -0400 Subject: [PATCH] chore: mypy for strong_typing Mostly just ignores because of the dynamic nature of the codebase. One prominent change is expanding the allowed types for attributes tracking property types to allow strings (which are valid and common typing hints in python). Signed-off-by: Ihar Hrachyshka --- llama_stack/strong_typing/auxiliary.py | 2 +- llama_stack/strong_typing/deserializer.py | 2 +- llama_stack/strong_typing/docstring.py | 2 +- llama_stack/strong_typing/inspection.py | 10 +++++----- llama_stack/strong_typing/schema.py | 6 +++--- llama_stack/strong_typing/serializer.py | 5 ++++- pyproject.toml | 5 ----- 7 files changed, 15 insertions(+), 17 deletions(-) diff --git a/llama_stack/strong_typing/auxiliary.py b/llama_stack/strong_typing/auxiliary.py index cf19d6083..d5057b258 100644 --- a/llama_stack/strong_typing/auxiliary.py +++ b/llama_stack/strong_typing/auxiliary.py @@ -77,7 +77,7 @@ def typeannotation( """ def wrap(cls: Type[T]) -> Type[T]: - cls.__repr__ = _compact_dataclass_repr + cls.__repr__ = _compact_dataclass_repr # type: ignore if not dataclasses.is_dataclass(cls): cls = dataclasses.dataclass( # type: ignore[call-overload] cls, diff --git a/llama_stack/strong_typing/deserializer.py b/llama_stack/strong_typing/deserializer.py index fc0f40f83..dc6708ce5 100644 --- a/llama_stack/strong_typing/deserializer.py +++ b/llama_stack/strong_typing/deserializer.py @@ -627,7 +627,7 @@ class NamedTupleDeserializer(ClassDeserializer[NamedTuple]): super().assign(property_parsers) def create(self, **field_values: Any) -> NamedTuple: - return self.class_type(**field_values) + return self.class_type(**field_values) # type: ignore class DataclassDeserializer(ClassDeserializer[T]): diff --git a/llama_stack/strong_typing/docstring.py b/llama_stack/strong_typing/docstring.py index 9169aadfe..b038d1024 100644 --- a/llama_stack/strong_typing/docstring.py +++ b/llama_stack/strong_typing/docstring.py @@ -48,7 +48,7 @@ class DocstringParam: name: str description: str - param_type: type = inspect.Signature.empty + param_type: type | str = inspect.Signature.empty def __str__(self) -> str: return f":param {self.name}: {self.description}" diff --git a/llama_stack/strong_typing/inspection.py b/llama_stack/strong_typing/inspection.py index 8bc313021..c66ca6a51 100644 --- a/llama_stack/strong_typing/inspection.py +++ b/llama_stack/strong_typing/inspection.py @@ -431,7 +431,7 @@ def _unwrap_generic_list(typ: Type[List[T]]) -> Type[T]: "Extracts the item type of a list type (e.g. returns `T` for `List[T]`)." (list_type,) = typing.get_args(typ) # unpack single tuple element - return list_type + return list_type # type: ignore def is_generic_set(typ: object) -> TypeGuard[Type[set]]: @@ -456,7 +456,7 @@ def _unwrap_generic_set(typ: Type[Set[T]]) -> Type[T]: "Extracts the item type of a set type (e.g. returns `T` for `Set[T]`)." (set_type,) = typing.get_args(typ) # unpack single tuple element - return set_type + return set_type # type: ignore def is_generic_dict(typ: object) -> TypeGuard[Type[dict]]: @@ -513,7 +513,7 @@ def unwrap_annotated_type(typ: T) -> T: if is_type_annotated(typ): # type is Annotated[T, ...] - return typing.get_args(typ)[0] + return typing.get_args(typ)[0] # type: ignore else: # type is a regular type return typ @@ -563,7 +563,7 @@ else: return typing.get_type_hints(typ) -def get_class_properties(typ: type) -> Iterable[Tuple[str, type]]: +def get_class_properties(typ: type) -> Iterable[Tuple[str, type | str]]: "Returns all properties of a class." if is_dataclass_type(typ): @@ -573,7 +573,7 @@ def get_class_properties(typ: type) -> Iterable[Tuple[str, type]]: return resolved_hints.items() -def get_class_property(typ: type, name: str) -> Optional[type]: +def get_class_property(typ: type, name: str) -> Optional[type | str]: "Looks up the annotated type of a property in a class by its property name." for property_name, property_type in get_class_properties(typ): diff --git a/llama_stack/strong_typing/schema.py b/llama_stack/strong_typing/schema.py index de69c9b82..1beee74fa 100644 --- a/llama_stack/strong_typing/schema.py +++ b/llama_stack/strong_typing/schema.py @@ -460,13 +460,13 @@ class JsonSchemaGenerator: discriminator = None if typing.get_origin(data_type) is Annotated: discriminator = typing.get_args(data_type)[1].discriminator - ret = {"oneOf": [self.type_to_schema(union_type) for union_type in typing.get_args(typ)]} + ret: Schema = {"oneOf": [self.type_to_schema(union_type) for union_type in typing.get_args(typ)]} if discriminator: # for each union type, we need to read the value of the discriminator - mapping = {} + mapping: JsonType = {} for union_type in typing.get_args(typ): props = self.type_to_schema(union_type, force_expand=True)["properties"] - mapping[props[discriminator]["default"]] = self.type_to_schema(union_type)["$ref"] + mapping[props[discriminator]["default"]] = self.type_to_schema(union_type)["$ref"] # type: ignore ret["discriminator"] = { "propertyName": discriminator, diff --git a/llama_stack/strong_typing/serializer.py b/llama_stack/strong_typing/serializer.py index 4ca4a4119..17848c14b 100644 --- a/llama_stack/strong_typing/serializer.py +++ b/llama_stack/strong_typing/serializer.py @@ -134,7 +134,10 @@ class IPv6Serializer(Serializer[ipaddress.IPv6Address]): class EnumSerializer(Serializer[enum.Enum]): def generate(self, obj: enum.Enum) -> Union[int, str]: - return obj.value + value = obj.value + if isinstance(value, int): + return value + return str(value) class UntypedListSerializer(Serializer[list]): diff --git a/pyproject.toml b/pyproject.toml index f7125b724..75dfcbb2f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -288,11 +288,6 @@ exclude = [ "^llama_stack/providers/utils/telemetry/dataset_mixin\\.py$", "^llama_stack/providers/utils/telemetry/trace_protocol\\.py$", "^llama_stack/providers/utils/telemetry/tracing\\.py$", - "^llama_stack/strong_typing/auxiliary\\.py$", - "^llama_stack/strong_typing/deserializer\\.py$", - "^llama_stack/strong_typing/inspection\\.py$", - "^llama_stack/strong_typing/schema\\.py$", - "^llama_stack/strong_typing/serializer\\.py$", "^llama_stack/templates/dev/dev\\.py$", "^llama_stack/templates/groq/groq\\.py$", "^llama_stack/templates/sambanova/sambanova\\.py$",