This rule raises an issue when synchronous HTTP client calls are used within asynchronous functions.

Why is this an issue?

Using synchronous HTTP clients like urllib3, requests, or httpx.Client in asynchronous code blocks the entire event loop. This undermines the primary advantage of asynchronous programming - the ability to perform concurrent operations without blocking execution.

When an async function makes a synchronous HTTP request:

Instead, async-compatible HTTP clients should be used:

Using these libraries allows other tasks to continue executing while waiting for HTTP responses, significantly improving application performance and responsiveness.

How to fix it

Replace synchronous HTTP clients with asynchronous alternatives. The httpx.AsyncClient is recommended as it provides a consistent API across asyncio, Trio, and AnyIO frameworks.

Code examples

Noncompliant code example

import requests

async def fetch_data():
    response = requests.get("https://api.example.com/data")  # Noncompliant
    return response.json()

Compliant solution

Using httpx.AsyncClient (works with asyncio, Trio, and AnyIO):

import httpx

async def fetch_data():
    async with httpx.AsyncClient() as client:
        response = await client.get("https://api.example.com/data")
        return response.json()

Resources

Documentation

Articles & blog posts