如何消除unittest测试类__init__方法的typeguard无类型注解警告
背景
假设创建一个测试对象,并在其初始化过程中创建一些测试对象属性,代码如下:
class Test_mdsa(unittest.TestCase): """测试MDSA算法规范是否能检测无效规范。""" # 初始化测试对象 @typechecked def __init__(self, *args, **kwargs): # type: ignore[no-untyped-def] super().__init__(*args, **kwargs) self.mdsa = MDSA(list(range(0, 4, 1))) self.mdsa_configs = get_algo_configs(self.mdsa.__dict__) verify_algo_configs("MDSA", self.mdsa_configs)
警告信息
执行python -m pytest -k the_test时出现以下警告:
./../anaconda/envs/snncompare/lib/python3.10/site-packages/typeguard/__init__.py:1016 /home/name/anaconda/envs/snncompare/lib/python3.10/site-packages/typeguard/__init__.py:1016: UserWarning: no type annotations present -- not typechecking test_mdsa_propagation.Test_mdsa.__init__ warn('no type annotations present -- not typechecking {}'.format(function_name(func)))
问题
如何在不屏蔽警告的前提下消除该警告?或是为参数添加正确的类型注解,告知类型检查器忽略初始化方法中的*args, **kwargs?
尝试方案
原本以为# type: ignore[no-untyped-def]能解决问题,但这个注解没被警告系统识别。
解决方案1:给参数添加类型注解
TypeGuard的警告源于未识别到参数类型注解,可直接标注*args和**kwargs的类型(对应unittest.TestCase.__init__的参数类型):
from typing import Any, Sequence class Test_mdsa(unittest.TestCase): """测试MDSA算法规范是否能检测无效规范。""" # 初始化测试对象 @typechecked def __init__(self, *args: Sequence[Any], **kwargs: Any) -> None: super().__init__(*args, **kwargs) self.mdsa = MDSA(list(range(0, 4, 1))) self.mdsa_configs = get_algo_configs(self.mdsa.__dict__) verify_algo_configs("MDSA", self.mdsa_configs)
添加后TypeGuard能识别到类型注解,不会再触发警告。
解决方案2:配置@typechecked忽略无类型注解的函数
TypeGuard的@typechecked装饰器支持ignore_untyped_defs参数,开启后会跳过对当前函数的无类型注解检查:
class Test_mdsa(unittest.TestCase): """测试MDSA算法规范是否能检测无效规范。""" # 初始化测试对象 @typechecked(ignore_untyped_defs=True) def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.mdsa = MDSA(list(range(0, 4, 1))) self.mdsa_configs = get_algo_configs(self.mdsa.__dict__) verify_algo_configs("MDSA", self.mdsa_configs)
此方案无需添加类型注解,直接通过装饰器参数告知TypeGuard忽略检查。
解决方案3:改用setUp方法初始化测试资源
unittest规范推荐使用setUp方法初始化测试资源,而非重写__init__,这样能从根源避开类型检查问题:
class Test_mdsa(unittest.TestCase): """测试MDSA算法规范是否能检测无效规范。""" @typechecked def setUp(self) -> None: super().setUp() self.mdsa = MDSA(list(range(0, 4, 1))) self.mdsa_configs = get_algo_configs(self.mdsa.__dict__) verify_algo_configs("MDSA", self.mdsa_configs)
这是更符合unittest设计的写法,同时消除了警告。
内容的提问来源于stack exchange,提问作者a.t.
相关产品推荐
相关产品推荐

