legacypath: only add `testdir` and `tmpdir` fixtures if corresponding plugins are registered

This preserves the existing behavior and gives a proper error message
in case e.g. `testdir` is requested without the `pytester` plugin being
loaded.
This commit is contained in:
Ran Benita 2021-10-29 13:11:12 +03:00
parent c3dff755af
commit e6eac28f0e
2 changed files with 51 additions and 41 deletions

View File

@ -638,7 +638,7 @@ tmpdir
:ref:`tmpdir and tmpdir_factory` :ref:`tmpdir and tmpdir_factory`
.. autofunction:: _pytest.legacypath.tmpdir() .. autofunction:: _pytest.legacypath.LegacyTmpdirPlugin.tmpdir()
:no-auto-options: :no-auto-options:

View File

@ -248,8 +248,10 @@ class Testdir:
pytest.Testdir = Testdir # type: ignore[attr-defined] pytest.Testdir = Testdir # type: ignore[attr-defined]
@pytest.fixture class LegacyTestdirPlugin:
def testdir(pytester: pytest.Pytester) -> Testdir: @staticmethod
@pytest.fixture
def testdir(pytester: pytest.Pytester) -> Testdir:
""" """
Identical to :fixture:`pytester`, and provides an instance whose methods return Identical to :fixture:`pytester`, and provides an instance whose methods return
legacy ``LEGACY_PATH`` objects instead when applicable. legacy ``LEGACY_PATH`` objects instead when applicable.
@ -285,15 +287,17 @@ class TempdirFactory:
pytest.TempdirFactory = TempdirFactory # type: ignore[attr-defined] pytest.TempdirFactory = TempdirFactory # type: ignore[attr-defined]
@pytest.fixture(scope="session") class LegacyTmpdirPlugin:
def tmpdir_factory(request: pytest.FixtureRequest) -> TempdirFactory: @staticmethod
@pytest.fixture(scope="session")
def tmpdir_factory(request: pytest.FixtureRequest) -> TempdirFactory:
"""Return a :class:`pytest.TempdirFactory` instance for the test session.""" """Return a :class:`pytest.TempdirFactory` instance for the test session."""
# Set dynamically by pytest_configure(). # Set dynamically by pytest_configure().
return request.config._tmpdirhandler # type: ignore return request.config._tmpdirhandler # type: ignore
@staticmethod
@pytest.fixture @pytest.fixture
def tmpdir(tmp_path: Path) -> LEGACY_PATH: def tmpdir(tmp_path: Path) -> LEGACY_PATH:
"""Return a temporary directory path object which is unique to each test """Return a temporary directory path object which is unique to each test
function invocation, created as a sub directory of the base temporary function invocation, created as a sub directory of the base temporary
directory. directory.
@ -400,6 +404,10 @@ def pytest_configure(config: pytest.Config) -> None:
mp = pytest.MonkeyPatch() mp = pytest.MonkeyPatch()
config.add_cleanup(mp.undo) config.add_cleanup(mp.undo)
if config.pluginmanager.has_plugin("pytester"):
config.pluginmanager.register(LegacyTestdirPlugin, "legacypath-pytester")
if config.pluginmanager.has_plugin("tmpdir"):
# Create TmpdirFactory and attach it to the config object. # Create TmpdirFactory and attach it to the config object.
# #
# This is to comply with existing plugins which expect the handler to be # This is to comply with existing plugins which expect the handler to be
@ -414,6 +422,8 @@ def pytest_configure(config: pytest.Config) -> None:
_tmpdirhandler = TempdirFactory(tmp_path_factory, _ispytest=True) _tmpdirhandler = TempdirFactory(tmp_path_factory, _ispytest=True)
mp.setattr(config, "_tmpdirhandler", _tmpdirhandler, raising=False) mp.setattr(config, "_tmpdirhandler", _tmpdirhandler, raising=False)
config.pluginmanager.register(LegacyTmpdirPlugin, "legacypath-tmpdir")
# Add Cache.makedir(). # Add Cache.makedir().
mp.setattr(pytest.Cache, "makedir", Cache_makedir, raising=False) mp.setattr(pytest.Cache, "makedir", Cache_makedir, raising=False)