From: Tom Christie Date: Fri, 13 Aug 2021 14:17:15 +0000 (+0100) Subject: Stricter enforcement of either 'with httpx.Client() as client' or 'client = httpx... X-Git-Tag: 0.19.0~3 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=927c88d34f73d98af5827aaa571e74d6159e5735;p=thirdparty%2Fhttpx.git Stricter enforcement of either 'with httpx.Client() as client' or 'client = httpx.Client()' lifespan styles. (#1800) --- diff --git a/httpx/_client.py b/httpx/_client.py index 9fd96c49..212222a2 100644 --- a/httpx/_client.py +++ b/httpx/_client.py @@ -1232,6 +1232,13 @@ class Client(BaseClient): transport.close() def __enter__(self: T) -> T: + if self._state != ClientState.UNOPENED: + msg = { + ClientState.OPENED: "Cannot open a client instance more than once.", + ClientState.CLOSED: "Cannot reopen a client instance, once it has been closed.", + }[self._state] + raise RuntimeError(msg) + self._state = ClientState.OPENED self._transport.__enter__() @@ -1941,6 +1948,13 @@ class AsyncClient(BaseClient): await proxy.aclose() async def __aenter__(self: U) -> U: + if self._state != ClientState.UNOPENED: + msg = { + ClientState.OPENED: "Cannot open a client instance more than once.", + ClientState.CLOSED: "Cannot reopen a client instance, once it has been closed.", + }[self._state] + raise RuntimeError(msg) + self._state = ClientState.OPENED await self._transport.__aenter__() diff --git a/tests/client/test_async_client.py b/tests/client/test_async_client.py index 0f83eddd..17612874 100644 --- a/tests/client/test_async_client.py +++ b/tests/client/test_async_client.py @@ -265,9 +265,15 @@ async def test_client_closed_state_using_implicit_open(): await client.aclose() assert client.is_closed + # Once we're close we cannot make any more requests. with pytest.raises(RuntimeError): await client.get("http://example.com") + # Once we're closed we cannot reopen the client. + with pytest.raises(RuntimeError): + async with client: + pass # pragma: nocover + @pytest.mark.usefixtures("async_environment") async def test_client_closed_state_using_with_block(): diff --git a/tests/client/test_client.py b/tests/client/test_client.py index 01d0de82..783d6d41 100644 --- a/tests/client/test_client.py +++ b/tests/client/test_client.py @@ -305,9 +305,16 @@ def test_client_closed_state_using_implicit_open(): client.close() assert client.is_closed + + # Once we're close we cannot make any more requests. with pytest.raises(RuntimeError): client.get("http://example.com") + # Once we're closed we cannot reopen the client. + with pytest.raises(RuntimeError): + with client: + pass # pragma: nocover + def test_client_closed_state_using_with_block(): with httpx.Client(transport=httpx.MockTransport(hello_world)) as client: