Can params passed to pytest fixture be passed in as a variable?

10,830

Solution 1

If i understand your question correctly, you basically want to select one instance of a parametrized fixture for executing with a test, by providing some info with the test. It's not possible although we could probably think about a mechanism. I am not sure if the following solution maps to your whole problem, but here is one way to solve the above concrete case:

import pytest

@pytest.fixture(scope="module")
def myFixture1():
    return 5

@pytest.fixture(scope="module")
def myFixture2():
    return 2

@pytest.fixture(scope="module", params=["param1", "param2"])
def myFixture(request):
    if request.param == 'param1':
        return request.getfuncargvalue("myFixture1")
    elif request.param == 'param2':
        return request.getfuncargvalue("myFixture2")

def test_1(myFixture1):
    assert myFixture1 == 5

def test_2(myFixture2):
    assert myFixture2 == 2

def test_all(myFixture):
    assert myFixture in (2,5)

This runs four tests, because the test_all is executed twice with both fixtures.

If the setup of your fixtures is not heavy, you might also have one fixture that produces a list and an "iterating" parametrized one. A test could then grab the whole list and index it into it.

Solution 2

Not sure if this is what you want, but the example case can be implemented like:

@pytest.mark.parametrize(('param', 'expected'), [('param1', 5), ('param2', 10)])
def test_madeup(param, expected):
    assert param == expected
Share:
10,830
jasmine
Author by

jasmine

Updated on July 17, 2022

Comments

  • jasmine
    jasmine almost 2 years

    I have two simple test setups and I'm trying to group them in one fixture and want the test function to pass in the 'params' to the fixture.

    Here's a contrived example, to explain my question. Say I have the following pytest fixture:

    @pytest.fixture(scope="module", params=['param1','param2'])
    def myFixture(request):
        if request.param == 'param1':
            p = 5
        elif request.param == 'param2':
            p = 10
        return p
    
    # would like to set request.param = ['param1'] for myFixture
    def test_madeup(myFixture):
        assert myFixture == 5
    
    # would like to set request.param = ['param2'] for myFixture
    def test_madeup2(myFixture):
        assert myFixture == 10
    

    Can I make it so that the params above are passed in as an input to the test_madeup function? So, something like the following:

    @pytest.fixture(scope="module", params=fixtureParams)
    def myFixture(request):
        if request.param == 'param1':
            return 5
        elif request.param == 'param2':
            return 10
    
    
    def test_madeup(myFixture, ['param1']):
        assert myFixture == 5
    

    The above, of course, doesn't work. The real case is a bit more complex, but I just want to know if I can pass the params=['param1','param2'] to the fixture from the test_madeup function.