Skip to main content

aioresponses-ng

PyPI version CI

This is a maintained fork of aioresponses with aiohttp compatibility fixes. The API is identical - just swap the package name.

Aioresponses is a helper to mock/fake web requests in python aiohttp package.

For the requests module there are a lot of packages that help us with testing (e.g. httpretty, responses, requests-mock).

When it comes to testing asynchronous HTTP requests it is a bit harder (at least at the beginning). The purpose of this package is to provide an easy way to test asynchronous HTTP requests.

Installing

pip install aioresponses-ng

Supported versions

  • Python 3.10+
  • aiohttp>=3.9,<4.0

Usage

To mock out HTTP requests use aioresponses as a method decorator or as a context manager.

Response status code, body, payload (for json response) and headers can be mocked.

Supported HTTP methods: GET, POST, PUT, PATCH, DELETE and OPTIONS.

import aiohttp
import asyncio
from aioresponses import aioresponses

@aioresponses()
def test_request(mocked):
    loop = asyncio.get_event_loop()
    mocked.get('http://example.com', status=200, body='test')
    session = aiohttp.ClientSession()
    resp = loop.run_until_complete(session.get('http://example.com'))

    assert resp.status == 200
    mocked.assert_called_once_with('http://example.com')

For convenience use the payload argument to mock out JSON responses.

As a context manager

import asyncio
import aiohttp
from aioresponses import aioresponses

def test_ctx():
    loop = asyncio.get_event_loop()
    session = aiohttp.ClientSession()
    with aioresponses() as m:
        m.get('http://test.example.com', payload=dict(foo='bar'))

        resp = loop.run_until_complete(session.get('http://test.example.com'))
        data = loop.run_until_complete(resp.json())

        assert dict(foo='bar') == data
        m.assert_called_once_with('http://test.example.com')

Mocking HTTP headers

import asyncio
import aiohttp
from aioresponses import aioresponses

@aioresponses()
def test_http_headers(m):
    loop = asyncio.get_event_loop()
    session = aiohttp.ClientSession()
    m.post(
        'http://example.com',
        payload=dict(),
        headers=dict(connection='keep-alive'),
    )

    resp = loop.run_until_complete(session.post('http://example.com'))

    # note that we pass 'connection' but get 'Connection' (capitalized)
    # under the hood `multidict` is used to work with HTTP headers
    assert resp.headers['Connection'] == 'keep-alive'
    m.assert_called_once_with('http://example.com', method='POST')

Multiple responses for the same URL

import asyncio
import aiohttp
from aioresponses import aioresponses

@aioresponses()
def test_multiple_responses(m):
    loop = asyncio.get_event_loop()
    session = aiohttp.ClientSession()
    m.get('http://example.com', status=500)
    m.get('http://example.com', status=200)

    resp1 = loop.run_until_complete(session.get('http://example.com'))
    resp2 = loop.run_until_complete(session.get('http://example.com'))

    assert resp1.status == 500
    assert resp2.status == 200

Repeating responses

Useful for testing retry mechanisms.

  • By default, repeat=False means the response is used once (repeat=1 does the same).
  • Use repeat=n to repeat a response n times.
  • Use repeat=True to repeat a response indefinitely.
import asyncio
import aiohttp
from aioresponses import aioresponses

@aioresponses()
def test_multiple_responses(m):
    loop = asyncio.get_event_loop()
    session = aiohttp.ClientSession()
    m.get('http://example.com', status=500, repeat=2)
    m.get('http://example.com', status=200)  # takes effect after two preceding calls

    resp1 = loop.run_until_complete(session.get('http://example.com'))
    resp2 = loop.run_until_complete(session.get('http://example.com'))
    resp3 = loop.run_until_complete(session.get('http://example.com'))

    assert resp1.status == 500
    assert resp2.status == 500
    assert resp3.status == 200

Matching URLs with regular expressions

import asyncio
import aiohttp
import re
from aioresponses import aioresponses

@aioresponses()
def test_regexp_example(m):
    loop = asyncio.get_event_loop()
    session = aiohttp.ClientSession()
    pattern = re.compile(r'^http://example\.com/api\?foo=.*$')
    m.get(pattern, status=200)

    resp = loop.run_until_complete(session.get('http://example.com/api?foo=bar'))

    assert resp.status == 200

Redirect responses

import asyncio
import aiohttp
from aioresponses import aioresponses

@aioresponses()
def test_redirect_example(m):
    loop = asyncio.get_event_loop()
    session = aiohttp.ClientSession()

    # absolute URLs are supported
    m.get(
        'http://example.com/',
        headers={'Location': 'http://another.com/'},
        status=307
    )

    resp = loop.run_until_complete(
        session.get('http://example.com/', allow_redirects=True)
    )
    assert resp.url == 'http://another.com/'

    # relative URLs are also supported
    m.get(
        'http://example.com/',
        headers={'Location': '/test'},
        status=307
    )
    resp = loop.run_until_complete(
        session.get('http://example.com/', allow_redirects=True)
    )
    assert resp.url == 'http://example.com/test'

Passthrough to real servers

import asyncio
import aiohttp
from aioresponses import aioresponses

@aioresponses(passthrough=['http://backend'])
def test_passthrough(m, test_client):
    session = aiohttp.ClientSession()
    # this will actually perform a request
    resp = loop.run_until_complete(session.get('http://backend/api'))

Passthrough all unmatched requests

import asyncio
import aiohttp
from aioresponses import aioresponses

@aioresponses(passthrough_unmatched=True)
def test_passthrough_unmatched(m, test_client):
    url = 'https://httpbin.org/get'
    m.get(url, status=200)
    session = aiohttp.ClientSession()
    # this will actually perform a request
    resp = loop.run_until_complete(session.get('http://backend/api'))
    # this will not perform a request and resp2.status will return 200
    resp2 = loop.run_until_complete(session.get(url))

Throwing exceptions

import asyncio
from aiohttp import ClientSession
from aiohttp.http_exceptions import HttpProcessingError
from aioresponses import aioresponses

@aioresponses()
def test_how_to_throw_an_exception(m, test_client):
    loop = asyncio.get_event_loop()
    session = ClientSession()
    m.get('http://example.com/api', exception=HttpProcessingError('test'))

    # calling
    # loop.run_until_complete(session.get('http://example.com/api'))
    # will throw an exception.

Callbacks for dynamic responses

import asyncio
import aiohttp
from aioresponses import CallbackResult, aioresponses

def callback(url, **kwargs):
    return CallbackResult(status=418)

@aioresponses()
def test_callback(m, test_client):
    loop = asyncio.get_event_loop()
    session = ClientSession()
    m.get('http://example.com', callback=callback)

    resp = loop.run_until_complete(session.get('http://example.com'))

    assert resp.status == 418

Using with pytest fixtures

import pytest
from aioresponses import aioresponses

@pytest.fixture
def mock_aioresponse():
    with aioresponses() as m:
        yield m

Features

  • Easy to mock out HTTP requests made by aiohttp.ClientSession

License

MIT — see LICENSE for details.

Credits

Fork maintained by MountainGod2. Originally created by Pawel Nuckowski using Cookiecutter and the audreyr/cookiecutter-pypackage template.

Metadata

Release files for aioresponses-ng 0.8.2

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for aioresponses-ng 0.8.2
File Size Uploaded
aioresponses_ng-0.8.2.tar.gz 19.4 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for aioresponses-ng 0.8.2
File Interpreter ABI Platform
aioresponses_ng-0.8.2-py3-none-any.whl Python 3 none any Details

Total release size: 30.2 kB

Release files / aioresponses_ng-0.8.2.tar.gz

Download URL aioresponses_ng-0.8.2.tar.gz
Size 19.4 kB
Tags Source
SHA-256 checksum
How to use checksums
0ee168f7bccfcc7990a995fcabf42bb84dd42faafaa30497c7108b093214633f
BLAKE2b-256 checksum
How to use checksums
646f6e317e805995b704894d9fc90ca63a87a567daf567e58db138659bf0abdc
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/6.1.0 CPython/3.13.13

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Jul 5, 2026.

Transparency log

Release files / aioresponses_ng-0.8.2-py3-none-any.whl

Download URL aioresponses_ng-0.8.2-py3-none-any.whl
Size 10.8 kB
Tags Python 3
SHA-256 checksum
How to use checksums
9de28a0de0ad289c6317b56da2f81c846643e4b9c2fde32023c1509064fbb72d
BLAKE2b-256 checksum
How to use checksums
a79d4ad5aebee5771ce0822135b6daaa21b45f44043b15eb1b7afc2faaeabf1c
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/6.1.0 CPython/3.13.13

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Jul 5, 2026.

Transparency log

Release history Release notifications | RSS feed

This release

0.8.2 This release

2 release files

0.8.1

2 release files

0.8.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page