Description
Follow-up to #1700 and #2352.
#2352 successfully decomposed func_metadata() into smaller helpers, addressing the first acceptance criterion of #1700. This issue tracks the remaining work: introducing a strategy/registry pattern for type handling.
Problem
_create_output_model() (extracted in #2352) still uses a long chain of if isinstance(...) checks to dispatch to the right model creation strategy for each type family (BaseModel, TypedDict, dataclasses, primitives, GenericAlias, etc.). Adding support for a new type family means modifying this function directly.
Proposal
Introduce a registry-based dispatch for type handling in _create_output_model():
- Define a protocol/interface for type handlers (e.g.,
TypeHandler with can_handle(type_expr) -> bool and create_model(type_expr, ...) -> BaseModel | None).
- Register built-in handlers for the existing type families.
- Allow external registration of custom type handlers for extensibility.
_create_output_model() iterates over registered handlers instead of hardcoded checks.
Why
- Extensibility: New type families can be supported without modifying core dispatch logic.
- Separation of concerns: Each handler encapsulates its own type detection and model creation.
- Testability: Handlers can be tested in isolation.
Acceptance criteria
References
Description
Follow-up to #1700 and #2352.
#2352 successfully decomposed
func_metadata()into smaller helpers, addressing the first acceptance criterion of #1700. This issue tracks the remaining work: introducing a strategy/registry pattern for type handling.Problem
_create_output_model()(extracted in #2352) still uses a long chain ofif isinstance(...)checks to dispatch to the right model creation strategy for each type family (BaseModel, TypedDict, dataclasses, primitives, GenericAlias, etc.). Adding support for a new type family means modifying this function directly.Proposal
Introduce a registry-based dispatch for type handling in
_create_output_model():TypeHandlerwithcan_handle(type_expr) -> boolandcreate_model(type_expr, ...) -> BaseModel | None)._create_output_model()iterates over registered handlers instead of hardcoded checks.Why
Acceptance criteria
_create_output_model()uses a registry/strategy pattern.References