python 自动化测试 pytest 的使用
pytest 是一款以python为开发语言的第三方测试,主要特点如下:
-
比自带的 unittest 更简洁高效,兼容 unittest框架
-
支持参数化
-
可以更精确的控制要测试的测试用例
-
丰富的插件,已有300多个各种各样的插件,也可自定义扩展,如pytest-selenium、pytest-html、pytest-rerunfailures、pytes-xdish
-
可很好的和CI工具结合
安装
pip install pytest
测试用例编写规则
-
测试文件以test_开头 或者 _test结尾
-
测试类以Test开头,并且不能带有 init 方法
-
测试文件以 test_开头
-
断言使用基本的 assert 即可
pytest会递归查找当前目录及子目录下所有 以test_开始 或者 _test结尾的python脚本,执行其中符合规则的函数和方法,不需要显示调用
运行命令:(cmd进入用例所在目录)
- pytest folder_name ======》直接运行文件夹内符合规则的所有用例
- pytest test_file.py ======》执行某个py文件中的用例
- pytest test_file.py::test_func ======》执行模块内的某个函数(节点运行)
- pytest test_file.py::TestClass::test_method ======》执行模块内测试类的某个方法(节点运行)
- pytest test_file.py::TestClass ======》执行模块内某个测试类(节点运行)
- pytest test_file.py::TestClass test_file2.py::test_mothod ======》多节点运行,中间用空格隔开
- pytest -k pass ======》匹配用例名称的表达式,含有“pass”的被执行,其他的deselected
- pytest -k "pass or fail" ======》组合匹配,含有“pass” 和 “fail”的被执行
- pytest -k "not pass" ======》排除运行,不含“pass”的被执行
- pytest -m finished ======》标记表达式,运行用@pytest.mark.finished 标记的用例
- pytest -m "finished and not merged" ======》多个标记逻辑匹配,运行含有finished 不含 merged标记的用例
- pytest -v ======》运行时显示详细信息
- pytest -s ======》显示打印消息
- pytest -x ======》遇到错误就停止运行
- pytest -x --maxfail=2 ======》遇到两个错误就停止运行
- pytest --setup-show ======》跟踪固件运行
- pytest -v --reruns 5 --reruns-delay 1 ======》运行失败的用例间隔1s重新运行5次 pip install pytest-rerunfailures
- pytest ======》多条断言,报错后,后面的依然执行, pip install pytest-assume,断言 pytest.assume(2==4)
- pytest -n 3 ======》3个cpu并行执行测试用例,需保证测试用例可随机执行, pip install pytest-xdist分布式执行插件,多个cpu或主机执行
- pytest -v -n auto ======》自动侦测系统里cpu的数目
- pytest --count=2 ======》重复运行测试 pip install pytest-repeat
- pytest --html=./report/report.html ======》生成报告,此报告中css是独立的,分享时会丢失样式,pip install pytest-html
- pytest --html=report.html --self-containd-html ======》合并css到html报告中,除了passed所有行都被展开
- pytest --durations=10 ======》获取最慢的10个用例的执行耗时
用例执行顺序控制
pytest 用例执行顺序默认是按字母顺序去执行,要控制执行顺序,需要安装插件 pytest-ordering:pip install pytest-ordering
在测试方法上加上装饰器:
@pytest.mark.last 最后一个执行
@pytest.mark.run(order=n) n=1则是第一个执行
Mark
标签的使用方法:
注册标签名 / 内置标签---> 在测试用例 / 测试类 / 模块文件 前面加上 @pytest.mark.标签名
注册方法:
1. 在conftest.py 文件中添加代码
# 单个标签文件内容
def pytest_configure(config):config.addinivalue_line("markers", "demo:demo标签名称")# 多个标签文件内容
def pytest_configure(config):marker_list = ["p0:p0级别用例", "p1:p1级别用例", "p2:p2级别用例"] # 标签名称for markers in marker_list:config.addinivalue_line("markers", markers)
2. 项目中添加pytest.ini配置文件
[pytest] markers = p0:p0级别用例p1:p1级别用例p2:p2级别用例
使用方法:
import pytest@pytest.mark.p0
def test_mark01():print("函数级别的mark_p0")@pytest.mark.p1
def test_mark02():print("函数级别的mark_p1")@pytest.mark.P2
class TestDemo:def test_mark03(self):print("mark_p2")def test_mark04(self):print("mark_p2")
运行方式:
1. 命令行运行
pytest -m "p0 and p1"
2. 文件运行
pytest.main(["-m", "P0", "--html=report.html"])
内置标签:
参数化:@pytest.mark.parametrize(argnames, argvalues)
无条件跳过用例:@pytest.mark.skip(reason="xxx")
有条件跳过用例:@pytest.mark.skipif(version < 0.3, reason = "not supported until 0.3")
预测执行失败进行提示标记:@pytest.mark.xfail(version < 0.3, reason = "not supported until 0.3"),运行结果为X(通过xpassed,失败xfailed)
# 参数化
import hashlib@pytest.mark.parametrize("x", list(range(10)))
def test_somethins(x):time.sleep(1)@pytest.mark.parametrize("passwd",["123456", "abcdefgfs", "as52345fasdf4"])
def test_passwd_length(passwd):assert len(passwd) >= 8@pytest.mark.parametrize('user, passwd',[('jack', 'abcdefgh'),('tom', 'a123456a')])
def test_passwd_md5(user, passwd):db = {'jack': 'e8dc4081b13434b45189a720b77b6818','tom': '1702a132e769a623c1adb78353fc9503'}assert hashlib.md5(passwd.encode()).hexdigest() == db[user]# 如果觉得每组测试的默认参数显示不清晰,可以使用 pytest.param 的 id 参数进行自定义
@pytest.mark.parametrize("user, passwd",[pytest.param("jack", "abcdefgh", id = "User<Jack>"),pytest.param("tom", "a123456a", id = "User<Tom>")])
def test_passwd_md5_id(user, passwd):db = {'jack': 'e8dc4081b13434b45189a720b77b6818','tom': '1702a132e769a623c1adb78353fc9503'}assert hashlib.md5(passwd.encode()).hexdigest() == db[user]
Fixture
固件:是一些函数,pytest会在执行函数之前或者之后加载运行它们,相当于预处理和后处理。
fixture的目的是提供一个固定基线,在该基线上测试可以可靠地、重复的执行。
- 名称:默认为定义时的函数名,可以通过 @pytest.fixture(name="demo") 给fixture重命名
- 定义:在固件函数定义前加上@pytest.fixture();fixture是有返回值的,没return则返回None
- 使用:作为参数、使用usefixtures、自动执行(定义时指定autouse参数)
- def test_demo(fixture_func_name)
- @pytest.mark.usefixtures("fixture_func_name1", "fixture_func_name2") 标记函数或者类
- 预处理和后处理:用yield关键词,yield之前的代码是预处理,之后的是后处理
- 作用域:通过scope参数控制作用域
- function:函数级,每个测试函数都会执行一次(默认)
- class:类级别,每个测试类执行一次,所有方法都共享这个fixture
- module:模块级别,每个模块.py执行一次,模块中所有测试函数、类方法 或者 其他fixture 都共享这个fixture
- session:会话级别,每次会话只执行一次,一次会话中所有的函数、方法都共享这个fixture
- 集中管理:使用文件conftest.py 集中管理,在不同层级定义,作用于在其所在的目录和子目录,pytest会自动调用
scope、yield、auto的使用
# scope、yield、auto使用
@pytest.fixture(scope = "function", autouse=True)
def function_scope():pass@pytest.fixture(scope = "module", autouse=True)
def module_scope():pass@pytest.fixture(scope = "session")
def session_scope():pass@pytest.fixture(scope = "class", autouse=True)
def class_scope():passimport timeDATE_FORMAT = '%Y-%m-%d %H:%M:%S'@pytest.fixture(scope='session', autouse=True)
def timer_session_scope():start = time.time()print('\nsession start: {}'.format(time.strftime(DATE_FORMAT, time.localtime(start))))yieldfinished = time.time()print('\nsession finished: {}'.format(time.strftime(DATE_FORMAT, time.localtime(finished))))print('session Total time cost: {:.3f}s'.format(finished - start))def test_1():time.sleep(1)def test_2():time.sleep(2)'''
执行命令:pytest --setup-show -s
固件执行结果:
test_pytest_study.py
session start: 2020-04-16 17:29:02SETUP S timer_session_scopeSETUP M module_scopeSETUP C class_scopeSETUP F function_scopetest_pytest_study.py::test_3 (fixtures used: class_scope, function_scope, module_scope, timer_session_scope).TEARDOWN F function_scopeTEARDOWN C class_scopeSETUP C class_scopeSETUP F function_scopetest_pytest_study.py::test_4 (fixtures used: class_scope, function_scope, module_scope, timer_session_scope).TEARDOWN F function_scopeTEARDOWN C class_scopeTEARDOWN M module_scope
session finished: 2020-04-16 17:29:05
session Total time cost: 3.087sTEARDOWN S timer_session_scope'''
使用文件conftest.py 集中管理
# conftest.py
# conding=utf-8
import pytest@pytest.fixture()
def postcode():print("执行postcode fixture")return "010"
# test_demo.py # coding=utf-8 import pytestclass TestDemo():def test_postcode(self, postcode):assert postcode == "010"if __name__=="__main__":pytest.main(["--setup-show", "-s", "test_demo.py"])
python test_demo.py 执行过程: test_demo.py 执行postcode fixtureSETUP F postcodetest_demo.py::TestDemo::test_postcode (fixtures used: postcode).TEARDOWN F postcode
# 如果整个文件都用一个fixture,可以用pytestmark标记
pytestmark = pytest.mark.usefixtures("login")
fixture参数化
固件参数化需要使用pytest内置的固件request,并通过 request.param 获取参数。
# test_demo.py
@pytest.fixture(params=[("user1", "passwd1"),("user2", "passwd2")])
def param(request):return request.param@pytest.fixture(autouse=True)
def login(param):print("\n登录成功 %s %s" %param)yieldprint("\n退出成功 %s %s" %param)def test_api():assert 1 == 1'''
pytest -s -v test_demo.py
运行结果:
test_demo.py::test_api[param0]
登录成功 user1 passwd1
PASSED
退出成功 user1 passwd1test_demo.py::test_api[param1]
登录成功 user2 passwd2
PASSED
退出成功 user2 passwd2
'''
assert
assert "h" in "hello"
assert 3==4
assert 3!=4
assert f()==4
assert 5>6
assert not xx
assert {"0", "1", "2"} == {"0", "1", "2"}
最后:下方这份完整的软件测试视频学习教程已经整理上传完成,朋友们如果需要可以自行免费领取 【保证100%免费】


相关文章:
python 自动化测试 pytest 的使用
pytest 是一款以python为开发语言的第三方测试,主要特点如下: 比自带的 unittest 更简洁高效,兼容 unittest框架 支持参数化 可以更精确的控制要测试的测试用例 丰富的插件,已有300多个各种各样的插件,也可自定义扩…...
闭包(回顾)
概念作用保护作用保存作用优缺点命名空间 概念 闭包(closure)指有权访问另一个函数作用域中变量的函数 — Javacript高级程序设计 p309 简单理解,一个作用域可以访问另一个函数内部的私有变量 // 其中 test就是一个闭包 function fn(){var num 10function test …...
利用好这两个方法,服务型企业缺成本票不再难解决!
现代服务业属于人才密集型和技术型类别,其中囊括了不少技术,知识,智力服务等产业:信息技术,文化创意,营销策划,广告设计,以及咨询,商务和法律服务。 在金税三期完善之前…...
前端面试编程题(异步调度,Promise实现、占用空间大小、渲染虚拟节点、实现for of)
目录 异步调度问题 题目一 答案 题目二 答案 递归输出 题目一 答案 Promise相关 题目一 答案 占用空间大小 题目一 答案 渲染虚拟节点 题目一 答案 实现for of 题目一 答案 异步调度问题 题目一 1.实现一个带并发限制的异步调度Scheduler,保证同…...
复旦团队发布国内首个模型MOSS 类ChatGPT
复旦团队发布国内首个模型MOSS 类ChatGPT 首先看到这个标题,还有这个名字,我是正经(zhen jing)的 (bu shi 流浪地球?550W?不了解的可以把550W倒过来写,就懂了 看到新闻里的一些图…...
5.35 综合案例2.0 -称重数据上传云端
综合案例2.0 - 称重数据上传云端案例说明连线功能实现1.阿里云平台连接代码应用开发3.1新建‘普通项目’3.2关联产品和设备3.3新建‘移动应用’3.4添加组件3.5配置组件信息3.6保存预览案例说明 使用hx711串口模块称重,结合IOT studio制作手机APP远程控制并采集物体重量。 hx7…...
如何让人机对话更自然?
来源:投稿 作者:顾相欢 编辑:学姐 AAAI-2022|定制对话的人设和知识背景 原文标题: Call for Customized Conversation: Customized Conversation Grounding Persona and Knowledge 原文链接: https://arxiv.org/ab…...
Python每日一练(20230224)
目录 1. 列表奇偶拆分 ★ 2. 二叉树的后序遍历 ★★ 3. 接雨水 ★★★ 附录 二叉树 特点 性质 特殊二叉树 满二叉树 完全二叉树 完全二叉树性质 二叉树的遍历 1. 列表奇偶拆分 【问题描述】 输入一个列表,包含若干个整数(允许为空ÿ…...
【Linux】-- Shell的运行原理、Linux当中的权限
目录 Shell的运行原理 Linux权限的概念 su命令 权限 文件访问权限的相关设置方法 chmod指令 chown指令 chgrp指令 sudo命令 文件的常见问题 umask 粘滞位 关于权限的总结 Shell的运行原理 Shell运行原理 —— 外壳程序。 Linux严格意义上说的是一个操作系统&…...
MOS管选型参数:VGS(th)
MOS管选型参数:VGS(th) VGS(th):开启电压(阀值电压)。当外加栅极控制电压 VGS 超过 VGS(th) 时,漏区和源区的表面反型层形成了连接的沟道。应用中,常将漏极短…...
二.线性表之顺序表
文章目录前言一.顺序表的概念及结构二.顺序表的接口实现1.顺序表的动态存储2.顺序表的初始化3.顺序表尾插#封装:扩容函数4.顺序表尾删5.顺序表头插6.顺序表头删7.顺序表查找8.顺序表在pos位置插入x9.顺序表删除pos位置的值10.顺序表销毁11.顺序表打印三.源1.Seqlist…...
ElasticSearch - SpringBoot整合ElasticSearch实现文档的增删改
文章目录1. ElasticSearch和kibana的安装和配置2. SpringBoot 项目环境搭建3. 创建索引4. 索引文档5. 更新文档6. 删除文档https://www.elastic.co/guide/en/elasticsearch/reference/current/search-your-data.htmlhttps://www.elastic.co/guide/cn/elasticsearch/guide/curre…...
JavaScript 库
文章目录JavaScript 库JavaScript 框架(库)jQueryPrototypeMooTools其他框架CDN -内容分发网络引用 jQuery使用框架JavaScript 库 JavaScript 库 - jQuery、Prototype、MooTools。 JavaScript 框架(库) JavaScript 高级程序设计…...
云解析DNS为什么要配置默认线路?
传统解析技术不会判断访客IP,而是会随机选择一个IP返回给访问者,这样就有可能造成移动用户访问电信服务器IP,北京用户访问深圳服务器IP这种跨域跨网访问的情况,产生非常大的延迟,带来很不好的访问体验。 而云解析DNS会…...
Linux命令之awk
awk是一个有强大的文本格式化能力的linux命令,早期是在Unix上实现的,linux后来也可以使用了,我们在Linux上使用的awk是gawk(GNU awk的意思) 语法 awk [option] 模式{动作} file option表示awk的可选参数,可…...
实战-缓存数据一致+binlog初始+cannel监听+数据迁移,数据一致性架构设计
前言 一. 解决缓存不命中(高并发操作击穿打挂DB的风险) 当并发量打的时候,当我们的缓存过期时,就算到数据库的比例偏小的时候,我们的请求时比较大的。那也会存在数据库崩掉的情况。解决方案想法如下(总体…...
nginx配置中proxy_pass反向代理502的bug
记录一个坑人的bug, 我今天在一台新的liunx上运行nginx来进行反向代理时候,发现怎么测都是502 我把配置全部删了从头开始配置,发现80端口正常,80端口index.html正常,反向代理转向http://127.0.0.1/也正常,…...
JavaScript 两种方案打开文件对话框
JavaScript 两种方案打开文件对话框 文章目录JavaScript 两种方案打开文件对话框一、文件对话框二、传统方案表单元素🌈三、文件系统访问API💦四、更进一步使用六、代码仓库🌐七、参考资料💘七、推荐博文🍗一、文件对话…...
Pycharm远程服务器常见问题
2023年02月23日 问题描述:Pycharm远程服务器跑代码时,不小心把Pycharm关掉了,但服务器代码还在运行? 解决办法:kill进程 先用watch -n 0.5 nvidia_smi查看进程,然后kill -9 <进程> 1、nvidia-smi…...
内容团队如何快速出稿
对于内容团队而言,每个内容选题就相当于一个小项目,它们并非简单的线性工作流,相反其复杂程度不亚于一个小型工厂。一个内容选题会涉及内容形式,选题类型等多个变量,这些变量因素组合起来就是十几种不同类型的工作流。…...
【AI Agent游戏行业应用实战指南】:20年资深架构师亲授7大落地场景与避坑清单
更多请点击: https://intelliparadigm.com 第一章:AI Agent游戏行业应用全景图谱 AI Agent 正在重塑游戏开发、运营与玩家体验的全生命周期。从智能NPC的行为建模,到自动化测试与关卡生成,再到实时个性化内容推荐与跨平台玩家陪伴…...
Julia语言在科学机器学习领域的优势、挑战与实践指南
1. 科学机器学习:当物理定律遇见数据驱动如果你和我一样,长期在科学计算和机器学习的交叉领域“搬砖”,那你一定对“两难困境”深有体会。我们既需要Python那样灵活、易上手的语法来快速验证物理模型和算法原型,又渴望C级别的极致…...
不只是安装:用Carla+Win11快速搭建你的第一个自动驾驶测试场景(手把手教程)
从零到一:用Carla在Win11上构建自动驾驶测试场景的实战指南当你第一次启动Carla仿真环境,看到那个空荡荡的数字化城市时,是否感到既兴奋又迷茫?作为一款开源的自动驾驶仿真平台,Carla的真正价值不在于安装过程…...
Zookeeper集群启动失败?从myid配置到防火墙,保姆级排错指南来了
Zookeeper集群启动失败?从myid配置到防火墙,保姆级排错指南来了当你满怀期待地执行bin/zkServer.sh start命令,却只看到一堆晦涩的错误日志时,那种挫败感我太熟悉了。Zookeeper作为分布式系统的"神经中枢",其…...
《论三生原理》对《周易》《道德经》的一次根本性重写?
AI辅助创作:一、关于《周易》来历根源的推断属于文化创新实验,是对《周易》来历、性质、底层逻辑的一次根本性重写?《论三生原理》关于《周易》来历根源的推断,确实属于一次大胆的文化创新实验,并且是对《周易》的来历…...
Claude API文档不是说明书,而是契约:用Swagger UI+Postman Collection+TypeScript SDK三件套构建零歧义协作协议
更多请点击: https://kaifayun.com 第一章:Claude API文档不是说明书,而是契约 Claude API 文档的本质并非操作指南或功能速查手册,而是一份具有技术约束力的**双向契约**——它明确定义了客户端与 Anthropic 服务之间在请求结构…...
分布式系统测试:验证分布式系统的正确性和性能
分布式系统测试:验证分布式系统的正确性和性能 一、分布式系统测试概述 1.1 分布式系统测试的定义 分布式系统测试是指对分布式系统进行验证和评估的过程,包括功能测试、性能测试、可靠性测试和安全性测试等方面。它确保分布式系统在各种场景下都能正确、…...
3个PDF编辑痛点,用这个免费工具轻松搞定!PDF补丁丁全面解析
3个PDF编辑痛点,用这个免费工具轻松搞定!PDF补丁丁全面解析 【免费下载链接】PDFPatcher PDF补丁丁——PDF工具箱,可以编辑书签、剪裁旋转页面、解除限制、提取或合并文档,探查文档结构,提取图片、转成图片等等 项目…...
7z2john报错Compress::Raw::Lzma.pm缺失的原理与修复
1. 这不是你的错:当7z2john突然报错“Cant locate Compress::Raw::Lzma.pm”时,你其实只缺一个Perl模块刚打开终端准备提取7z压缩包里的密码哈希,7z2john archive.7z > hash.txt回车一敲,屏幕却猛地跳出一行红字:Ca…...
C++超详细讲解析构函数
析构函数是特殊的成员函数特征如下:析构函数名是~类名;无参数无返回值;一个类有且只有一个析构函数;对象声明周期结束,编译器自动调用析构函数;12345678910111213141516171819202122232425262728293031clas…...
