HHead26
HHead26

Reputation: 69

How to mock external requests using aiohttp?

I'm trying to mock a single request to an external URL but in the documentation exists just examples to internal request (starting with '/'), it's impossible to add routers who not start with '/' on the current version of aiohttp. I'm using pytest and pytest-aiohttp, here are an example of the request code:

import aiohttp
import asyncio

async def fetch(client):
   async with client.get('http://python.org') as resp:
       return resp.status, (await resp.text())

async def main():
   async with aiohttp.ClientSession() as client:
       html = await fetch(client)
       print(html)

loop = asyncio.get_event_loop()
loop.run_until_complete(main())

The kind of assertion that I want to do is very simple, like check the status code, the headers, and the content.

Upvotes: 2

Views: 3507

Answers (2)

Mike B
Mike B

Reputation: 741

In your comment (below your question), you say you're actually looking to mock aiohttp responses. For that, I've been using the 3rd-party library aioresponses: https://github.com/pnuckowski/aioresponses

I use it for integration testing, where it seems better than directly mocking or patching aiohttp methods.

I made it into a little pytest fixture like so:

@pytest.fixture
def aiohttp_mock():
    with aioresponses() as aioresponse_mock:
        yield aioresponse_mock

which I can then call like an aiohttp client/session: aiohttp_mock.get(...)

Edit from the future: We actually went back to mocking aiohttp methods because aioresponses currently lacks the ability to verify the args that were used in the call. We decided that verifying the args was a requirement for us.

Upvotes: 0

Yurii Kramarenko
Yurii Kramarenko

Reputation: 1064

You can patch (using asynctest.patch) your ClientSession. But in this case you need to implement simple ResponseContextManager with .status, async .text() (async .json()), etc. methods and attrs.

Upvotes: 1

Related Questions