根据装饰器手写ddt实现原理(提升对装饰器理解)
2022-11-23 本文已影响0人
测试探索
一:浅谈ddt
@ddt装饰器装饰类,@data装饰器装饰用例方法并传入测试数据。
@data:做的是第一步,将传入测试数据保存起来
@ddt:第二步,遍历用例数据,给测试类动态添加用例方法
image.png
二、装饰器实现
import pprint
# ==================v2通过装饰器实现,根据数据给类动态添加方法==============
def parameter(cls):
# 在装饰器内部,给cls类动态添加方法
# todo:数据不能在装饰器内部写死,需要优化
# todo:获取类里面原有的方法(不能写死,需要优化)
# 如何 动态去获取测试方法(在测试类中通过给测试方法加上装饰器对方法做标记)
# 1、先获取测试类所有的属性和方法,然后遍历,判断是否拥有is_test属性
attrs = list(cls.__dict__.items())
print("这里获取的结果:", attrs)
for name, value in attrs:
if hasattr(value, "is_test"):
cases = getattr(value, "params")
method = value
print("这里就是需要的结果", name, value, method.__dict__)
for index, item in enumerate(cases):
new_name = "{}_{}".format(name, index)
def create_test_method(method, item):
# 定义一个函数作为测试方法
def test_method(self):
# 调用原来的方法并传入
method(self, item)
return test_method
# 给类动态添加方法
setattr(cls, new_name, create_test_method(method, item))
else:
delattr(cls, name)
return cls
def data(datas):
def mark(func):
# 给被装饰的函数添加is_test属性
func.is_test = True
# 将数据datas保存为方法的属性
func.params = datas
return func
return mark
@parameter #TestDemo = parameter(TestDemo)
class TestDemo:
cases1 = [
{"title": "用例1", "data": 1111},
{"title": "用例2", "data": 2222},
{"title": "用例3", "data": 3333},
]
cases2 = [
{"title": "login2用例1", "data": 1111},
{"title": "login2用例2", "data": 2222},
{"title": "login2用例3", "data": 3333},
{"title": "login2用例4", "data": 4444}
]
@data(cases1)
def test_login(self,item):
pass
print("结果是:",item)
@data(cases2)
def test_register(self,item):
pass
pprint.pprint(TestDemo.__dict__)
image.png