ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

python测试框架之pytest (四)fixture

2022-01-30 10:03:06  阅读:190  来源: 互联网

标签:python fix fixture test pytest print def


一 引言
在测试过程中,通常会包括三个步骤,前置、执行测试、后置,pytest框架中,提供了类似的函数。

模块级别:setup_module (前置) / teardown_module(后置) ->不在类中,全局的

函数级别:setup_function(前置)/ teardown_function(后置) ->不在类中

类级别: setup_class (前置) / teardown_class (后置) ->只在类中前后运行一次

方法级别:setup_method(前置)/ teardown_method (后置)->类中方法前后

用例级别:setup (前置)/ teardown (后置)->运行测试用例的前后

但是,这种前置、后置处理方式存在一定的缺陷。假如,一个测试类中,存在多个测试方法,每一个测试方法需要不同的前置、后置,该怎么处理会比较好呢?

pytest提供了一种高级的功能,fixture。可以通过实现文件共享机制,供模块、函数、类或者整个项目会话使用。

在conftest.py中实现文件共享机制,而且不需要import导入,pytest会自动去加载匹配对应的fixture。

二 fixture参数详解

@pytest.fixture(scope = "function", params=None, autouse=False, ids=None, name=None)

1、scope:控制fixture作用域,默认是function级别

 session:每次会话只需要运行一次,会话内所有模块、类、方法,都共享这个fixture

 module:每一个.py文件调用一次

 class:每一个类中调用一次

 function:每一个function或者类方法中都会调用

2、params:可选的参数列表

 ①Fixture可选的参数列表,支持列表传入

 ②默认为None,每个param的值。

 ③可通过request.param接受设置的返回值,params中有多少个元素,在测试时,引用次fixture的函数就会调用几次。

 ④可与参数ids一起使用,作为每个参数的标识。

3、autouse:是否自动执行设置的fixture,默认是False

 当autouse为True时,自动执行定义的fixture。

 当autouse为False时,测试函数需要调用定义的fixture,定义的fixture函数才能执行。

4、ids:指定每个字符串id

 当有多个params时,针对每一个param,可以指定id,这个id将变成测试用例名字的一部分。如果没有提供id,id将自动生成。

5、name:fixture的重命名

 默认是fixture函数的名称,可以通过name参数更改这个fixture的名称。更改后,如果这个fixture被调用,则使用更改后的名称。

三 fixture应用
3.1、函数名调用fixture

import pytest


@pytest.fixture
def fix_a():
    print("调用fix_a")


def test_a(fix_a):
    print("执行test_a用例")

执行结果在这里插入图片描述
根据运行结果可以看出,先执行了前置fixture,再执行测试用例。

3.2、@pytest.mark.usefixtures调用fixture

import pytest


@pytest.fixture
def fix_a():
    print("调用fix_a")


@pytest.mark.usefixtures('fix_a')
def test_a1(fix_a):
    print("执行test_a1用例")

3.3、多参数调用fixture

@pytest.fixture(params=['a', 'b', 'c'], scope="function")
def fix_a2(request):
    print(f'调用fixture:{request.param}')


def test_a2(fix_a2):
    print('执行test_a2用例')

执行结果在这里插入图片描述
从执行结果,可以看到生成了三条测试用例,所以fixture也支持参数化。

3.4、autouse使用
从上面例子来看,fixture都需要主动调用,才能生效。但有时需要让用例自动执行,这时候就需要添加autouse参数,让fixture自动执行。

@pytest.fixture(autouse=True)
def fix_a3(request):
    case_name = request.node.name
    print(f"开始执行{case_name}测试用例 ")
    yield
    print(f"{case_name}测试用例执行结束 ")


def test_a3():
    print('test_a3')
    assert "tom" == "tom"

执行结果
在这里插入图片描述
从执行结果看,设置了autouse=True后,定义的fixture自动执行。并且定义的fixture通过yield关键字隔离前置、后置,yield之前是前置,yield之后是后置。

3.5、fixture嵌套使用

@pytest.fixture()
def fix_a4():
    print('调用fix_a4')


@pytest.fixture()
def fix_a5(fix_a4):
    print('调用fix_a5')


def test_a4(fix_a5):
    print('-----执行test_a4测试用例------')

执行结果
在这里插入图片描述
从执行结果看,调用fix_a5时,先调用fix_a4,再调用fix_a5。这个场景比较适用于多个测试场景组合,多个前置测试步骤时使用。

3.6、conftest.py共享机制
实际测试工作中,常需要在全局范围内使用同一个测试前置、后置操作。可以使用conftest.py,在conftest.py定义的fixture不需要进行import,pytest会自动查找使用。

3.7、有返回值的fixture

@pytest.fixture()
def fix_a6():
    amount = round(32.567, 2)
    yield amount


def test_a6(fix_a6):
    # 通过一个变量接收fix_a6
    amount = fix_a6
    print(f'fix_a6接受到的数据时{amount}')

执行结果
在这里插入图片描述
3.8、@pytest.fixture与@pytest.mark.parametrize结合使用

@pytest.fixture()
def fix_a7(request):
    print("fixture拿到的原始参数是:", request.param)
    sum = request.param[0] + request.param[1]
    yield sum


@pytest.mark.parametrize("fix_a7", [(1, 3), (2, 4)], indirect=True)
def test_a7(fix_a7):
    print('-----执行test_a7测试用例------')
    print(f"fixture返回的参数和是:{fix_a7}")

执行结果
在这里插入图片描述
首先,fixture做了参数化,需要在fixture中接受变量,传入request这个内置fixture。然后传入的变量,通过request的param接收,在@pytest.mark.parametrize中,将定义的xi_a7传入参数化中用例中。

标签:python,fix,fixture,test,pytest,print,def
来源: https://blog.csdn.net/weixin_44045851/article/details/122744235

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有