Python中结合Concatenate与wraps实现kwargs透传类型提示方案咨询
解决方案
要让类型提示工具正确识别configure方法的参数(无需传入self、something为字符串、展开Config的kwargs),可以结合**TypedDict + Unpack(Python 3.11+)或者ParamSpec + Concatenate**实现,以下是两种简洁方案:
方案1:Python 3.11+ 用 Unpack + TypedDict(最直观)
先定义对应Config参数的TypedDict,再在方法参数中用Unpack展开,同时保留自身的something参数:
from pydantic import BaseConfig from typing import TypedDict, Unpack # 定义Config支持的所有参数(可根据实际Config类调整) class ConfigParams(TypedDict, total=False): title: str | None arbitrary_types_allowed: bool str_max_length: int validate_assignment: bool class SomeClass: @classmethod def configure(cls, something: str, **kwargs: Unpack[ConfigParams]) -> BaseConfig: # 实际业务逻辑:初始化Config并处理 config = BaseConfig(**kwargs) print(f"Configured with something: {something}") return config
效果:
- 调用
SomeClass.configure()时,类型提示会要求传入字符串类型的something - kwargs会自动展开ConfigParams中定义的所有参数,带完整类型提示
- 无需传入
self或cls(类方法调用时自动绑定)
方案2:兼容旧版本 Python 用 ParamSpec + Concatenate
如果需要兼容Python 3.10及以下,用ParamSpec和Concatenate组合方法自身参数与Config的参数:
from pydantic import BaseConfig from functools import wraps from typing import Concatenate, ParamSpec, TypeVar, Callable P = ParamSpec("P") T = TypeVar("T", bound=BaseConfig) def bind_config_params(config_cls: type[T]) -> Callable[[Callable[Concatenate[str, P], T]], Callable[P, T]]: def decorator(func: Callable[Concatenate[str, P], T]) -> Callable[P, T]: @wraps(func) def wrapper(something: str, **kwargs: P.kwargs) -> T: return func(something, **kwargs) # 把Config的参数注解合并到wrapper,去掉self wrapper.__annotations__.update({k: v for k, v in config_cls.__init__.__annotations__.items() if k != "self"}) return wrapper return decorator class SomeClass: @bind_config_params(BaseConfig) @classmethod def configure(cls, something: str, **kwargs) -> BaseConfig: return BaseConfig(**kwargs)
效果:
- 类型提示工具会识别
something为字符串,同时自动补全Config的所有kwargs参数 - 装饰器自动继承Config的参数注解,无需手动维护TypedDict
关键说明
- 用
@classmethod而非@staticmethod:类方法会自动绑定cls参数,调用时无需手动传入,符合你“无需传入self”的需求 - 避免直接用
functools.wraps装饰Config类:因为Config的__init__包含self参数,会导致类型提示错误,必须先过滤掉self注解
内容的提问来源于stack exchange,提问作者Samreay
相关产品推荐
相关产品推荐

