Skip to content

Parametrization with Variables Unexpectedly Changes Fixture Scope from Class-Level to Function-Level #12146

@yogendrasinghx

Description

@yogendrasinghx

I have a setup fixture that I've parameterized with class-level scope. When I directly specify the argument values as [("chrome", "windows", "latest")], it works fine, maintaining the class-level scope. However, when I try to use variables to set these argument values, I've noticed that the scope unexpectedly shifts to function-level.

tests/test_app.py

import pytest


@pytest.mark.usefixtures("setup")
class TestSmoke:
    def test_1(self):
        assert True

    def test_2(self):
        assert True

Scenario 1 with hardcoded values

tests/conftest.py

import pytest

def pytest_generate_tests(metafunc):
    if 'setup' in metafunc.fixturenames:
        metafunc.parametrize("setup",argvalues=[("chrome", "windows", "latest")], indirect=True, scope='class')


@pytest.fixture
def setup(request):
    print(f"\nSetting up")
    print(f"Param {request.param}")
    print(f"fixture (scope={request.scope})")

    yield
    print(f"\nTearing down")

Output

python -m pytest -s -v -k "TestSmoke" tests
======================================================================================================= test session starts =======================================================================================================
platform darwin -- Python 3.12.2, pytest-8.1.1, pluggy-1.4.0 -- /Volumes/T7/mywork/pythonProject/dynamic_parameter/venv/bin/python
cachedir: .pytest_cache
rootdir: /Volumes/T7/mywork/pythonProject/dynamic_parameter
collected 2 items                                                                                                                                                                                                                 

tests/test_app.py::TestSmoke::test_1[setup0] 
Setting up
Param ('chrome', 'windows', 'latest')
fixture (scope=class)
PASSED
tests/test_app.py::TestSmoke::test_2[setup0] PASSED
Tearing down

Scenario 2 with variable values

tests/conftest.py

import pytest


def pytest_generate_tests(metafunc):
    browser_name = "chrome"
    os_name = "windows"
    browser_version = "latest"

    if 'setup' in metafunc.fixturenames:
        metafunc.parametrize("setup", argvalues=[(os_name, browser_name, browser_version)], indirect=True, scope='class')


@pytest.fixture
def setup(request):
    print(f"\nSetting up")
    print(f"Param {request.param}")
    yield
    print(f"\nTearing down")

Output

python -m pytest -s -v -k "TestSmoke" tests
======================================================================================================= test session starts =======================================================================================================
platform darwin -- Python 3.12.2, pytest-7.4.4, pluggy-1.4.0 -- /Volumes/T7/mywork/pythonProject/dynamic_parameter/venv/bin/python
cachedir: .pytest_cache
rootdir: /Volumes/T7/mywork/pythonProject/dynamic_parameter
collected 2 items                                                                                                                                                                                                                 

tests/test_app.py::TestSmoke::test_1[setup0] 
Setting up
Param ('windows', 'chrome', 'latest')
PASSED
tests/test_app.py::TestSmoke::test_2[setup0] 
Tearing down

Setting up
Param ('windows', 'chrome', 'latest')
PASSED
Tearing down
(venv) yogen@Mac-mini dynamic_parameter % pip list
Package        Version
-------------- -------
attrs          23.2.0
iniconfig      2.0.0
more-itertools 10.2.0
packaging      24.0
pip            24.0
pluggy         1.4.0
py             1.11.0
pytest         8.1.1
toml           0.10.2
wcwidth        0.2.13

Metadata

Metadata

Assignees

No one assigned

    Labels

    topic: fixturesanything involving fixtures directly or indirectlytype: bugproblem that needs to be addressed

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions