From 6d8562d8420b3e464877b941e04663fdac29a54c Mon Sep 17 00:00:00 2001 From: Shubh Agarwal Date: Mon, 7 Oct 2024 01:47:33 +0530 Subject: [PATCH] Disabling retry_persistent_connection in Tests (#9396) --- CHANGES/9141.misc.rst | 2 ++ CONTRIBUTORS.txt | 1 + aiohttp/client.py | 6 +++++- aiohttp/test_utils.py | 1 + tests/test_test_utils.py | 22 ++++++++++++++++++++++ 5 files changed, 31 insertions(+), 1 deletion(-) create mode 100644 CHANGES/9141.misc.rst diff --git a/CHANGES/9141.misc.rst b/CHANGES/9141.misc.rst new file mode 100644 index 00000000000..d23439fa742 --- /dev/null +++ b/CHANGES/9141.misc.rst @@ -0,0 +1,2 @@ +Disabled automatic retries of failed requests in :class:`aiohttp.test_utils.TestClient`'s client session +(which could potentially hide errors in tests) -- by :user:`ShubhAgarwal-dev`. diff --git a/CONTRIBUTORS.txt b/CONTRIBUTORS.txt index e18aad14f64..c97977fe8ae 100644 --- a/CONTRIBUTORS.txt +++ b/CONTRIBUTORS.txt @@ -309,6 +309,7 @@ Sergey Skripnick Serhii Charykov Serhii Kostel Serhiy Storchaka +Shubh Agarwal Simon Kennedy Sin-Woo Bang Stanislas Plum diff --git a/aiohttp/client.py b/aiohttp/client.py index 82cbce19d8d..8fce18b1a18 100644 --- a/aiohttp/client.py +++ b/aiohttp/client.py @@ -254,6 +254,7 @@ class ClientSession: "_resolve_charset", "_default_proxy", "_default_proxy_auth", + "_retry_connection", ) def __init__( @@ -367,6 +368,7 @@ def __init__( self._default_proxy = proxy self._default_proxy_auth = proxy_auth + self._retry_connection: bool = True def __init_subclass__(cls: Type["ClientSession"]) -> None: raise TypeError( @@ -539,7 +541,9 @@ async def _request( try: with timer: # https://www.rfc-editor.org/rfc/rfc9112.html#name-retrying-requests - retry_persistent_connection = method in IDEMPOTENT_METHODS + retry_persistent_connection = ( + self._retry_connection and method in IDEMPOTENT_METHODS + ) while True: url, auth_from_url = strip_auth_from_url(url) if not url.raw_host: diff --git a/aiohttp/test_utils.py b/aiohttp/test_utils.py index 88dcf8ebf1b..eb40ab2f4d7 100644 --- a/aiohttp/test_utils.py +++ b/aiohttp/test_utils.py @@ -294,6 +294,7 @@ def __init__( # type: ignore[misc] if cookie_jar is None: cookie_jar = aiohttp.CookieJar(unsafe=True) self._session = ClientSession(cookie_jar=cookie_jar, **kwargs) + self._session._retry_connection = False self._closed = False self._responses: List[ClientResponse] = [] self._websockets: List[ClientWebSocketResponse] = [] diff --git a/tests/test_test_utils.py b/tests/test_test_utils.py index 718b95b6512..e1145f81d53 100644 --- a/tests/test_test_utils.py +++ b/tests/test_test_utils.py @@ -11,6 +11,7 @@ import aiohttp from aiohttp import web +from aiohttp.pytest_plugin import AiohttpClient from aiohttp.test_utils import ( AioHTTPTestCase, RawTestServer, @@ -316,6 +317,27 @@ def test_noop(self) -> None: result.stdout.fnmatch_lines(["*TypeError*"]) +async def test_disable_retry_persistent_connection( + aiohttp_client: AiohttpClient, +) -> None: + num_requests = 0 + + async def handler(request: web.Request) -> web.Response: + nonlocal num_requests + + num_requests += 1 + request.protocol.force_close() + return web.Response() + + app = web.Application() + app.router.add_get("/", handler) + client = await aiohttp_client(app) + with pytest.raises(aiohttp.ServerDisconnectedError): + await client.get("/") + + assert num_requests == 1 + + async def test_server_context_manager( app: web.Application, loop: asyncio.AbstractEventLoop ) -> None: