Pytest с использованием инструментов в качестве аргументов в параметризации

Я хотел бы использовать фикстуры в качестве аргументов pytest.mark.parametrize или что-то, что будет иметь те же результаты.

Например:

import pytest
import my_package

@pytest.fixture
def dir1_fixture():
    return '/dir1'

@pytest.fixture
def dir2_fixture():
    return '/dir2'

@pytest.parametrize('dirname, expected', [(dir1_fixture, 'expected1'), (dir2_fixture, 'expected2')]
def test_directory_command(dirname, expected):
    result = my_package.directory_command(dirname)
    assert result == expected

Проблема с параметрами прибора состоит в том, что каждый параметр прибора запускается каждый раз, когда он используется, но я этого не хочу. Я хочу иметь возможность выбрать, какие приборы будут использоваться в зависимости от теста.

Ответ 1

Если вы используете Pytest 3.0 или более позднюю версию, я думаю, что вы сможете решить этот конкретный сценарий, написав следующее:

@pytest.fixture(params=['dir1_fixture', 'dir2_fixture'])
def dirname(request):
    return request.getfixturevalue(request.param)

Документы здесь: http://doc.pytest.org/en/latest/builtin.html#_pytest.fixtures.FixtureRequest.getfixturevalue

Однако вы не можете использовать этот подход, если прибор, который вы пытаетесь загрузить динамически, параметризован.

В качестве альтернативы вы можете выяснить что-то с помощью хука pytest_generate_tests. Однако я не смог заставить себя разобраться в этом.

Ответ 3

Как сейчас, мое единственное решение - создать прибор, который возвращает словарь приборов.

import pytest
import my_package

@pytest.fixture
def dir1_fixture():
    return '/dir1'

@pytest.fixture
def dir2_fixture():
    return '/dir2'

@pytest.fixture
def dir_fixtures(
    dir1_fixture,
    dir2_fixture
    ):
    return {
        'dir1_fixture': dir1_fixture,
        'dir2_fixture': dir2_fixture
    }

@pytest.mark.parametrize('fixture_name, expected', [('dir1_fixture', 'expected1'), ('dir2_fixture', 'expected2')]
def test_directory_command(dir_fixtures, fixture_name, expected):
    dirname = dir_fixtures[fixture_name]
    result = my_package.directory_command(dirname)
    assert result == expected

Не лучший, поскольку он не использует решение, встроенное в pytest, но оно работает для меня.