Skip to content

No longer works with starlette/fastapi TestClient #165

@sscherfke

Description

@sscherfke

Follow-up of #144 (comment)


The following example works with pytest-httpx 0.26 but fails with pytest-httpx 0.30:

import fastapi
import httpx
import pytest
import pytest_asyncio
import pytest_httpx


@pytest_asyncio.fixture
async def client() -> fastapi.FastAPI:
    app = fastapi.FastAPI()

    @app.get("/")
    def get() -> None:
        return None

    async with httpx.AsyncClient(
        transport=httpx.ASGITransport(app=app),
        base_url="http://test",
    ) as api_client:
        yield api_client


@pytest.mark.asyncio
async def test_ok(client: httpx.AsyncClient) -> None:
    response = await client.get("/")
    assert response.status_code == 200


@pytest.mark.asyncio
async def test_err(
    client: httpx.AsyncClient, httpx_mock: pytest_httpx.HTTPXMock
) -> None:
    httpx_mock.add_response(status_code=500, text="Internal Server Error")
    response = await client.get("/")
    assert response.status_code == 500

httpx.ASGITransport inherits httpx.AsyncBaseTransport and pytest-httpx only mocks httpx.AsyncHTTPTransport.

I don't think it would be a good idea to mock the base transport, because its handle-Method is "abstract" and should remain so.

Maybe it should mock the asgi/wsgi transport in addition to the http transport or allow passing a list of transport classes to mock.

The Starlette test client inherts httpx.BaseTransport: https://github.com/encode/starlette/blob/master/starlette/testclient.py#L239

My current workaround is this fixture:

@pytest.fixture
def httpx_testclient_mock(monkeypatch: pytest.MonkeyPatch) -> HTTPXMock:
    # This fixture is a workaound for
    # https://github.com/Colin-b/pytest_httpx/issues/144
    mock = HTTPXMock()

    def mocked_handle_request(
        transport: httpx.HTTPTransport, request: httpx.Request
    ) -> httpx.Response:
        return mock._handle_request(transport, request)  # noqa: SLF001

    monkeypatch.setattr(
        starlette.testclient._TestClientTransport,  # noqa: SLF001
        "handle_request",
        mocked_handle_request,
    )

    return mock

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions