Skip to content
1 change: 1 addition & 0 deletions CHANGES/10851.bugfix.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Fix pytest plugin to not use deprecated asyncio policy APIs.
1 change: 1 addition & 0 deletions CHANGES/10851.misc.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Update tests to avoid using deprecated asyncio policy APIs.
27 changes: 14 additions & 13 deletions aiohttp/pytest_plugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -224,9 +224,13 @@ def pytest_pyfunc_call(pyfuncitem): # type: ignore[no-untyped-def]
"""Run coroutines in an event loop instead of a normal function call."""
fast = pyfuncitem.config.getoption("--aiohttp-fast")
if inspect.iscoroutinefunction(pyfuncitem.function):
existing_loop = pyfuncitem.funcargs.get(
"proactor_loop"
) or pyfuncitem.funcargs.get("loop", None)
existing_loop = (
pyfuncitem.funcargs.get("proactor_loop")
or pyfuncitem.funcargs.get("selector_loop")
or pyfuncitem.funcargs.get("uvloop_loop")
or pyfuncitem.funcargs.get("loop", None)
)

with _runtime_warning_context():
with _passthrough_loop_context(existing_loop, fast=fast) as _loop:
testargs = {
Expand All @@ -243,11 +247,11 @@ def pytest_generate_tests(metafunc): # type: ignore[no-untyped-def]
return

loops = metafunc.config.option.aiohttp_loop
avail_factories: Dict[str, Type[asyncio.AbstractEventLoopPolicy]]
avail_factories = {"pyloop": asyncio.DefaultEventLoopPolicy}
avail_factories: dict[str, Callable[[], asyncio.AbstractEventLoop]]
avail_factories = {"pyloop": asyncio.new_event_loop}

if uvloop is not None:
avail_factories["uvloop"] = uvloop.EventLoopPolicy
avail_factories["uvloop"] = uvloop.new_event_loop

if loops == "all":
loops = "pyloop,uvloop?"
Expand All @@ -272,14 +276,12 @@ def pytest_generate_tests(metafunc): # type: ignore[no-untyped-def]

@pytest.fixture
def loop(
loop_factory: Callable[[], asyncio.AbstractEventLoopPolicy],
loop_factory: Callable[[], asyncio.AbstractEventLoop],
fast: bool,
loop_debug: bool,
) -> Iterator[asyncio.AbstractEventLoop]:
"""Return an instance of the event loop."""
policy = loop_factory()
asyncio.set_event_loop_policy(policy)
with loop_context(fast=fast) as _loop:
with loop_context(loop_factory, fast=fast) as _loop:
if loop_debug:
_loop.set_debug(True)
asyncio.set_event_loop(_loop)
Expand All @@ -288,10 +290,9 @@ def loop(

@pytest.fixture
def proactor_loop() -> Iterator[asyncio.AbstractEventLoop]:
policy = asyncio.WindowsProactorEventLoopPolicy() # type: ignore[attr-defined]
asyncio.set_event_loop_policy(policy)
factory = asyncio.ProactorEventLoop # type: ignore[attr-defined]

with loop_context(policy.new_event_loop) as _loop:
with loop_context(factory) as _loop:
asyncio.set_event_loop(_loop)
yield _loop

Expand Down
12 changes: 4 additions & 8 deletions tests/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -233,20 +233,16 @@ def assert_sock_fits(sock_path: str) -> None:

@pytest.fixture
def selector_loop() -> Iterator[asyncio.AbstractEventLoop]:
policy = asyncio.WindowsSelectorEventLoopPolicy() # type: ignore[attr-defined]
asyncio.set_event_loop_policy(policy)

with loop_context(policy.new_event_loop) as _loop:
factory = asyncio.SelectorEventLoop
with loop_context(factory) as _loop:
asyncio.set_event_loop(_loop)
yield _loop


@pytest.fixture
def uvloop_loop() -> Iterator[asyncio.AbstractEventLoop]:
policy = uvloop.EventLoopPolicy()
asyncio.set_event_loop_policy(policy)

with loop_context(policy.new_event_loop) as _loop:
factory = uvloop.new_event_loop
with loop_context(factory) as _loop:
asyncio.set_event_loop(_loop)
yield _loop

Expand Down
2 changes: 1 addition & 1 deletion tests/test_connector.py
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ def create_mocked_conn(
try:
loop = asyncio.get_running_loop()
except RuntimeError:
loop = asyncio.get_event_loop_policy().get_event_loop()
loop = asyncio.get_event_loop()

f = loop.create_future()
proto: mock.Mock = mock.create_autospec(
Expand Down
4 changes: 2 additions & 2 deletions tests/test_loop.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ async def test_on_startup_hook(self) -> None:


def test_default_loop(loop: asyncio.AbstractEventLoop) -> None:
assert asyncio.get_event_loop_policy().get_event_loop() is loop
assert asyncio.get_event_loop() is loop


def test_setup_loop_non_main_thread() -> None:
Expand All @@ -46,7 +46,7 @@ def test_setup_loop_non_main_thread() -> None:
def target() -> None:
try:
with loop_context() as loop:
assert asyncio.get_event_loop_policy().get_event_loop() is loop
assert asyncio.get_event_loop() is loop
loop.run_until_complete(test_subprocess_co(loop))
except Exception as exc:
nonlocal child_exc
Expand Down
2 changes: 1 addition & 1 deletion tests/test_proxy_functional.py
Original file line number Diff line number Diff line change
Expand Up @@ -241,7 +241,6 @@ async def test_https_proxy_unsupported_tls_in_tls(
await asyncio.sleep(0.1)


@pytest.mark.usefixtures("uvloop_loop")
@pytest.mark.skipif(
platform.system() == "Windows" or sys.implementation.name != "cpython",
reason="uvloop is not supported on Windows and non-CPython implementations",
Expand All @@ -253,6 +252,7 @@ async def test_https_proxy_unsupported_tls_in_tls(
async def test_uvloop_secure_https_proxy(
client_ssl_ctx: ssl.SSLContext,
secure_proxy_url: URL,
uvloop_loop: asyncio.AbstractEventLoop,
) -> None:
"""Ensure HTTPS sites are accessible through a secure proxy without warning when using uvloop."""
conn = aiohttp.TCPConnector()
Expand Down
Loading