pytest中文使用文档----10skip和xfail标记
- 1. 跳过测试用例的执行
- 1.1.
@pytest.mark.skip装饰器 - 1.2.
pytest.skip方法 - 1.3.
@pytest.mark.skipif装饰器 - 1.4.
pytest.importorskip方法 - 1.5. 跳过测试类
- 1.6. 跳过测试模块
- 1.7. 跳过指定文件或目录
- 1.8. 总结
- 1.1.
- 2. 标记用例为预期失败的
- 2.1. 去使能
xfail标记
- 2.1. 去使能
- 3. 结合
pytest.param方法
实际工作中,测试用例的执行可能会依赖于一些外部条件,例如:只能运行在某个特定的操作系统(Windows),或者我们本身期望它们测试失败,例如:被某个已知的Bug所阻塞;如果我们能为这些用例提前打上标记,那么pytest就相应地预处理它们,并提供一个更加准确的测试报告;
在这种场景下,常用的标记有:
skip:只有当某些条件得到满足时,才执行测试用例,否则跳过整个测试用例的执行;例如,在非Windows平台上跳过只支持Windows系统的用例;xfail:因为一个确切的原因,我们知道这个用例会失败;例如,对某个未实现的功能的测试,或者阻塞于某个已知Bug的测试;
pytest默认不显示skip和xfail用例的详细信息,我们可以通过-r选项来自定义这种行为;
通常,我们使用一个字母作为一种类型的代表,具体的规则如下:
(f)ailed, (E)rror, (s)kipped, (x)failed, (X)passed, (p)assed, (P)assed with output, (a)ll except passed(p/P), or (A)ll
例如,显示结果为XFAIL、XPASS和SKIPPED的用例:
pytest -rxXs
更多细节可以参考:2、使用和调用 – 总结报告
1. 跳过测试用例的执行
1.1. @pytest.mark.skip装饰器
跳过执行某个用例最简单的方式就是使用@pytest.mark.skip装饰器,并且可以设置一个可选参数reason,表明跳过的原因;
@pytest.mark.skip(reason="no way of currently testing this")
def test_the_unknown():...
1.2. pytest.skip方法
如果我们想在测试执行期间(也可以在SetUp/TearDown期间)强制跳过后续的步骤,可以考虑pytest.skip()方法,它同样可以设置一个参数msg,表明跳过的原因;
def test_function():if not valid_config():pytest.skip("unsupported configuration")
另外,我们还可以为其设置一个布尔型的参数allow_module_level(默认是False),表明是否允许在模块中调用这个方法,如果置为True,则跳过模块中剩余的部分;
例如,在Windows平台下,不测试这个模块:
import sys
import pytestif not sys.platform.startswith("win"):pytest.skip("skipping windows-only tests", allow_module_level=True)
注意:
当在用例中设置
allow_module_level参数时,并不会生效;def test_one():pytest.skip("跳出", allow_module_level=True)def test_two():assert 1也就是说,在上述示例中,并不会跳过
test_two用例;
1.3. @pytest.mark.skipif装饰器
如果我们想有条件的跳过某些测试用例的执行,可以使用@pytest.mark.skipif装饰器;
例如,当python的版本小于3.6时,跳过用例:
import sys@pytest.mark.skipif(sys.version_info < (3, 6), reason="requires python3.6 or higher")
def test_function():...
我们也可以在两个模块之间共享pytest.mark.skipif标记;
例如,我们在test_module.py中定义了minversion,表明当python的最低支持版本:
# src/chapter-10/test_module.pyimport sysimport pytestminversion = pytest.mark.skipif(sys.version_info < (3, 8),reason='请使用 python 3.8 或者更高的版本。')@minversion
def test_one():assert True
并且,在test_other_module.py中引入了minversion:
# src/chapter-10/test_other_module.pyfrom test_module import minversion@minversion
def test_two():assert True
现在,我们来执行这两个用例(当前虚拟环境的python版本为3.7.3):
λ pytest -rs -k 'module' src/chapter-10/
================================ test session starts =================================
platform win32 -- Python 3.7.3, pytest-5.1.3, py-1.8.0, pluggy-0.13.0
rootdir: D:\Personal Files\Projects\pytest-chinese-doc
collected 2 itemssrc\chapter-10\test_module.py s [ 50%]
src\chapter-10\test_other_module.py s [100%]============================== short test summary info ===============================
SKIPPED [1] src\chapter-10\test_module.py:29: 请使用 python 3.8 或者更高的版本。
SKIPPED [1] src\chapter-10\test_other_module.py:26: 请使用 python 3.8 或者更高的版本。
================================= 2 skipped in 0.03s =================================
可以看到,minversion在两个测试模块中都生效了;
因此,在大型的测试项目中,可以在一个文件中定义所有的执行条件,需要时再引入到模块中;
另外,需要注意的是,当一个用例指定了多个skipif条件时,只需满足其中一个,就可以跳过这个用例的执行;
注意:不存在
pytest.skipif()的方法;
1.4. pytest.importorskip方法
当引入某个模块失败时,我们同样可以跳过后续部分的执行;
docutils = pytest.importorskip("docutils")
我们也可以为其指定一个最低满足要求的版本,判断的依据是检查引入模块的__version__ 属性:
docutils = pytest.importorskip("docutils", minversion="0.3")
我们还可以再为其指定一个reason参数,表明跳过的原因;
我们注意到
pytest.importorskip和pytest.skip(allow_module_level=True)都可以在模块的引入阶段跳过剩余部分;实际上,在源码中它们抛出的都是同样的异常:# pytest.skip(allow_module_level=True)raise Skipped(msg=msg, allow_module_level=allow_module_level)# pytest.importorskip()raise Skipped(reason, allow_module_level=True) from None只是
importorskip额外增加了minversion参数:# _pytest/outcomes.pyif minversion is None:return modverattr = getattr(mod, "__version__", None)if minversion is not None:if verattr is None or Version(verattr) < Version(minversion):raise Skipped("module %r has __version__ %r, required is: %r"% (modname, verattr, minversion),allow_module_level=True,)从中我们也证实了,它实际检查的是模块的
__version__属性;所以,对于一般场景下,使用下面的方法可以实现同样的效果:
try:import docutils except ImportError:pytest.skip("could not import 'docutils': No module named 'docutils'",allow_module_level=True)
1.5. 跳过测试类
在类上应用@pytest.mark.skip或@pytest.mark.skipif:
# src/chapter-10/test_skip_class.pyimport pytest@pytest.mark.skip("作用于类中的每一个用例,所以 pytest 共收集到两个 SKIPPED 的用例。")
class TestMyClass():def test_one(self):assert Truedef test_two(self):assert True
1.6. 跳过测试模块
在模块中定义pytestmark变量(推荐):
# src/chapter-10/test_skip_module.pyimport pytestpytestmark = pytest.mark.skip('作用于模块中的每一个用例,所以 pytest 共收集到两个 SKIPPED 的用例。')def test_one():assert Truedef test_two():assert True
或者,在模块中调用pytest.skip方法,并设置allow_module_level=True:
# src/chapter-10/test_skip_module.pyimport pytestpytest.skip('在用例收集阶段就已经跳出了,所以不会收集到任何用例。', allow_module_level=True)def test_one():assert Truedef test_two():assert True
1.7. 跳过指定文件或目录
通过在conftest.py中配置collect_ignore_glob项,可以在用例的收集阶段跳过指定的文件和目录;
例如,跳过当前测试目录中文件名匹配test_*.py规则的文件和config的子文件夹sub中的文件:
collect_ignore_glob = ['test*.py', 'config/sub']
更多细节可以参考:https://docs.pytest.org/en/5.1.3/example/pythoncollection.html#customizing-test-collection
1.8. 总结
pytest.mark.skip | pytest.mark.skipif | pytest.skip | pytest.importorskip | conftest.py | |
|---|---|---|---|---|---|
| 用例 | @pytest.mark.skip() | @pytest.mark.skipif() | pytest.skip(msg='') | / | / |
| 类 | @pytest.mark.skip() | @pytest.mark.skipif() | / | / | / |
| 模块 | pytestmark = pytest.mark.skip() | pytestmark = pytest.mark.skipif() | pytest.skip(allow_module_level=True) | pytestmark = pytest.importorskip() | / |
| 文件或目录 | / | / | / | / | collect_ignore_glob |
2. 标记用例为预期失败的
我们可以使用@pytest.mark.xfail标记用例,表示期望这个用例执行失败;
用例会正常执行,只是失败时不再显示堆栈信息,最终的结果有两个:用例执行失败时(XFAIL:符合预期的失败)、用例执行成功时(XPASS:不符合预期的成功)
另外,我们也可以通过pytest.xfail方法在用例执行过程中直接标记用例结果为XFAIL,并跳过剩余的部分:
def test_function():if not valid_config():pytest.xfail("failing configuration (but should work)")
同样可以为pytest.xfail指定一个reason参数,表明原因;
下面我们来重点看一下@pytest.mark.xfail的用法:
-
condition位置参数,默认值为None和
@pytest.mark.skipif一样,它也可以接收一个python表达式,表明只有满足条件时才标记用例;例如,只在
pytest 3.6版本以上标记用例:@pytest.mark.xfail(sys.version_info >= (3, 6), reason="python3.6 api changes") def test_function():... -
reason关键字参数,默认值为None可以指定一个字符串,表明标记用例的原因;
-
strict关键字参数,默认值为False当
strict=False时,如果用例执行失败,结果标记为XFAIL,表示符合预期的失败;如果用例执行成功,结果标记为XPASS,表示不符合预期的成功;当
strict=True时,如果用例执行成功,结果将标记为FAILED,而不再是XPASS了;我们也可以在
pytest.ini文件中配置:[pytest] xfail_strict=true -
raises关键字参数,默认值为None可以指定为一个异常类或者多个异常类的元组,表明我们期望用例上报指定的异常;
如果用例的失败不是因为所期望的异常导致的,
pytest将会把测试结果标记为FAILED; -
run关键字参数,默认值为True:当
run=False时,pytest不会再执行测试用例,直接将结果标记为XFAIL;
我们以下表来总结不同参数组合对测试结果的影响(其中xfail = pytest.mark.xfail):
@xfail() | @xfail(strict=True) | @xfail(raises=IndexError) | @xfail(strict=True, raises=IndexError) | @xfail(..., run=False) | |
|---|---|---|---|---|---|
| 用例测试成功 | XPASS | FAILED | XPASS | FAILED | XFAIL |
用例测试失败,上报AssertionError | XFAIL | XFAIL | FAILED | FAILED | XFAIL |
用例上报IndexError | XFAIL | XFAIL | XFAIL | XFAIL | XFAIL |
2.1. 去使能xfail标记
我们可以通过命令行选项pytest --runxfail来去使能xfail标记,使这些用例变成正常执行的用例,仿佛没有被标记过一样:
同样,pytest.xfail()方法也将会失效;
3. 结合pytest.param方法
pytest.param方法可用于为@pytest.mark.parametrize或者参数化的fixture指定一个具体的实参,它有一个关键字参数marks,可以接收一个或一组标记,用于标记这轮测试的用例;
我们以下面的例子来说明:
# src/chapter-10/test_params.pyimport pytest
import sys@pytest.mark.parametrize(('n', 'expected'),[(2, 1),pytest.param(2, 1, marks=pytest.mark.xfail(), id='XPASS'),pytest.param(0, 1, marks=pytest.mark.xfail(raises=ZeroDivisionError), id='XFAIL'),pytest.param(1, 2, marks=pytest.mark.skip(reason='无效的参数,跳过执行')),pytest.param(1, 2, marks=pytest.mark.skipif(sys.version_info <= (3, 8), reason='请使用3.8及以上版本的python。'))])
def test_params(n, expected):assert 2 / n == expected
执行:
λ pytest -rA src/chapter-10/test_params.py
================================ test session starts =================================
platform win32 -- Python 3.7.3, pytest-5.1.3, py-1.8.0, pluggy-0.13.0
rootdir: D:\Personal Files\Projects\pytest-chinese-doc
collected 5 itemssrc\chapter-10\test_params.py .Xxss [100%]======================================= PASSES =======================================
============================== short test summary info ===============================
PASSED src/chapter-10/test_params.py::test_params[2-1]
SKIPPED [1] src\chapter-10\test_params.py:26: 无效的参数,跳过执行
SKIPPED [1] src\chapter-10\test_params.py:26: 请使用3.8及以上版本的python。
XFAIL src/chapter-10/test_params.py::test_params[XFAIL]
XPASS src/chapter-10/test_params.py::test_params[XPASS]
================= 1 passed, 2 skipped, 1 xfailed, 1 xpassed in 0.08s =================
关于参数化的fixture的细节可以参考:4、fixtures:明确的、模块化的和可扩展的 – 在参数化的fixture中标记用例
相关文章:
pytest中文使用文档----10skip和xfail标记
1. 跳过测试用例的执行 1.1. pytest.mark.skip装饰器1.2. pytest.skip方法1.3. pytest.mark.skipif装饰器1.4. pytest.importorskip方法1.5. 跳过测试类1.6. 跳过测试模块1.7. 跳过指定文件或目录1.8. 总结 2. 标记用例为预期失败的 2.1. 去使能xfail标记 3. 结合pytest.param方…...
【Spring MVC】快速学习使用Spring MVC的注解及三层架构
💓 博客主页:从零开始的-CodeNinja之路 ⏩ 收录文章:【Spring MVC】快速学习使用Spring MVC的注解及三层架构 🎉欢迎大家点赞👍评论📝收藏⭐文章 目录 Spring Web MVC一: 什么是Spring Web MVC࿱…...
Python(乱学)
字典在转化为其他类型时,会出现是否舍弃value的操作,只有在转化为字符串的时候才不会舍弃value 注释的快捷键是ctrl/ 字符串无法与整数,浮点数,等用加号完成拼接 5不入??? 还有一种格式化的方法…...
OpenHarmony实战:轻量级系统之子系统移植概述
OpenHarmony系统功能按照“系统 > 子系统 > 部件”逐级展开,支持根据实际需求裁剪某些非必要的部件,本文以部分子系统、部件为例进行介绍。若想使用OpenHarmony系统的能力,需要对相应子系统进行适配。 OpenHarmony芯片适配常见子系统列…...
Neo4j基础知识
图数据库简介 图数据库是基于数学里图论的思想和算法而实现的高效处理复杂关系网络的新型数据库系统。它善于高效处理大量的、复杂的、互连的、多变的数据。其计算效率远远高于传统的关系型数据库。 在图形数据库当中,每个节点代表一个对象,节点之间的…...
HTTP/1.1 特性(计算机网络)
HTTP/1.1 的优点有哪些? 「简单、灵活和易于扩展、应用广泛和跨平台」 1. 简单 HTTP 基本的报文格式就是 header body,头部信息也是 key-value 简单文本的形式,易于理解。 2. 灵活和易于扩展 HTTP 协议里的各类请求方法、URI/URL、状态码…...
每日一题————P5725 【深基4.习8】求三角形
题目: 题目乍一看非常的简单,属于初学者都会的问题——————————但是实际上呢,有一些小小的坑在里面。 就是三角形的打印。 平常我们在写代码的时候,遇到打印三角形的题,一般简简单单两个for循环搞定 #inclu…...
第三题:时间加法
题目描述 现在时间是 a 点 b 分,请问 t 分钟后,是几点几分? 输入描述 输入的第一行包含一个整数 a。 第二行包含一个整数 b。 第三行包含一个整数 t。 其中,0≤a≤23,0≤b≤59,0≤t, 分钟后还是在当天。 输出描…...
【RAG】内部外挂知识库搭建-本地GPT
大半年的项目告一段落了,现在自己找找感兴趣的东西学习下,看看可不可以搞出个效果不错的local GPT,自研下大模型吧 RAG是什么? 检索增强生成(RAG)是指对大型语言模型输出进行优化,使其能够在生成响应之前引用训练数据来…...
MySQL——锁
全局锁 全局锁是一种数据库锁定机制,它可以锁定整个数据库,阻止其他会话对数据库的读写操作。在MySQL中,全局锁定可以使用FLUSH TABLES WITH READ LOCK命令来实现。执行这个命令后,MySQL将获取一个全局读锁,直到当前会…...
C++(12): std::mutex及其高级变种的使用
1. 简述 在多线程或其他许多场景下,同时对一个变量或一段资源进行读写操作是一个比较常见的过程,保证数据的一致性和防止竞态条件至关重要。 C的标准库中为我们提供了使用的互斥及锁对象,帮助我们实现资源的互斥操作。 2. std::mutex及其衍…...
基于ROS软路由的百元硬件升级方案实现突破千兆宽带
前言 很多用户得利于FTTR光网络不断推广,家用宽带带宽已经实现千兆速率的突破。而现在很多ISP运营商已经在多个城市率先推出2000M光宽带。这种情况下,要想将自家宽带的带宽能够充分发挥利用,就需要对原有的千兆设备进行升级来满足突破千兆的…...
OpenHarmony实战开发-分布式关系型数据库
介绍 本示例使用ohos.data.relationalStore 接口和ohos.distributedDeviceManager 接口展示了在eTS中分布式关系型数据库的使用,在增、删、改、查的基本操作外,还包括分布式数据库的数据同步同能。 效果预览 使用说明: 1.启动应用后点击“”按钮可以添…...
图片标注编辑平台搭建系列教程(6)——fabric渲染原理
原理 fabric的渲染步骤大致如下: 渲染前都设置背景图然后调用ctx.save(),存储画布的绘制状态参数然后调用每个object自身的渲染方法最后调用ctx.restore(),恢复画布的保存状态后处理,例如控制框的渲染等 值得注意的是࿰…...
Qt中QIcon图标设置(标题、菜单栏、工具栏、状态栏图标)
1 exe程序图标概述 在 Windows 操作系统中,程序图标一般会涉及三个地方; (1) 可执行程序(以及对应的快捷方式)的图标 (2) 程序界面标题栏图标 (3)程序在任务…...
C语言程序10题
第101题 (10.0分) 难度:易 第2章 /*------------------------------------------------------- 【程序填空】 --------------------------------------------------------- 功能:计算平均成绩并统计90分以上人数。 --…...
定时器-间歇函数
1.开启定时器 setInterval(function (){console.log(一秒执行一次)},1000) function fn(){console.log(一秒执行一次) } setInterval(fn,1000) //调用有名的函数,只写函数名 1.函数名字不需要加小括号 2.定时器返回是一个id数字 每个定时器的序号是不一样的 2.关…...
Ajax-XMLHttpRequest基本使用
一、Ajax的原理 就是XMLHttpRequest对象。 二、为什么学习XHR? 有更多与服务器数据通信方式,了解Ajax内部。 三、XHR使用步骤 1.创建XHR对象 2.调用open方法,设置url和请求方法 3.监听loadend事件,接受结果 4.调用send方法…...
门控循环单元(GRU)
概述 门控循环单元(Gated Recurrent Unit, GRU)由Junyoung Chung等人于2014年提出,原论文为《Empirical Evaluation of Gated Recurrent Neural Networks on Sequence Modeling》。GRU是循环神经网络(Recurrent Neural Network, …...
789. 数的范围 (二分学习)左端大右,右端小左
题目链接https://www.acwing.com/file_system/file/content/whole/index/content/4317/ 当求左端点时,条件是a【mid】大于等于x,并把右端点缩小。 当求右端点时,条件是a【mid】小于等于x,并把左端点扩大。 1.确定一个区间&…...
XML Group端口详解
在XML数据映射过程中,经常需要对数据进行分组聚合操作。例如,当处理包含多个物料明细的XML文件时,可能需要将相同物料号的明细归为一组,或对相同物料号的数量进行求和计算。传统实现方式通常需要编写脚本代码,增加了开…...
uniapp 对接腾讯云IM群组成员管理(增删改查)
UniApp 实战:腾讯云IM群组成员管理(增删改查) 一、前言 在社交类App开发中,群组成员管理是核心功能之一。本文将基于UniApp框架,结合腾讯云IM SDK,详细讲解如何实现群组成员的增删改查全流程。 权限校验…...
Linux应用开发之网络套接字编程(实例篇)
服务端与客户端单连接 服务端代码 #include <sys/socket.h> #include <sys/types.h> #include <netinet/in.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <arpa/inet.h> #include <pthread.h> …...
HTML前端开发:JavaScript 常用事件详解
作为前端开发的核心,JavaScript 事件是用户与网页交互的基础。以下是常见事件的详细说明和用法示例: 1. onclick - 点击事件 当元素被单击时触发(左键点击) button.onclick function() {alert("按钮被点击了!&…...
UR 协作机器人「三剑客」:精密轻量担当(UR7e)、全能协作主力(UR12e)、重型任务专家(UR15)
UR协作机器人正以其卓越性能在现代制造业自动化中扮演重要角色。UR7e、UR12e和UR15通过创新技术和精准设计满足了不同行业的多样化需求。其中,UR15以其速度、精度及人工智能准备能力成为自动化领域的重要突破。UR7e和UR12e则在负载规格和市场定位上不断优化…...
SpringTask-03.入门案例
一.入门案例 启动类: package com.sky;import lombok.extern.slf4j.Slf4j; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cache.annotation.EnableCach…...
企业如何增强终端安全?
在数字化转型加速的今天,企业的业务运行越来越依赖于终端设备。从员工的笔记本电脑、智能手机,到工厂里的物联网设备、智能传感器,这些终端构成了企业与外部世界连接的 “神经末梢”。然而,随着远程办公的常态化和设备接入的爆炸式…...
2025年渗透测试面试题总结-腾讯[实习]科恩实验室-安全工程师(题目+回答)
安全领域各种资源,学习文档,以及工具分享、前沿信息分享、POC、EXP分享。不定期分享各种好玩的项目及好用的工具,欢迎关注。 目录 腾讯[实习]科恩实验室-安全工程师 一、网络与协议 1. TCP三次握手 2. SYN扫描原理 3. HTTPS证书机制 二…...
人工智能--安全大模型训练计划:基于Fine-tuning + LLM Agent
安全大模型训练计划:基于Fine-tuning LLM Agent 1. 构建高质量安全数据集 目标:为安全大模型创建高质量、去偏、符合伦理的训练数据集,涵盖安全相关任务(如有害内容检测、隐私保护、道德推理等)。 1.1 数据收集 描…...
Oracle11g安装包
Oracle 11g安装包 适用于windows系统,64位 下载路径 oracle 11g 安装包...
