I want to test a function get_xyz(a, b, foo)
, where foo is a class. A foo_fixture
is defined in a conftest.py like so:
@pytest.fixture()
def foo_fixture():
return Foo()
The fixture simply returns a new instance of a class Foo. How would I parametrize this foo_fixture as an argument to test_get_xyz
? I have tried the below code but it doesn't work, also have read about using indirect=True in the parametrize decorator but also couldn't get that to work properly...
@pytest.mark.parametrize("a,b,foo_fixture",
[1, 2, pytest.lazy_fixture('foo_fixture')]
)
def test_get_xyz(a, b, foo_fixture):
get_xyz(a, b, foo_fixture)
Here is implementation with indirect parametrize:
import pytest
class Foo:
pass
@pytest.fixture
def foo_fixture():
return Foo()
@pytest.mark.parametrize(
"a, b, foo_fixture",
[
(1, 2, None),
(3, 4, None),
(5, 6, None),
],
indirect=["foo_fixture"]
)
def test_get_xyz(a, b, foo_fixture):
print("\n", a, b, foo_fixture)
Output is:
PASSED [ 33%]
1 2 <test_indirect.Foo object at 0x000002318A4084C0>
PASSED [ 66%]
3 4 <test_indirect.Foo object at 0x000002318A408610>
PASSED [100%]
5 6 <test_indirect.Foo object at 0x000002318A4086A0>
As you can see Foo is different instance in each test.
Read more about indirect parametrize.
Basically you just specify which of your parameters are fixtures and pass any value for it (None
for example).
If you need to change something in fixture based on passed parameters then you will need to pass some value instead of None
and grab it inside foo_fixture
using request
fixture like this:
@pytest.fixture
def foo_fixture(request):
return Foo(request.param)