pytest的setup和teardown

本文详细介绍了unittest和pytest测试框架中setup和teardown的使用,包括模块级、函数级、类级和方法级的生命周期钩子。通过示例代码展示了这些钩子在不同层级的执行顺序,帮助读者理解如何在测试中设置和清理环境。

在unittest中就有setup和teardown,pytest也不例外。主要有五种:

  • 模块级(setup_module/teardown_module),开始于模块始末,全局的
  • 函数级(setup_function/teardown_function),只对函数用例生效(不在类中)
  • 类级(setup_class/teardown_class),只在类中前后运行一次(在类中)
  • 方法级(setup_method/teardown_method),开始于方法前后(在类中)
  • setup/teardown运行在调用方法/函数的前后

例如:下面的test_setup.py测试了上面五种方法,且setup/teardown在模块里。

import pytest

def setup_module():
    print('setup_module')

def teardown_module():

    print('teardown_module')
def setup_function():
    print('setup_function')

def teardown_function():
    print('teardown_function')

def test_01():
    print('test01')

def test_02():
    print('test02')

class TestSet():
    @classmethod
    def setup_class(cls):
        print('setup_class')

    @classmethod
    def teardown_class(cls):
        print('teardown_class')

    def test_method1(self):
        print('test_method1')

    def test_method2(self):
        print('test_method2')

    def setup_method(self):
        print('setup_method')


    def teardown_method(self):
        print('teardown_method')


def setup():
    print('setup')

def teardown():
    print('teardown')

输出为:

D:\pythonProject\my_selenium_project\testcases\pytest>pytest -v -s  test_setup.py
======================================================================== test session starts ========================================================================
platform win32 -- Python 3.7.6, pytest-6.2.4, py-1.10.0, pluggy-0.13.1 -- d:\python3.7.6\python.exe
cachedir: .pytest_cache
rootdir: D:\pythonProject\my_selenium_project\testcases\pytest, configfile: pytest.ini
collected 4 items                                                                                                                                                    

test_setup.py::test_01 setup_module
setup_function
setup
test01
PASSEDteardown
teardown_function

test_setup.py::test_02 setup_function
setup
test02
PASSEDteardown
teardown_function

test_setup.py::TestSet::test_method1 setup_class
setup_method
test_method1
PASSEDteardown_method

test_setup.py::TestSet::test_method2 setup_method
test_method2
PASSEDteardown_method
teardown_class
teardown_module

setup/teardown在类中:

D:\pythonProject\my_selenium_project\testcases\pytest>pytest -v -s  test_setup.py
======================================================================== test session starts ========================================================================
platform win32 -- Python 3.7.6, pytest-6.2.4, py-1.10.0, pluggy-0.13.1 -- d:\python3.7.6\python.exe
cachedir: .pytest_cache
rootdir: D:\pythonProject\my_selenium_project\testcases\pytest, configfile: pytest.ini
collected 4 items                                                                                                                                                    

test_setup.py::test_01 setup_module
setup_function
test01
PASSEDteardown_function

test_setup.py::test_02 setup_function
test02
PASSEDteardown_function

test_setup.py::TestSet::test_method1 setup_class
setup_method
setup
test_method1
PASSEDteardown
teardown_method

test_setup.py::TestSet::test_method2 setup_method
setup
test_method2
PASSEDteardown
teardown_method
teardown_class
teardown_module


========================================================================= 4 passed in 0.04s =========================================================================

<think>我们正在讨论Pytest框架中的setupteardown方法。根据引用,Pytest提供了不同级别的setupteardown方法,用于在测试的不同阶段进行初始化清理工作。这些方法包括模块级、函数级、类级、方法级会话级。根据引用[2],Pytest提供了5种类型的setupteardown方法:1.模块级别:setup_module/teardown_module,在整个模块的开始结束执行。2.函数级别:setup_function/teardown_function,在每个测试函数(不在类中)的开始结束执行。3.类级别:setup_class/teardown_class,在每个类的开始结束执行,使用@classmethod装饰器。4.方法级别:setup_method/teardown_method,在每个类中的测试方法(即类中的函数)的开始结束执行。5.会话级别:setup_session/teardown_session,在整个测试会话的开始结束执行(pytest通常使用更高级的fixture来实现会话级别的设置,但这里提到的可能是旧的或另一种方式,实际上在pytest中会话级别的设置通常通过fixture的scope="session"实现)。另外,引用[3][4]提到,执行顺序是:当测试函数在类外时,使用函数级别的setup_functionteardown_function;当测试函数在类内时,会先执行类级别的setup_class,然后执行方法级别的setup_method(或setup),然后执行测试方法,之后执行方法级别的teardown_method(或teardown),最后执行类级别的teardown_class。需要注意的是,在Pytest中,还有一种更现代的方式是使用fixture,它可以更灵活地定义设置清理,并且可以通过不同的作用域(function,class,module,session)来控制执行的频率。但是,用户明确询问的是setupteardown,所以我们主要讨论传统的xUnit风格的setup/teardown。下面我们详细说明:1.模块级别(Module):-setup_module:在整个模块的第一个测试开始之前运行一次。-teardown_module:在整个模块的最后一个测试结束之后运行一次。2.函数级别(Function):-setup_function:在每个不在类中的测试函数之前运行。-teardown_function:在每个不在类中的测试函数之后运行。3.类级别(Class):-setup_class:在一个类中的所有测试方法执行之前运行一次(使用@classmethod装饰器)。-teardown_class:在一个类中的所有测试方法执行之后运行一次(使用@classmethod装饰器)。4.方法级别(Method):-setup_method:在每个类中的测试方法(即类中的函数)之前运行。-teardown_method:在每个类中的测试方法之后运行。5.另外,在类中,还可以使用setupteardown(不带后缀)作为方法级别的设置清理,它们与setup_method/teardown_method作用相同。执行顺序示例(引用[3]):-类外的测试函数:setup_function->测试函数->teardown_function-类内的测试方法:setup_class->(setup_method->测试方法->teardown_method)[每个方法都这样]->teardown_class注意:在同一个类中,每个测试方法都会触发一次setup_methodteardown_method。另外,引用[4]提到,有时控制台输出可能会因为使用-s参数而导致teardown的输出在测试函数输出之前,但实际执行顺序是正确的。使用-v参数可以更清晰地看到执行顺序。总结区别:-不同级别的setupteardown控制不同的范围:模块、函数、类、方法。-它们按照从大到小的范围嵌套执行:例如,对于类中的测试方法,先执行模块级setup(如果有),然后类级setup,然后方法级setup,然后测试方法,然后方法级teardown,然后类级teardown,最后模块级teardown(在模块结束时)。下面用一个代码示例来说明:```python#模块级别defsetup_module():print("\n模块级别setup_module")defteardown_module():print("\n模块级别teardown_module")#函数级别defsetup_function(function):print(f"\n函数级别setup_function:{function.__name__}")defteardown_function(function):print(f"\n函数级别teardown_function:{function.__name__}")#类外的测试函数deftest_outside():print("执行类外的测试函数")#类定义classTestClass:#类级别@classmethoddefsetup_class(cls):print("\n类级别setup_class")@classmethoddefteardown_class(cls):print("\n类级别teardown_class")#方法级别(也可以使用setup/teardown)defsetup_method(self,method):print(f"\n方法级别setup_method:{method.__name__}")defteardown_method(self,method):print(f"\n方法级别teardown_method:{method.__name__}")#类内的测试方法deftest_inside1(self):print("执行类内的测试方法1")deftest_inside2(self):print("执行类内的测试方法2")```执行顺序(假设按顺序执行):1.setup_module2.setup_function(为test_outside)3.test_outside4.teardown_function(为test_outside)5.setup_class6.对于test_inside1:setup_method->test_inside1->teardown_method7.对于test_inside2:setup_method->test_inside2->teardown_method8.teardown_class9.teardown_module注意:模块级别的setup_module在模块中所有测试之前,teardown_module在最后。函数级别的setup_function/teardown_function只对类外的函数有效。类内的每个测试方法都会触发一次setup_methodteardown_method。另外,在Pytest中,还可以使用fixture来替代这些setup/teardown方法,并且fixture更加灵活,可以参数化,可以共享等。但用户问题聚焦在setup/teardown,所以这里不展开fixture。如果用户想了解fixture,可以在相关问题中提出。现在,生成相关问题:</think>### Pytestsetupteardown的使用方法及区别 在Pytest框架中,**setupteardown**是用于测试用例初始化清理的关键机制。根据执行范围级别,可分为5种类型: #### 📌 1. 模块级别(Module) - **`setup_module`**: 整个模块**开始前**执行一次 - **`teardown_module`**: 整个模块**结束后**执行一次 ```python def setup_module(): print("模块初始化:创建数据库连接") def teardown_module(): print("模块清理:关闭数据库连接") ``` #### 📌 2. 函数级别(Function) - **`setup_function`**: 每个**非类测试函数**前执行 - **`teardown_function`**: 每个**非类测试函数**后执行 ```python def setup_function(): print("函数初始化:准备测试数据") def test_api_response(): assert 200 == 200 def teardown_function(): print("函数清理:删除临时文件") ``` #### 📌 3. 类级别(Class) - **`setup_class`**: 类中**所有方法前**执行一次(需`@classmethod`) - **`teardown_class`**: 类中**所有方法后**执行一次(需`@classmethod`) ```python class TestUser: @classmethod def setup_class(cls): print("类初始化:创建测试用户") def test_login(self): assert True @classmethod def teardown_class(cls): print("类清理:删除测试用户") ``` #### 📌 4. 方法级别(Method) - **`setup_method`**: 类中**每个测试方法前**执行 - **`teardown_method`**: 类中**每个测试方法后**执行 ```python class TestCart: def setup_method(self): print("方法初始化:清空购物车") def test_add_item(self): assert items == 1 def teardown_method(self): print("方法清理:重置购物车") ``` #### 📌 5. 会话级别(Session) - 通过`fixture(scope="session")`实现(传统setup/teardown无此级别) ```python @pytest.fixture(scope="session") def global_setup(): print("会话初始化") yield print("会话清理") ``` --- ### 🧩 关键区别总结 | 类型 | 作用范围 | 执行频率 | 典型应用场景 | |------------|-------------------|----------------|----------------------------------| | **模块级** | 整个.py文件 | 1次/模块 | 数据库连接/全局配置[^2] | | **函数级** | 类外的独立测试函数 | 1次/测试函数 | 接口测试的独立初始化[^1] | | **类级** | 测试类内部 | 1次/测试类 | 用户登录态/共享资源初始化[^3] | | **方法级** | 类中的测试方法 | 1次/测试方法 | 测试数据准备/环境重置[^4] | | **会话级** | 整个测试会话 | 1次/测试运行 | 全局缓存/跨模块共享资源 | --- ### ⚠️ 执行顺序规则 1. **嵌套结构**优先级: ``` 模块级 → 类级 → 方法级 → 测试用例 → 方法级 → 类级 → 模块级 ``` 2. **类内外差异**: - 类外测试函数:仅触发`setup_function/teardown_function` - 类内测试方法:触发`setup_class+setup_method``teardown_method+teardown_class`[^3] 3. **实际执行顺序**: ```mermaid graph LR A[setup_module] --> B[setup_class] B --> C[setup_method] C --> D[测试用例] D --> E[teardown_method] E --> F[teardown_class] F --> G[teardown_module] ``` --- ### 💡 最佳实践建议 1. **资源复用**:高频操作(如DB连接)用**模块级**,避免重复开销 2. **环境隔离**:相互干扰的测试用**方法级**保证独立性 3. **浏览器测试**:使用`setup_class/teardown_class`减少浏览器启动次数[^1] 4. **输出顺序**:添加`-v`参数确保控制台显示正确的执行顺序[^4] > 示例:Selenium测试优化 > ```python > class TestCheckout: > @classmethod > def setup_class(cls): > cls.driver = webdriver.Chrome() # 只启动1次浏览器 > > def test_add_to_cart(self): > self.driver.get(url) > # 测试操作... > > @classmethod > def teardown_class(cls): > cls.driver.quit() # 所有用例结束后关闭 > ``` ---
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

永远不要矫情

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值