Pytest夹具,范围" class"在每个方法上运行

时间:2017-11-15 16:41:09

标签: python pytest

我试图用Pytest创建一个测试环境。我们的想法是将测试方法分组到类中。

对于每个类/组,我想附加一个将要参数化的config灯具。这样我就可以使用"配置A"来运行所有测试。然后用"配置B"进行所有测试;等等。

但是,我想要一个reset夹具,可以在特定方法或类的所有方法之前执行。

我遇到的问题是,一旦我将reset夹具(应用于某个方法或整个类),config夹具似乎在函数范围内工作,而不是班级范围。因此,一旦我应用reset夹具,就会在课程中的每个方法之前/之后调用config夹具。

以下代码重现了这个问题:

import pytest
from pytest import *

@fixture(scope='class')
def config(request):
    print("\nconfiguring with %s" % request.param)
    yield
    print("\ncleaning up config")

@fixture(scope='function')
def reset():
    print("\nreseting")

@mark.parametrize("config", ["config-A", "config-B"], indirect=True)
#@mark.usefixtures("reset")
class TestMoreStuff(object):

    def test_a(self, config):
        pass

    def test_b(self, config):
        pass

    def test_c(self, config):
        pass

测试显示config装置应该如何工作,对整个班级只执行一次。如果取消注释usefixtures装饰,您会注意到config装置将在每个测试方法中执行。 是否可以在不触发此行为的情况下使用reset灯具?

2 个答案:

答案 0 :(得分:4)

正如我在评论中提到的,这似乎是Pytest 3.2.5中的一个错误。

有一种解决方法,即“强制”参数化的范围。因此,在这种情况下,如果您在scope="class"装饰器中包含parametrize,则会获得所需的行为。

import pytest
from pytest import *

@fixture(scope='class')
def config(request):
    print("\nconfiguring with %s" % request.param)
    yield
    print("\ncleaning up config")

@fixture(scope='function')
def reset():
    print("\nreseting")

@mark.parametrize("config", ["config-A", "config-B"], indirect=True, scope="class")
@mark.usefixtures("reset")
class TestMoreStuff(object):

    def test_a(self, config):
        pass

    def test_b(self, config):
        pass

    def test_c(self, config):
        pass

答案 1 :(得分:0)

这取决于您使用的是哪个版本的pytest。

在旧版 { "_id": "5a0d424079191657fca9e853", "reason": "Say Hello", "approved": false, "held": false, "doctor": "5a0add9b577d7916187cd9f2", "patient": "59f5df20a3071554c5f843e1", "appointmentStamp": 1510927380000, "__v": 0, "createdOn": 1510817910134 } 中实现此问题存在一些语义问题。因此,这个想法尚未在较早的pytest中实现。有人已经提出了实施相同的建议。你可以参考this

“当参数化测试使用参数化夹具时,夹具范围不起作用”。 这就是错误。 您可以参考this

此问题已在最新版本的pytest中得到解决。这是与pytest

相同的commit

希望它会对你有所帮助。