【python自动化】pytest系列(完结)

1123 篇文章 44 订阅
833 篇文章 2 订阅

pytest系列文章一共有四篇,本文为第四篇完结篇。应各位小伙伴留言,希望可以把这几篇pytest文章进行汇总。后续我会进行整理将会以PDF格式免费赠送给各位小伙伴。

  • Pytest高阶用法

    • (1)参数化

    • (2)pytest.ini

    • (3)pytest.mark.相关

    • (4)失败重运行

    • (5)指定用例的运行顺序

    • (6)用例相互依赖

  • 其他

    • 报错一:DeprecationWarning:

Pytest高阶用法

(1)参数化

@pytest.mark.parametrize("参数名",列表数据)
'''
参数名:用来接收每一项数据,并作为测试用例的参数。
列表数据:一组测试数据。
'''
@pytest.mark.parametrize(self,argnames, argvalues, indirect=False, ids=None, scope=None)):
参数说明
argnames必传,参数名, 以逗号分隔的字符串,表示一个或多个参数名称(key),或参数字符串的列表/元组
argvalues必传,参数值,若argnames有一个则单值列表传入,若argnames有多个,以套用元组的列表展示,元组内与参数名一一对应
indirect为true时,那argnames一定是一个fixture函数名称,argvalues值将传入对应的fixture内,相当于@pytest.fixture(params=)的用法,默认False
ids标记子用例执行名称,与argvalues数量一致,未指定自动生成,默认None
scope如果指定,则表示参数的范围。范围用于按参数实例对测试进行分组。它还将覆盖任何fixture函数定义的范围,允许使用测试上下文或配置设置动态范围
#示例
# 这里参数名 a,b,c,对应传入进去的参数a,b,c,需要一一对应。
# 如果只写了一个参数,那么就表示后面每一个以逗号分隔的内容,都为一组数据。
@pytest.mark.parametrize("a,b,c",[(1,2,3),(7,8,15),(2,2,3),(9,6,15)])
def test_add(a,b,c):
    sum = a+b
    assert sum==c
    
    ### 运行结果 ###
============================= test session starts =============================
collecting ... collected 4 items

test_004_参数化.py::test_add[1-2-3] PASSED                               [ 25%]
test_004_参数化.py::test_add[7-8-15] PASSED                              [ 50%]
test_004_参数化.py::test_add[2-2-3] FAILED                               [ 75%]
test_004_参数化.py:12 (test_add[2-2-3])
4 != 3

Expected :3
Actual   :4
<Click to see difference>

a = 2, b = 2, c = 3

    @pytest.mark.parametrize("a,b,c",[(1,2,3),(7,8,15),(2,2,3),(9,6,15)])
    def test_add(a,b,c):
        sum = a+b
>       assert sum==c
E       assert 4 == 3

test_004_参数化.py:16: AssertionError

test_004_参数化.py::test_add[9-6-15] PASSED                              [100%]

========================= 1 failed, 3 passed in 0.06s =========================

「组合参数化 :多组参数,依次组合,笛卡尔积」

@pytest.mark.parametrize("x",[2,4,6])
@pytest.mark.parametrize("y",[1,3,5])
def test_add(x,y):
    print(f"x:{x},y:{y}")

会生成9组测试用例

============================= test session starts =============================
collecting ... collected 9 items

test_004_参数化.py::test_add[1-2] PASSED                                 [ 11%]x:2,y:1

test_004_参数化.py::test_add[1-4] PASSED                                 [ 22%]x:4,y:1

test_004_参数化.py::test_add[1-6] PASSED                                 [ 33%]x:6,y:1

test_004_参数化.py::test_add[3-2] PASSED                                 [ 44%]x:2,y:3

test_004_参数化.py::test_add[3-4] PASSED                                 [ 55%]x:4,y:3

test_004_参数化.py::test_add[3-6] PASSED                                 [ 66%]x:6,y:3

test_004_参数化.py::test_add[5-2] PASSED                                 [ 77%]x:2,y:5

test_004_参数化.py::test_add[5-4] PASSED                                 [ 88%]x:4,y:5

test_004_参数化.py::test_add[5-6] PASSED                                 [100%]x:6,y:5


============================== 9 passed in 0.03s ==============================

Process finished with exit code 0

(2)pytest.ini

1、pytest配置文件可以改变pytest的运行方式,它是一个固定的文件pytest.ini文件,读取配置信息,按指定的方式去运行

2、位置:一般放在项目的根目录(即当前项目的顶级文件夹下)

现在我也找了很多测试的朋友,做了一个分享技术的交流群,共享了很多我们收集的技术文档和视频教程。
如果你不想再体验自学时找不到资源,没人解答问题,坚持几天便放弃的感受
可以加入我们一起交流。而且还有很多在自动化,性能,安全,测试开发等等方面有一定建树的技术大牛
分享他们的经验,还会分享很多直播讲座和技术沙龙
可以免费学习!划重点!开源的!!!
qq群号:691998057【暗号:csdn999】

3、命名:pytest.ini,不能使用任何中文符号,包括汉字、空格、引号、冒号等等

4、运行的规则:不管是主函数模式运行,命令行模式运行,都会自动读取这个全局配置文件。

「示列」

[pytest]
markers = 
	mark1:描述
	mark2:描述
	mark3:描述
addopts = -vs
;指定pytest最低版本号
minversion = 7.0
;pytest默认是搜索执行当前目录下的所有以test_开头的测试用例;
;我们可以在pytest.ini配置testpaths = test_case/test_001.py,则只执行当前配置的文件夹下或文件里的指定用例,可配置多个,空格隔开
testpaths = ./testcase

;模块名的规则,配置测试搜索的模块文件名称
python_files = test*.py

;类名的规则,配置测试搜索的测试类名
python_classes = Test*

;方法名的规则,配置测试搜索的测试函数名
python_functions = test
① marks标记

「打标记: marks功能」

  • 对用例打标记,运行的时候,只运行打标记的用例。

  • 300个回归用例。--打标记50个,作为冒烟测试。

「1、得先注册标记名」

pytest.ini

[pytest]
    markers = 
        mark1:标签说明(只能英文,可不写)
        mark2:标签说明(只能英文,可不写)
        mark3:标签说明(只能英文,可不写)

「2、给测试用例/测试类打标记」

基本使用

 @pytest.mark.已注册的标记
 # 如
 @pytest.mark.mark1

在测试类里面打标签,使用以下声明(测试类下,所有用例都被打上该标签):

class TestClass():
    pytestmark = pytest.mark.已注册标签名
    # 或者 多标签模式
    pytestmark = [pytest.mark.标签名1,pytest.mark.标签名2] 

在模块文件里打标签,使用以下声明(py文件下,所有测试函数和测试类里的测试函数,都被打上该标签)

import pytest
pytestmark = pytest.mark.已注册标签名
# 或者 多标签模式
pytestmark = [pytest.mark.标签名1,pytest.mark.标签名2]

「3、运行时设置只运行标记的用例」

pytest命令行:-m 标记名
在收集到的所有用例中,只运行对应标记名的用例。

「4、可以叠加标记」

② addopts配置
参数作用
-s表示输出调试信息,用于显示测试函数中print()打印的信息
-v未加前只打印模块名,加v后打印类名、模块名、方法名,显示更详细的信息
-q表示只显示整体测试结果
-vs这两个参数可以一起使用
-n支持多线程或者分布式运行测试用例(前提需安装:pytest-xdist插件)
–html生成html的测试报告(前提需安装:pytest-html插件)  如:pytest -vs --html ./reports/result.html
-x表示只要有一个测试用例报错,则执行停止
-k模糊匹配,测试用例的部分字符串,指定执行测试用例。
-mmark标记

(3)pytest.mark.相关

1、直接跳过执行
@pytest.mark.skip

2、满足条件跳过执行
@pytest.mark.skipif
根据特定的条件,不执行标识的测试函数.
 方法:
     skipif(condition, reason=None)
 参数:
     condition:跳过的条件,必传参数
     reason:标注原因,必传参数
 使用方法:
     @pytest.mark.skipif(condition, reason="xxx") 

「当condition为True则跳过,否则执行」

图片

3、标记为预期失败函数
标记测试函数为失败函数
 方法:
     xfail(condition=None, reason=None, raises=None, run=True, strict=False)
 常用参数:
     condition:预期失败的条件,必传参数
     reason:失败的原因,必传参数
 使用方法:
     @pytest.mark.xfail(condition, reason="xx")

「当condition为True则将这条用例标记为xpassed,否则标记为passed」

图片

4、重复测试

「使用"@pytest.mark.repeat"装饰器可以对测试用例进行重复运行」

import pytest

@pytest.mark.repeat(3)
def test_something():
    assert 1 + 1 == 2

这个测试用例会运行三次。

5、依赖测试

「使用"@pytest.mark.dependency"装饰器标记测试用例之间的依赖关系,以确保在需要的测试用例之前运行先决条件」

import pytest

@pytest.mark.dependency()
def test_login():
    assert True

@pytest.mark.dependency(depends=["test_login"])
def test_access_profile():
    assert True

@pytest.mark.dependency(depends=["test_login"])
def test_access_settings():
    assert True

(4)失败重运行

用例失败的情况下,可以重运行用例。

需要安装插件rerunfailures

「安装方法:」

pip install pytest-rerunfailures

「使用方式:」

命令行参数形式:

# 命令
pytest --reruns 重试次数
pytest --reruns 3 :运行失败的用例可以重新运行3次

「拓展」

#
pytest --reruns 重试次数 --rerun-dalay 次数之间的延时设置(单位:秒)

# 示列
pytest  --reruns 3 --rerun-dalay 5
表示失败的用例可以重新运行3次,每次重运行间隔5秒。

(5)指定用例的运行顺序

前面有讲到pytest有自己的用例执行顺序,但有时候我们就是想指定它按照我的方式去执行,有什么办法呢?

pytest有这样一个插件可以实现这个功能,pytest-ordering:指定用例的运行顺序

1、安装依赖包
pip install pytest-ordering
2、pytest-ordering的使用

「通过装饰器的方法来控制case的执行顺序」

「1.方式一:」

- 第一个执行:  @ pytest.mark.run('first')
- 第二个执行:  @ pytest.mark.run('second')
- 倒数第二个执行: @ pytest.mark.run('second_to_last')
- 最后一个执行:  @ pytest.mark.run('last')

「2.方式二:」

 - 第一个执行:  @ pytest.mark.first
 - 第二个执行:  @ pytest.mark.second
 - 倒数第二个执行:   @ pytest.mark.second_to_last
 - 最后一个执行:    @pytest.mark.last

「3.方式三:」

 - 第一个执行:  @ pytest.mark.run(order=1)
 - 第二个执行:  @ pytest.mark.run(order=2)
 - 倒数第二个执行:   @ pytest.mark.run(order=-2)
 - 最后一个执行:     @ pytest.mark.run(order=-1)

「执行优先级:0>较小的正数>较大的正数>无标记>较小的负数>较大的负数」

(6)用例相互依赖

场景:存在一个增删改查相关的操作功能,当增加操作用例失败时,删除、修改、查询操作不执行,这种场景该怎么来处理呢?Pytest 框架提供了一个pytest-dependency 插件帮我们做了这件事情,我们只需要简单的使用即可。

安装
  • 在命令行窗口输入:pip install pytest-dependency

  • 查看安装版本:pip show pytest-dependency

使用

使用方法 :用 @pytest.mark.dependency()对所依赖的用例进行标记,使用@pytest.mark.dependency(depends=["测试用例名称"]) 引用依赖,测试用例名称可以是多个

说明:当依赖的用例执行失败,被依赖的用例直接跳过

# !/usr/bin/python3
# _*_coding:utf-8 _*_
import pytest

@pytest.mark.dependency()
def test_add():
    print("我是 test_add 用例")
    assert False

@pytest.mark.dependency(depends=["test_add"])
def test_update():
    print("我是 test_update 用例")
    assert False

@pytest.mark.dependency(depends=["test_add"])
def test_delete():
    print("我是 test_delete 用例")
    assert True

@pytest.mark.dependency(depends=["test_add"])
def test_select():
    print("我是 test_select 用例")
    assert True

if __name__ == '__main__':
    pytest.main(["-s"])
  • 用 @pytest.mark.dependency()对所依赖的用例进行标记,使用@pytest.mark.dependency(depends=["测试用例名称"]) 引用依赖,测试用例名称可以是多个

  • 用例多存在多个依赖时,只要存在一个依赖失败,被依赖用例就跳过,所有依赖成功才执行

还有其他插件和功能可以自行在插件库进行探索。

其他

报错一:DeprecationWarning:

DeprecationWarning: distutils Version classes are deprecated. Use packaging.version instead.

if version.LooseVersion(pytest.version) >= version.LooseVersion(“6.0”):

网上很多说是版本过低啥的,我验证后发现,并不是,而是pytest有很多相关依赖,当前所用的环境和当前你安装的pytest所需要的一些依赖无法匹配,比如Allure之类的。

所以很简单的做法就是,你重新创建一个python的环境,保持一个项目拥有一套干净的环境,这样就不会出现类似的依赖冲突,相互不满足提示告警甚至报错的情况。

图片

进入虚拟环境,在pycharm里面点击Terminal选择Command Prompt,前面显示有个括号的就是进入了虚拟环境。

#退出虚拟环境
deactivate
#进入虚拟环境,重开命令窗口更快
activate

图片

至此,pytest系列完结,感谢各位小伙伴阅读至此,你一定是最棒的  ~

你这么好看又努力,关注一下我嘛~

下面是配套资料,对于做【软件测试】的朋友来说应该是最全面最完整的备战仓库,这个仓库也陪伴我走过了最艰难的路程,希望也能帮助到你!

最后: 可以在公众号:程序员小濠 ! 免费领取一份216页软件测试工程师面试宝典文档资料。以及相对应的视频学习教程免费分享!,其中包括了有基础知识、Linux必备、Shell、互联网程序原理、Mysql数据库、抓包工具专题、接口测试工具、测试进阶-Python编程、Web自动化测试、APP自动化测试、接口自动化测试、测试高级持续集成、测试架构开发测试框架、性能测试、安全测试等。

如果我的博客对你有帮助、如果你喜欢我的博客内容,请 “点赞” “评论” “收藏” 一键三连哦!

  • 22
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值