前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Python测试框架pytest(08)fixture - conftest.py、yield、addfinalizer

Python测试框架pytest(08)fixture - conftest.py、yield、addfinalizer

作者头像
wangmcn
发布2022-07-26 14:16:47
3710
发布2022-07-26 14:16:47
举报
文章被收录于专栏:AllTests软件测试

Python测试框架pytest(08)

fixture

conftest.py、yield、addfinalizer

目录

  • 1、conftest.py作用范围
  • 2、yield实现teardown
  • 3、yield+with的结合
  • 4、addfinalizer终结函数

1、conftest.py作用范围

conftest.py 文件名称是固定的,pytest 会自动识别该文件,可以理解成一个专门存放 fixture 的配置文件。

一个工程下可以建多个 conftest.py 的文件,一般在工程根目录下设置的 conftest 文件起到全局作用。在不同子目录下也可以放 conftest.py 的文件,作用范围只能在该层级以及以下目录生效。

conftest.py 配置 fixture 注意事项:

  • pytest 会默认读取 conftest.py 里面的所有 fixture。
  • conftest.py 文件名称是固定的,不能改动。
  • conftest.py 只对同一个 package 下的所有测试用例生效。
  • 不同目录可以有自己的 conftest.py,一个项目中可以有多个 conftest.py。
  • 测试用例文件中不需要手动 import conftest.py,pytest 会自动查找。

示例:

目录结构:

1、My_pytest_Demo/conftest.py

脚本代码:

代码语言:javascript
复制
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
微信公众号:AllTests软件测试
"""

import pytest

@pytest.fixture(scope='session', autouse=True)
def login():
    print("====准备登录====")

2、My_pytest_Demo/fixture_chapter/conftest.py

脚本代码:

代码语言:javascript
复制
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
微信公众号:AllTests软件测试
"""

import pytest

@pytest.fixture(scope='session', autouse=True)
def bai_du():
    print("====登录成功====")

3、My_pytest_Demo/fixture_chapter/login_demo.py

脚本代码:

代码语言:javascript
复制
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
微信公众号:AllTests软件测试
"""

import pytest

class TestCase:
    def test_case(self):
        print("====执行用例====")

if __name__ == '__main__':
    pytest.main(['-s', 'login_demo.py'])

4、运行结果:

执行login_demo.py文件,根目录下的conftest.py先执行,之后执行fixture_chapter目录下的conftest.py,最后才执行login_demo.py

2、yield实现teardown

前面章节讲的其实都是 setup 的操作,接下来讲解怎样来实现 teardown 的操作。

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

  • 当 pytest.fixture(scope="session") 时,作用域是整个测试会话,即开始执行 pytest 到结束测试只会执行一次。
  • 当 pytest.fixture(scope="function") 时,pytest 的 yield 类似 unittest 的 teardown。每个方法(函数)都会执行一次。
  • 当 pytest.fixture(scope="module") 时,module 作用是整个 .py 文件都会生效(整个文件只会执行一次),用例调用时,参数写上函数名称就可以。

1、创建test_fixture4.py文件

脚本代码:

代码语言:javascript
复制
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
微信公众号:AllTests软件测试
"""
import pytest

@pytest.fixture(scope="session")
def open():
    # 会话前置操作setup
    print("===打开浏览器open===")
    yield
    # 会话后置操作teardown
    print("===关闭浏览器open===")

@pytest.fixture
def login(open):
    # 方法级别前置操作setup
    print("===登陆操作login===")
    name = "===账号==="
    pwd = "===密码==="
    # 返回变量
    yield name, pwd
    # 方法级别后置操作teardown
    print("===登录成功login===")

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

def test_case2(login):
    print("===测试用例2===")
    print(login)

2、运行结果:

注意要点:

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

3、yield+with的结合

yield 也可以配合 with 语句使用。

创建test_fixture5.py文件

脚本代码:

代码语言:javascript
复制
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
微信公众号:AllTests软件测试
"""
import pytest
import smtplib

@pytest.fixture(scope="module")
def smtp_connection():
    with smtplib.SMTP("smtp.gmail.com", 587, timeout=5) as smtp_connection:
        yield smtp_connection

4、addfinalizer终结函数

除了 yield 可以实现 teardown,在 request-context 对象中注册 addfinalizer 方法也可以实现终结函数。

1、创建test_fixture6.py文件

在用法上,addfinalizer 跟 yield 是不同的,需要你去注册作为终结器使用的函数。例如:增加一个函数 fin,并且注册成终结函数。

脚本代码:

代码语言:javascript
复制
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
微信公众号:AllTests软件测试
"""
import pytest

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

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

    request.addfinalizer(fin)
    # 返回前置操作的变量
    return test

def test_case(test_addfinalizer):
    print("===最新用例===", test_addfinalizer)

2、运行结果:

yield 与 addfinalizer 的区别:

1、addfinalizer 可以注册多个终结函数。

创建test_fixture_7.py文件

脚本代码:

代码语言:javascript
复制
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
微信公众号:AllTests软件测试
"""
import pytest

@pytest.fixture()
def demo_addfinalizer(request):
    print("====setup====")
    def fin1():
        print("====teardown1====")
    def fin2():
        print("====teardown2====")
    def fin3():
        print("====teardown3====")

    # 注册demo_addfinalizer为终结函数
    request.addfinalizer(fin1)
    request.addfinalizer(fin2)
    request.addfinalizer(fin3)

def test_case1(demo_addfinalizer):
    print("====执行用例test_case1====")

def test_case2(demo_addfinalizer):
    print("====执行用例test_case2====")

def test_case3(demo_addfinalizer):
    print("====执行用例test_case3====")

运行结果:

注册的3个函数都被执行了,但是要注意的是执行顺序,与注册的顺序相反。

2、当setup的代码执行错误,addfinalizer依旧会执行。

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-07-30,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 AllTests软件测试 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 目录
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档