以编程方式在 pytest 插件中注册夹具

rth*_*rth 1 python pytest python-unittest

我正在寻找一种从 Python 运行一些 pytest 单元测试并动态注册 pytest 夹具的方法。如 Pytest 文档中所述,以编程方式运行测试时,可以使用自定义插件更改其行为。我有以下设置

validation.py (包含要运行的测试)

def test_valid(new_fixture):
    assert new_fixture > 0
Run Code Online (Sandbox Code Playgroud)

启动时,

import pytest

new_fixture_value = 36

class FixtureRegPlugin(object):
    def pytest_sessionstart(self):
        print('Test session start')

        @pytest.fixture
        def new_fixture():
            return new_fixture_value

pytest.main(['-sv', './validation.py'], plugins=[FixtureRegPlugin()])
Run Code Online (Sandbox Code Playgroud)

在这里,我们validation.py使用一个自定义插件运行测试,该插件为pytest_sessionstart. 这个钩子在测试会话开始时执行,我可以看到预期的打印输出。但是,new_fixture未注册,因此测试失败并显示“未找到夹具”错误。

目标是在运行时修改夹具的结果,因此我不能将其定义放在validation.py.

小智 5

您是否有任何理由不想@pytest.fixture(scope='session')conftest.py文件中使用而不是编写自己的插件?这能否实现您正在寻找的在运行时更改夹具的功能?

无论如何,如果您更改缩进并添加selfnew_fixture的参数,它应该可以工作。

        @pytest.fixture
        def new_fixture():
            return new_fixture_value
Run Code Online (Sandbox Code Playgroud)

    @pytest.fixture(scope='session')
    def new_fixture(self):
        return new_fixture_value
Run Code Online (Sandbox Code Playgroud)

您可以--setup-show在命令行上查看设置和拆卸。

script.py”的内容:

import pytest


class FixtureRegPlugin(object):

    @pytest.fixture(scope='session')
    def session_fixture(self):
        pass

    @pytest.fixture(scope='module')
    def module_fixture(self):
        pass

    @pytest.fixture(scope='function')
    def function_fixture(self):
        pass


pytest.main(['--setup-show', './validation.py'], plugins=[FixtureRegPlugin()])
Run Code Online (Sandbox Code Playgroud)

内容validation.py

def test_A(session_fixture, module_fixture, function_fixture):
    pass

def test_B(session_fixture, module_fixture, function_fixture):
    pass
Run Code Online (Sandbox Code Playgroud)

运行python script.py

Test session start
=================================== test session starts
platform linux -- Python 3.6.2, pytest-3.2.2, py-1.4.34, pluggy-0.4.0
rootdir: /home/stackoverflow, inifile:
collected 2 items                                                                                                                                                                                     

validation.py 
SETUP    S session_fixture
  SETUP    M module_fixture
      SETUP    F function_fixture
        validation.py::test_A (fixtures used: function_fixture, module_fixture, session_fixture).
      TEARDOWN F function_fixture
      SETUP    F function_fixture
        validation.py::test_B (fixtures used: function_fixture, module_fixture, session_fixture).
      TEARDOWN F function_fixture
  TEARDOWN M module_fixture
TEARDOWN S session_fixture

=================================== 2 passed in 0.00 seconds
Run Code Online (Sandbox Code Playgroud)