Pytest之参数化
VOL 154
02
2020-09
今天距2021年120天
这是ITester软件测试小栈第154次推文
点击上方蓝字“ITester软件测试小栈“关注我,每周一、三、五早上 08:30准时推送,每月不定期赠送技术书籍。
微信公众号后台回复“资源”、“测试工具包”领取测试资源,回复“微信群”一起进群打怪。
本文3090字,阅读约需8分钟
在上一篇Pytest系列文章:Pytest之自定义mark,主要介绍pytest自定义配置及用例运行实战。以下主要介绍pytest参数化讲解及实战。
熟悉unittest单元测试框架的小伙伴知道,使用ddt进行数据驱动测试,那么身为功能更加强大且更加灵活的Pytest框架怎么可能没有数据驱动的概念呢?Pytest
使用@pytest.mark.parametrize
装饰器来实现数据驱动测试的,也就是常说的参数化。
一
parametrize语法
parametrize(self,argnames, argvalues, indirect=False, ids=None, scope=None)
argnames
:参数名。
argvalues
:参数对应值,类型必须为list。如果只有一个参数,里面则是值的列表:
如:@pytest.mark.parametrize("username", ["yy", "yy2", "yy3"])。如果有多个参数,则需要用元组来存放值,一个元组对应一组参数的值,如:@pytest.mark.parametrize("name,pwd", [("yy1", "123"), ("yy2", "123"), ("yy3", "123")])。
indirect
:如果设置成True,则把传进来的参数当函数执行,而不是一个参数。
ids
:用例的ID,传一个字符串列表,用来标识每一个测试用例,自定义测试数据结果,增加可读性。
二
参数讲解
1
单个数据
import pytest
data = ["小红", "小明"]
@pytest.mark.parametrize("name",data)
def test_demo(name):
print("测试数据为{}".format(name))
运行结果为:
2
一组数据
01 列表嵌套字典
import pytest
data_1 = [
{"username": "admin1", "password": "123456"},
{"username": "admin2", "password": "12345678"},
]
@pytest.mark.parametrize("data", data_1)
def test_login(data):
print("账号:{},密码:{}".format(data["username"],data["password"]))
运行结果为:
02 列表嵌套列表
import pytest
data_1 = [
["admin1", "123456"],
["admin2", "12345678"],
]
@pytest.mark.parametrize("username,password", data_1)
def test_login(username,password):
print("账号:{},密码:{}".format(username, password))
运行结果为:
03 列表嵌套元组
import pytest
data_1 = [
("admin1", "123456"),
("admin2", "12345678"),
]
@pytest.mark.parametrize("username,password", data_1)
def test_login(username,password):
print("账号:{},密码:{}".format(username, password))
运行结果为:
三
场景运用
1
装饰函数
import pytest
@pytest.mark.parametrize("username,password",[("admin01","123456"),("admin02","12345678")])
def test_demo(username,password):
print("用户名:{},密码:{}".format(username,password))
运行结果为:
2
装饰类
import pytest
@pytest.mark.parametrize("username,password",[("admin01","123456"),("admin02","12345678")])
class TestDemo:
def test_demo(self,username,password):
print("用户名:{},密码:{}".format(username,password))
运行结果为:
注意:装饰测试类时,类内所有的方法必须接收测试数据,否则会报错;装饰测试函数时比较灵活,如果函数不使用数据就可以不装饰。
3
多个参数化装饰器
使用多个参数化装饰器,数据会进行交叉组合的方式传递给测试函数,进而生成n*n个测试用例(笛卡尔积)。
test_demo.py
import pytest
username = ["admin1", "admin2", "admin3"]
password = ["123456", "1234567", "12345678"]
@pytest.mark.parametrize("uname",username)
@pytest.mark.parametrize("pwd",password)
def test_demo(uname,pwd):
print("用户名:{},密码:{}".format(uname, pwd))
运行结果如下:
4
增加可读性
parametrize参数中的ids
,可以标识每一个测试用例,自定义测试数据结果的显示,增加可读性。
test_demo.py
import pytest
data_1 = [
(1, 2, 3),
(4, 5, 9)
]
ids = ["a:{} + b:{} = expect:{}".format(a, b, expect) for a, b, expect in data_1]
def add(a, b):
return a + b
@pytest.mark.parametrize('a, b, expect', data_1, ids=ids)
def test_parametrize_1(a, b, expect):
print('n测试函数1测试数据为n{}-{}'.format(a, b))
assert add(a, b) == expect
命令行输入:pytest -v
以上
That‘s all
- ASP.NET Core 在 Azure 开启 HTTPS
- 算法基础:最大递减数问题(Golang实现)
- 亲身经历的痛--database/sql: Stmt的使用以及坑
- Ubuntu上通过nginx部署Django笔记
- Go学习笔记:golang交叉编译
- Python魔术方法-Magic Method
- python类中super()和__init__()的区别
- Python正则表达式:最短匹配
- 转--Go时间格式化和类型互换操作
- Python标准库(1) — itertools模块
- Linux笔记:使用Vim编辑器
- 一步一步学lucene——(第二步:示例篇)
- 类属性的延迟计算
- 一步一步学lucene——(第三步:索引篇)
- JavaScript 教程
- JavaScript 编辑工具
- JavaScript 与HTML
- JavaScript 与Java
- JavaScript 数据结构
- JavaScript 基本数据类型
- JavaScript 特殊数据类型
- JavaScript 运算符
- JavaScript typeof 运算符
- JavaScript 表达式
- JavaScript 类型转换
- JavaScript 基本语法
- JavaScript 注释
- Javascript 基本处理流程
- Javascript 选择结构
- Javascript if 语句
- Javascript if 语句的嵌套
- Javascript switch 语句
- Javascript 循环结构
- Javascript 循环结构实例
- Javascript 跳转语句
- Javascript 控制语句总结
- Javascript 函数介绍
- Javascript 函数的定义
- Javascript 函数调用
- Javascript 几种特殊的函数
- JavaScript 内置函数简介
- Javascript eval() 函数
- Javascript isFinite() 函数
- Javascript isNaN() 函数
- parseInt() 与 parseFloat()
- escape() 与 unescape()
- Javascript 字符串介绍
- Javascript length属性
- javascript 字符串函数
- Javascript 日期对象简介
- Javascript 日期对象用途
- Date 对象属性和方法
- Javascript 数组是什么
- Javascript 创建数组
- Javascript 数组赋值与取值
- Javascript 数组属性和方法
- LeetCode - 198 简单动态规划 打家劫舍
- Jaskson精讲第7篇-JsonTypeInfo注解在类继承关系下的使用
- 《剑指Offer 1.二维数组中的查找》2019-03-25
- Elasticsearch:Dynamic mapping
- 设计模式《单例设计模式》
- 《0-1 背包问题》
- 使用分治思想 求数组中的最大和最小值
- python 入门笔记[语法基础(下)]
- Java 成员变量和属性的区别
- xmuC语言程序实践week 1 大作业
- 《01-背包问题-点菜》
- 模拟赛 2018 Benelux Algorithm Programming Contest (BAPC 18)(部分题)
- vue动态生成表单组件vue-form-maker
- 对顶堆求区间k小(大)数
- 祖传快读快写模板