Pytest框架之fixture的详细使用教程


Posted in Python onApril 07, 2020

前言

前面一篇讲了setup、teardown可以实现在执行用例前或结束后加入一些操作,但这种都是针对整个脚本全局生效的
如果有以下场景:用例 1 需要先登录,用例 2 不需要登录,用例 3 需要先登录。很显然无法用 setup 和 teardown 来实现了fixture可以让我们自定义测试用例的前置条件

fixture优势

  • 命名方式灵活,不局限于 setup 和teardown 这几个命名
  • conftest.py 配置里可以实现数据共享,不需要 import 就能自动找到fixture
  • scope="module" 可以实现多个.py 跨文件共享前置
  • scope="session" 以实现多个.py 跨文件使用一个 session 来完成多个用例

fixture参数列表

@pytest.fixture(scope="function", params=None, autouse=False, ids=None, name=None)
def test():
    print("fixture初始化的参数列表")

参数列表

  • scope:可以理解成fixture的作用域,默认:function,还有class、module、package、session四个【常用】
  • autouse:默认:False,需要用例手动调用该fixture;如果是True,所有作用域内的测试用例都会自动调用该fixture
  • name:默认:装饰器的名称,同一模块的fixture相互调用建议写个不同的name

注意

session的作用域:是整个测试会话,即开始执行pytest到结束测试

测试用例如何调用fixture

  • 将fixture名称作为测试用例函数的输入参数
  • 测试用例加上装饰器:@pytest.mark.usefixtures(fixture_name)
  • fixture设置autouse=True
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
__title__ =
__Time__ = 2020-04-06 15:50
__Author__ = 小菠萝测试笔记
__Blog__ = https://www.cnblogs.com/poloyy/
"""
import pytest
# 调用方式一
@pytest.fixture
def login():
 print("输入账号,密码先登录")

def test_s1(login):
 print("用例 1:登录之后其它动作 111")

def test_s2(): # 不传 login
 print("用例 2:不需要登录,操作 222")

# 调用方式二
@pytest.fixture
def login2():
 print("please输入账号,密码先登录")

@pytest.mark.usefixtures("login2", "login")
def test_s11():
 print("用例 11:登录之后其它动作 111")

# 调用方式三
@pytest.fixture(autouse=True)
def login3():
 print("====auto===")

# 不是test开头,加了装饰器也不会执行fixture
@pytest.mark.usefixtures("login2")
def loginss():
 print(123)

执行结果

Pytest框架之fixture的详细使用教程

fixture的实例化顺序

  • 较高 scope 范围的fixture(session)在较低 scope 范围的fixture( function 、 class )之前实例化【session > package > module > class > function】
  • 具有相同作用域的fixture遵循测试函数中声明的顺序,并遵循fixture之间的依赖关系【在fixture_A里面依赖的fixture_B优先实例化,然后到fixture_A实例化】
  • 自动使用(autouse=True)的fixture将在显式使用(传参或装饰器)的fixture之前实例化
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
__title__ =
__Time__ = 2020-04-06 16:14
__Author__ = 小菠萝测试笔记
__Blog__ = https://www.cnblogs.com/poloyy/
"""
import pytest
order = []
@pytest.fixture(scope="session")
def s1():
 order.append("s1")
@pytest.fixture(scope="module")
def m1():
 order.append("m1")
@pytest.fixture
def f1(f3, a1):
 # 先实例化f3, 再实例化a1, 最后实例化f1
 order.append("f1")
 assert f3 == 123
@pytest.fixture
def f3():
 order.append("f3")
 a = 123
 yield a
@pytest.fixture
def a1():
 order.append("a1")
@pytest.fixture
def f2():
 order.append("f2")
def test_order(f1, m1, f2, s1):
 # m1、s1在f1后,但因为scope范围大,所以会优先实例化
 assert order == ["s1", "m1", "f3", "a1", "f1", "f2"]

执行结果 

断言成功

 关于fixture的注意点

添加了 @pytest.fixture ,如果fixture还想依赖其他fixture,需要用函数传参的方式,不能用 @pytest.mark.usefixtures() 的方式,否则会不生效

@pytest.fixture(scope="session")
def open():
 print("===打开浏览器===")

@pytest.fixture
# @pytest.mark.usefixtures("open") 不可取!!!不生效!!!
def login(open):
 # 方法级别前置操作setup
 print(f"输入账号,密码先登录{open}")

前面讲的,其实都是setup的操作,那么现在就来讲下teardown是怎么实现的

用fixture实现teardown并不是一个独立的函数,而是用 yield 关键字来开启teardown操作

#!/usr/bin/env python
# -*- coding: utf-8 -*-

"""
__title__ =
__Time__ = 2020-04-06 15:50
__Author__ = 小菠萝测试笔记
__Blog__ = https://www.cnblogs.com/poloyy/
"""

import pytest

@pytest.fixture(scope="session")
def open():
 # 会话前置操作setup
 print("===打开浏览器===")
 test = "测试变量是否返回"
 yield test
 # 会话后置操作teardown
 print("==关闭浏览器==")

@pytest.fixture
def login(open):
 # 方法级别前置操作setup
 print(f"输入账号,密码先登录{open}")
 name = "==我是账号=="
 pwd = "==我是密码=="
 age = "==我是年龄=="
 # 返回变量
 yield name, pwd, age
 # 方法级别后置操作teardown
 print("登录成功")

def test_s1(login):
 print("==用例1==")
 # 返回的是一个元组
 print(login)
 # 分别赋值给不同变量
 name, pwd, age = login
 print(name, pwd, age)
 assert "账号" in name
 assert "密码" in pwd
 assert "年龄" in age

def test_s2(login):
 print("==用例2==")
 print(login)

yield注意事项

  • 如果yield前面的代码,即setup部分已经抛出异常了,则不会执行yield后面的teardown内容
  • 如果测试用例抛出异常,yield后面的teardown内容还是会正常执行

yield+with的结合

# 官方例子
@pytest.fixture(scope="module")
def smtp_connection():
 with smtplib.SMTP("smtp.gmail.com", 587, timeout=5) as smtp_connection:
 yield smtp_connection # provide the fixture value

smtp_connection 连接将测试完成执行后已经关闭,因为 smtp_connection 对象自动关闭时, with 语句结束。

addfinalizer 终结函数

@pytest.fixture(scope="module")
def test_addfinalizer(request):
 # 前置操作setup
 print("==再次打开浏览器==")
 test = "test_addfinalizer"

 def fin():
 # 后置操作teardown
 print("==再次关闭浏览器==")

 request.addfinalizer(fin)
 # 返回前置操作的变量
 return test
def test_anthor(test_addfinalizer):
 print("==最新用例==", test_addfinalizer)

 注意事项

如果 request.addfinalizer() 前面的代码,即setup部分已经抛出异常了,则不会执行 request.addfinalizer() 的teardown内容(和yield相似,应该是最近新版本改成一致了)
可以声明多个终结函数并调用

总结

到此这篇关于Pytest框架之fixture的详细使用教程的文章就介绍到这了,更多相关Pytest fixture使用内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
python读取html中指定元素生成excle文件示例
Apr 03 Python
Python环境下安装使用异步任务队列包Celery的基础教程
May 07 Python
python学习教程之Numpy和Pandas的使用
Sep 11 Python
python 统计一个列表当中的每一个元素出现了多少次的方法
Nov 14 Python
windows系统中Python多版本与jupyter notebook使用虚拟环境的过程
May 15 Python
Python Django简单实现session登录注销过程详解
Aug 06 Python
python实现批量修改服务器密码的方法
Aug 13 Python
python 两个数据库postgresql对比
Oct 21 Python
pytorch torch.nn.AdaptiveAvgPool2d()自适应平均池化函数详解
Jan 03 Python
Python 使用 environs 库定义环境变量的方法
Feb 25 Python
Django日志及中间件模块应用案例
Sep 10 Python
python 字符串格式化的示例
Sep 21 Python
4行Python代码生成图像验证码(2种)
Apr 07 #Python
Django media static外部访问Django中的图片设置教程
Apr 07 #Python
快速解决Django关闭Debug模式无法加载media图片与static静态文件
Apr 07 #Python
Python图片处理模块PIL操作方法(pillow)
Apr 07 #Python
解决Django no such table: django_session的问题
Apr 07 #Python
Python PIL库图片灰化处理
Apr 07 #Python
Python3.7 读取音频根据文件名生成脚本的代码
Apr 07 #Python
You might like
php4与php5的区别小结(配置异同)
2011/12/20 PHP
php中使用parse_url()对网址进行解析的实现代码(parse_url详解)
2012/01/03 PHP
php使用GeoIP库实例
2014/06/27 PHP
日常整理PHP中简单的图形处理(经典)
2015/10/26 PHP
Javascript 遮罩层和加载效果代码
2013/08/01 Javascript
自动设置iframe大小的jQuery代码
2013/09/11 Javascript
Jquery中children与find之间的区别详细解析
2013/11/29 Javascript
jquery操作checkbox示例分享
2014/07/21 Javascript
jQuery实现冻结表头的方法
2015/03/09 Javascript
深入浅出理解javaScript原型链
2015/05/09 Javascript
浅析Node.js的Stream模块中的Readable对象
2015/07/29 Javascript
Google 地图控件集详解及实例代码
2016/08/06 Javascript
vue如何引用其他组件(css和js)
2017/04/13 Javascript
在 Angular 中使用Chart.js 和 ng2-charts的示例代码
2017/08/17 Javascript
JavaScript变量提升和严格模式实例分析
2019/01/27 Javascript
VUE的history模式下除了index外其他路由404报错解决办法
2019/08/21 Javascript
[02:05]DOTA2完美大师赛趣味视频之看我表演
2017/11/18 DOTA
[33:15]2018DOTA2亚洲邀请赛3月30日 小组赛B组 VP VS Mineski
2018/03/31 DOTA
分析python服务器拒绝服务攻击代码
2014/01/16 Python
python数据结构之二叉树的统计与转换实例
2014/04/29 Python
python list排序的两种方法及实例讲解
2017/03/20 Python
Python实现的圆形绘制(画圆)示例
2018/01/31 Python
Python中那些 Pythonic的写法详解
2019/07/02 Python
python Django的web开发实例(入门)
2019/07/31 Python
tensorflow入门:TFRecordDataset变长数据的batch读取详解
2020/01/20 Python
在python下实现word2vec词向量训练与加载实例
2020/06/09 Python
美国知名奢侈美容品牌零售商:Cos Bar
2017/04/21 全球购物
Tarte Cosmetics官网:美国最受欢迎的化妆品公司之一
2017/08/24 全球购物
美国儿童珠宝在线零售商:Loveivy
2019/05/22 全球购物
专业实习自我鉴定
2013/10/29 职场文书
小区消防演习方案
2014/02/21 职场文书
本溪水洞导游词
2015/02/11 职场文书
上帝为你开了一扇窗之Tkinter常用函数详解
2021/06/02 Python
Spring Boot 实现敏感词及特殊字符过滤处理
2021/06/29 Java/Android
Win11 Build 21996.1 Dev版怎么样? win11系统截图欣赏
2021/11/21 数码科技
十大动画制作软件,Adobe产品上榜两款,第一是行业标准软件
2022/03/18 杂记