def test_is_generator_asyncio(pytester: Pytester) -> None: pytester.makepyfile( """ from _pytest.compat import is_generator import asyncio @asyncio.coroutine def baz(): yield from [1,2,3] def test_is_generator_asyncio(): assert not is_generator(baz) """ ) # avoid importing asyncio into pytest's own process, # which in turn imports logging (#8) result = pytester.runpytest_subprocess() result.stdout.fnmatch_lines(["*1 passed*"])
def test_fixture_values_leak(pytester: Pytester) -> None: """Ensure that fixture objects are properly destroyed by the garbage collector at the end of their expected life-times (#2981). """ pytester.makepyfile( """ import attr import gc import pytest import weakref @attr.s class SomeObj(object): name = attr.ib() fix_of_test1_ref = None session_ref = None @pytest.fixture(scope='session') def session_fix(): global session_ref obj = SomeObj(name='session-fixture') session_ref = weakref.ref(obj) return obj @pytest.fixture def fix(session_fix): global fix_of_test1_ref obj = SomeObj(name='local-fixture') fix_of_test1_ref = weakref.ref(obj) return obj def test1(fix): assert fix_of_test1_ref() is fix def test2(): gc.collect() # fixture "fix" created during test1 must have been destroyed by now assert fix_of_test1_ref() is None """ ) # Running on subprocess does not activate the HookRecorder # which holds itself a reference to objects in case of the # pytest_assert_reprcompare hook result = pytester.runpytest_subprocess() result.stdout.fnmatch_lines(["* 2 passed *"])
def test_shown_by_default(self, pytester: Pytester, customize_filters) -> None: """Show deprecation warnings by default, even if user has customized the warnings filters (#4013).""" self.create_file(pytester) if customize_filters: pytester.makeini(""" [pytest] filterwarnings = once::UserWarning """) result = pytester.runpytest_subprocess() result.stdout.fnmatch_lines([ "*== %s ==*" % WARNINGS_SUMMARY_HEADER, "*test_shown_by_default.py:3: DeprecationWarning: collection", "*test_shown_by_default.py:7: PendingDeprecationWarning: test run", "* 1 passed, 2 warnings*", ])
def test_issue4445_issue5928_mark_generator(self, pytester: Pytester) -> None: """#4445 and #5928: Make sure the warning from an unknown mark points to the test file where this mark is used. """ testfile = pytester.makepyfile(""" import pytest @pytest.mark.unknown def test_it(): pass """) result = pytester.runpytest_subprocess() # with stacklevel=2 the warning should originate from the above created test file result.stdout.fnmatch_lines_random([ f"*{testfile}:3*", "*Unknown pytest.mark.unknown*", ])
def test_as_errors(pytester: Pytester, pyfile_with_warnings, method) -> None: args = ("-W", "error") if method == "cmdline" else () if method == "ini": pytester.makeini( """ [pytest] filterwarnings=error """ ) # Use a subprocess, since changing logging level affects other threads # (xdist). result = pytester.runpytest_subprocess(*args, pyfile_with_warnings) result.stdout.fnmatch_lines( [ "E UserWarning: user warning", "as_errors_module.py:3: UserWarning", "* 1 failed in *", ] )
def test_plain_unittest_does_not_support_async(pytester: Pytester) -> None: """Async functions in plain unittest.TestCase subclasses are not supported without plugins. This test exists here to avoid introducing this support by accident, leading users to expect that it works, rather than doing so intentionally as a feature. See https://github.com/pytest-dev/pytest-asyncio/issues/180 for more context. """ pytester.copy_example("unittest/test_unittest_plain_async.py") result = pytester.runpytest_subprocess() if hasattr(sys, "pypy_version_info"): # in PyPy we can't reliable get the warning about the coroutine not being awaited, # because it depends on the coroutine being garbage collected; given that # we are running in a subprocess, that's difficult to enforce expected_lines = ["*1 passed*"] else: expected_lines = [ "*RuntimeWarning: coroutine * was never awaited", "*1 passed*", ] result.stdout.fnmatch_lines(expected_lines)
def test_cancel_scope_in_asyncgen_fixture(testdir: Pytester) -> None: testdir.makepyfile(""" import pytest from anyio import create_task_group, sleep @pytest.fixture async def asyncgen_fixture(): async with create_task_group() as tg: tg.cancel_scope.cancel() await sleep(1) yield 1 @pytest.mark.anyio async def test_cancel_in_asyncgen_fixture(asyncgen_fixture): assert asyncgen_fixture == 1 """) result = testdir.runpytest_subprocess(*pytest_args) result.assert_outcomes(passed=len(get_all_backends()))
def test_timeout(pytester: Pytester, enabled: bool) -> None: """Test option to dump tracebacks after a certain timeout. If faulthandler is disabled, no traceback will be dumped. """ pytester.makepyfile(""" import os, time def test_timeout(): time.sleep(1 if "CI" in os.environ else 0.1) """) pytester.makeini(""" [pytest] faulthandler_timeout = 0.01 """) args = ["-p", "no:faulthandler"] if not enabled else [] result = pytester.runpytest_subprocess(*args) tb_output = "most recent call first" if enabled: result.stderr.fnmatch_lines(["*%s*" % tb_output]) else: assert tb_output not in result.stderr.str() result.stdout.fnmatch_lines(["*1 passed*"]) assert result.ret == 0
def test_tee_stdio_captures_and_live_prints(pytester: Pytester) -> None: testpath = pytester.makepyfile(""" import sys def test_simple(): print ("@this is stdout@") print ("@this is stderr@", file=sys.stderr) """) result = pytester.runpytest_subprocess( testpath, "--capture=tee-sys", "--junitxml=output.xml", "-o", "junit_logging=all", ) # ensure stdout/stderr were 'live printed' result.stdout.fnmatch_lines(["*@this is stdout@*"]) result.stderr.fnmatch_lines(["*@this is stderr@*"]) # now ensure the output is in the junitxml with open(pytester.path.joinpath("output.xml")) as f: fullXml = f.read() assert "@this is stdout@\n" in fullXml assert "@this is stderr@\n" in fullXml
def test_pdb_can_be_rewritten(pytester: Pytester) -> None: pytester.makepyfile( **{ "conftest.py": """ import pytest pytest.register_assert_rewrite("pdb") """, "__init__.py": "", "pdb.py": """ def check(): assert 1 == 2 """, "test_pdb.py": """ def test(): import pdb assert pdb.check() """, }) # Disable debugging plugin itself to avoid: # > INTERNALERROR> AttributeError: module 'pdb' has no attribute 'set_trace' result = pytester.runpytest_subprocess("-p", "no:debugging", "-vv") result.stdout.fnmatch_lines([ " def check():", "> assert 1 == 2", "E assert 1 == 2", "E +1", "E -2", "", "pdb.py:2: AssertionError", "*= 1 failed in *", ]) assert result.ret == 1
def test_environ_custom_class(self, pytester: Pytester, custom_debugger_hook, arg: str) -> None: pytester.makeconftest(""" import os import sys os.environ['PYTHONBREAKPOINT'] = '_pytest._CustomDebugger.set_trace' def pytest_configure(config): config.add_cleanup(check_restored) def check_restored(): assert sys.breakpointhook == sys.__breakpointhook__ def test_check(): import _pytest assert sys.breakpointhook is _pytest._CustomDebugger.set_trace """) pytester.makepyfile(""" def test_nothing(): pass """) args = (arg, ) if arg else () result = pytester.runpytest_subprocess(*args) result.stdout.fnmatch_lines(["*1 passed in *"])
def test_pytester_run_no_timeout(pytester: Pytester) -> None: testfile = pytester.makepyfile("def test_no_timeout(): pass") assert pytester.runpytest_subprocess(testfile).ret == ExitCode.OK
def test_pytester_subprocess(pytester: Pytester) -> None: testfile = pytester.makepyfile("def test_one(): pass") assert pytester.runpytest_subprocess(testfile).ret == 0
def test_hidden_by_system(self, pytester: Pytester, monkeypatch) -> None: self.create_file(pytester) monkeypatch.setenv("PYTHONWARNINGS", "once::UserWarning") result = pytester.runpytest_subprocess() assert WARNINGS_SUMMARY_HEADER not in result.stdout.str()
def test_debug(pytester: Pytester) -> None: result = pytester.runpytest_subprocess("--debug") assert result.ret == ExitCode.NO_TESTS_COLLECTED p = pytester.path.joinpath("pytestdebug.log") assert "pytest_sessionstart" in p.read_text("utf-8")
def test_PYTEST_DEBUG(pytester: Pytester, monkeypatch) -> None: monkeypatch.setenv("PYTEST_DEBUG", "1") result = pytester.runpytest_subprocess() assert result.ret == ExitCode.NO_TESTS_COLLECTED result.stderr.fnmatch_lines( ["*pytest_plugin_registered*", "*manager*PluginManager*"])