Pytest参数化用例
Pytest 参数化用例
简介
Pytest 中的参数化是一种非常有用的功能,通过参数的方式传递数据,从而实现数据和脚本分离。允许在同一个测试函数上多次运行相同的测试,使用不同的输入数据进而生成多个测试用例。
参数化的优点
-
简化测试代码:使用参数化测试,在测试代码中可以使用单个测试函数来覆盖多种不同的测试情况。这样可以避免编写大量重复的测试代码,并提高代码的可读性和维护性。
-
提高测试覆盖率:通过参数化测试,可以为各种场景和不同的输入提供更全面的测试覆盖。通过一次性编写多个测试用例,可以在执行中覆盖更多的测试情况,从而提高测试覆盖率。
-
减少维护成本:如果需要对测试逻辑进行更改或添加更多测试用例,使用参数化测试可以避免修改多个重复的测试用例。只需修改一个参数化测试案例,就可以覆盖所有相关的测试情况,减少了维护的工作量和成本。
参数化实现方案
使用 @pytest.mark.parametrize
装饰器为测试函数提供参数化数据。
例如测试登录场景:
- 登录成功(账号正确,密码正确)
- 登录失败(账号错误,密码错误)
代码示例:
@pytest.mark.parametrize("username,password",[["right","right"], ["wrong","wrong"]])
def test_param(username,password):
login(username,password)
参数化测试函数的使用
Pytest 的参数化功能允许灵活地为测试函数提供不同的输入参数:
- 单参数
- 多参数
- 用例重命名
- 笛卡尔积
参数化:单参数情况
- 单参数,可以将数据放在列表中。
代码示例:
search_list = ['appium','selenium','pytest']
@pytest.mark.parametrize('name',search_list)
def test_search(name):
assert name in search_list
运行结果:
参数化:多参数情况
- 将数据放在列表嵌套元组中。
- 将数据放在列表嵌套列表中。
代码示例:
# 数据放在元组中
@pytest.mark.parametrize("test_input,expected",[
("3+5",8),("2+5",7),("7+5",12)
])
def test_mark_more(test_input,expected):
assert eval(test_input) == expected
# 数据放在列表中
@pytest.mark.parametrize("test_input,expected",[
["3+5",8],["2+5",7],["7+5",12]
])
def test_mark_more(test_input,expected):
assert eval(test_input) == expected
运行结果:
参数化:用例重命名-添加 ids 参数
- 通过 ids 参数,将别名放在列表中。
- 注意 ids 列表参数的个数要与参数值的个数一致。
代码示例:
@pytest.mark.parametrize("test_input,expected",[
("3+5",8),("2+5",7),("7+5",12)
],ids=['add_3+5=8','add_2+5=7','add_3+5=12'])
def test_mark_more(test_input,expected):
assert eval(test_input) == expected
参数化:用例重命名-添加 ids 参数(中文)
代码示例:
@pytest.mark.parametrize("test_input,expected",[
("3+5",8),("2+5",7),("7+5",12)
],ids=["3和5相加","2和5相加","7和5相加"])
def test_mark_more(test_input,expected):
assert eval(test_input) == expected
测试用例重命名为中文时,需要创建 confest.py 文件,将以下代码复制进去,再运行测试脚本,中文名称就可正常显示,否则会展示为乱码。代码如下:
# 创建conftest.py 文件 ,将下面内容添加进去,运行脚本
def pytest_collection_modifyitems(items):
"""
测试用例收集完成时,将收集到的用例名name和用例标识nodeid的中文信息显示在控制台上
"""
for i in items:
i.name=i.name.encode("utf-8").decode("unicode_escape")
i._nodeid=i.nodeid.encode("utf-8").decode("unicode_escape")
参数化:笛卡尔积
-
两组数据:
-
a=[1,2,3]
-
b=[a,b,c]
-
对应有几种组合形势 ?
-
(1,a),(1,b),(1,c)
- (2,a),(2,b),(2,c)
- (3,a),(3,b),(3,c)
代码示例:
@pytest.mark.parametrize("b",["a","b","c"])
@pytest.mark.parametrize("a",[1,2,3])
def test_param1(a,b):
print(f"笛卡积形式的参数化中 a={a} , b={b}")
运行结果:
总结
- 参数化测试用例的优点。
- 参数化测试用例的实现方案。