Skip to content

Commit 216ec3c

Browse files
committed
Remove PytestReturnNotNoneWarning and PytestUnhandledCoroutineWarning. Make tests fail instead of raising warning/exception. fix tests. add changelog.
1 parent 45c2ffb commit 216ec3c

File tree

6 files changed

+28
-59
lines changed

6 files changed

+28
-59
lines changed

src/_pytest/config/exceptions.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
from __future__ import annotations
22

3+
from typing import final
34

5+
6+
@final
47
class UsageError(Exception):
58
"""Error in pytest usage or invocation."""
69

src/_pytest/python.py

Lines changed: 17 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,6 @@
5151
from _pytest.config import Config
5252
from _pytest.config import hookimpl
5353
from _pytest.config.argparsing import Parser
54-
from _pytest.config.exceptions import UsageError
5554
from _pytest.deprecated import check_ispytest
5655
from _pytest.fixtures import FixtureDef
5756
from _pytest.fixtures import FixtureRequest
@@ -74,7 +73,6 @@
7473
from _pytest.scope import Scope
7574
from _pytest.stash import StashKey
7675
from _pytest.warning_types import PytestCollectionWarning
77-
from _pytest.warning_types import PytestReturnNotNoneWarning
7876

7977

8078
if TYPE_CHECKING:
@@ -135,48 +133,36 @@ def pytest_configure(config: Config) -> None:
135133
)
136134

137135

138-
@final
139-
class PytestUnhandledCoroutineError(UsageError):
140-
"""An unraisable exception resulted in an error.
141-
142-
Unraisable exceptions are exceptions raised in :meth:`__del__ <object.__del__>`
143-
implementations and similar situations when the exception cannot be raised
144-
as normal.
145-
"""
146-
147-
148-
def async_warn_and_skip(nodeid: str) -> None:
149-
msg = "async def functions are not natively supported and have been skipped.\n"
150-
msg += (
136+
def async_fail(nodeid: str) -> None:
137+
msg = (
138+
"async def functions are not natively supported.\n"
151139
"You need to install a suitable plugin for your async framework, for example:\n"
140+
" - anyio\n"
141+
" - pytest-asyncio\n"
142+
" - pytest-tornasync\n"
143+
" - pytest-trio\n"
144+
" - pytest-twisted"
152145
)
153-
msg += " - anyio\n"
154-
msg += " - pytest-asyncio\n"
155-
msg += " - pytest-tornasync\n"
156-
msg += " - pytest-trio\n"
157-
msg += " - pytest-twisted"
158-
raise PytestUnhandledCoroutineError(
159-
msg.format(nodeid)
160-
) # TODO: This is the warning to look at
161-
skip(reason="async def function and no async plugin installed (see warnings)")
146+
fail(msg, pytrace=False)
162147

163148

164149
@hookimpl(trylast=True)
165150
def pytest_pyfunc_call(pyfuncitem: Function) -> object | None:
166151
testfunction = pyfuncitem.obj
167152
if is_async_function(testfunction):
168-
async_warn_and_skip(pyfuncitem.nodeid)
153+
async_fail(pyfuncitem.nodeid)
169154
funcargs = pyfuncitem.funcargs
170155
testargs = {arg: funcargs[arg] for arg in pyfuncitem._fixtureinfo.argnames}
171156
result = testfunction(**testargs)
172157
if hasattr(result, "__await__") or hasattr(result, "__aiter__"):
173-
async_warn_and_skip(pyfuncitem.nodeid)
158+
async_fail(pyfuncitem.nodeid)
174159
elif result is not None:
175-
warnings.warn(
176-
PytestReturnNotNoneWarning(
177-
f"Expected None, but {pyfuncitem.nodeid} returned {result!r}, which will be an error in a "
178-
"future version of pytest. Did you mean to use `assert` instead of `return`?"
179-
)
160+
fail(
161+
(
162+
f"Expected None, but test returned {result!r}. "
163+
"Did you mean to use `assert` instead of `return`?"
164+
),
165+
pytrace=False,
180166
)
181167
return True
182168

src/_pytest/warning_types.py

Lines changed: 0 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -56,12 +56,6 @@ class PytestRemovedIn9Warning(PytestDeprecationWarning):
5656
__module__ = "pytest"
5757

5858

59-
class PytestReturnNotNoneWarning(PytestWarning):
60-
"""Warning emitted when a test function is returning value other than None."""
61-
62-
__module__ = "pytest"
63-
64-
6559
@final
6660
class PytestExperimentalApiWarning(PytestWarning, FutureWarning):
6761
"""Warning category used to denote experiments in pytest.
@@ -77,18 +71,6 @@ def simple(cls, apiname: str) -> PytestExperimentalApiWarning:
7771
return cls(f"{apiname} is an experimental api that may change over time")
7872

7973

80-
@final
81-
class PytestUnhandledCoroutineWarning(PytestReturnNotNoneWarning): # TODO: look at this
82-
"""Warning emitted for an unhandled coroutine.
83-
84-
A coroutine was encountered when collecting test functions, but was not
85-
handled by any async-aware plugin.
86-
Coroutine test functions are not natively supported.
87-
"""
88-
89-
__module__ = "pytest"
90-
91-
9274
@final
9375
class PytestUnknownMarkWarning(PytestWarning):
9476
"""Warning emitted on use of unknown markers.

src/pytest/__init__.py

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -78,8 +78,6 @@
7878
from _pytest.warning_types import PytestDeprecationWarning
7979
from _pytest.warning_types import PytestExperimentalApiWarning
8080
from _pytest.warning_types import PytestRemovedIn9Warning
81-
from _pytest.warning_types import PytestReturnNotNoneWarning
82-
from _pytest.warning_types import PytestUnhandledCoroutineWarning
8381
from _pytest.warning_types import PytestUnhandledThreadExceptionWarning
8482
from _pytest.warning_types import PytestUnknownMarkWarning
8583
from _pytest.warning_types import PytestUnraisableExceptionWarning
@@ -142,10 +140,8 @@
142140
"PytestDeprecationWarning",
143141
"PytestExperimentalApiWarning",
144142
"PytestRemovedIn9Warning",
145-
"PytestReturnNotNoneWarning",
146143
"Pytester",
147144
"PytestPluginManager",
148-
"PytestUnhandledCoroutineWarning",
149145
"PytestUnhandledThreadExceptionWarning",
150146
"PytestUnknownMarkWarning",
151147
"PytestUnraisableExceptionWarning",

testing/acceptance_test.py

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1235,7 +1235,7 @@ def test_usage_error_code(pytester: Pytester) -> None:
12351235
assert result.ret == ExitCode.USAGE_ERROR
12361236

12371237

1238-
def test_error_on_async_function(pytester: Pytester) -> None: # TODO: Change this
1238+
def test_error_on_async_function(pytester: Pytester) -> None:
12391239
# In the below we .close() the coroutine only to avoid
12401240
# "RuntimeWarning: coroutine 'test_2' was never awaited"
12411241
# which messes with other tests.
@@ -1254,16 +1254,16 @@ def test_3():
12541254
result = pytester.runpytest()
12551255
result.stdout.fnmatch_lines(
12561256
[
1257+
"*async def functions are not natively supported*",
12571258
"*test_async.py::test_1*",
12581259
"*test_async.py::test_2*",
12591260
"*test_async.py::test_3*",
1260-
"*async def functions are not natively supported*",
12611261
]
12621262
)
12631263
result.assert_outcomes(failed=3)
12641264

12651265

1266-
def test_error_on_async_gen_function(pytester: Pytester) -> None: # TODO: Change this
1266+
def test_error_on_async_gen_function(pytester: Pytester) -> None:
12671267
pytester.makepyfile(
12681268
test_async="""
12691269
async def test_1():
@@ -1277,12 +1277,13 @@ def test_3():
12771277
result = pytester.runpytest()
12781278
result.stdout.fnmatch_lines(
12791279
[
1280+
"*async def functions are not natively supported*",
12801281
"*test_async.py::test_1*",
12811282
"*test_async.py::test_2*",
12821283
"*test_async.py::test_3*",
1283-
"*async def functions are not natively supported*",
12841284
]
12851285
)
1286+
result.assert_outcomes(failed=3)
12861287

12871288

12881289
def test_pdb_can_be_rewritten(pytester: Pytester) -> None:
@@ -1368,14 +1369,15 @@ def test_no_brokenpipeerror_message(pytester: Pytester) -> None:
13681369
popen.stderr.close()
13691370

13701371

1371-
def test_function_return_non_none_warning(pytester: Pytester) -> None:
1372+
def test_function_return_non_none_error(pytester: Pytester) -> None:
13721373
pytester.makepyfile(
13731374
"""
13741375
def test_stuff():
13751376
return "something"
13761377
"""
13771378
)
13781379
res = pytester.runpytest()
1380+
res.assert_outcomes(failed=1)
13791381
res.stdout.fnmatch_lines(["*Did you mean to use `assert` instead of `return`?*"])
13801382

13811383

testing/test_unittest.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1314,7 +1314,7 @@ def test_1(self):
13141314
assert tracked == []
13151315

13161316

1317-
def test_async_support(pytester: Pytester) -> None: # TODO: Change this
1317+
def test_async_support(pytester: Pytester) -> None:
13181318
pytest.importorskip("unittest.async_case")
13191319

13201320
pytester.copy_example("unittest/test_unittest_asyncio.py")

0 commit comments

Comments
 (0)