Quand utiliser async vs sync
Le choix n’est pas toujours evident
L’asynchrone n’est pas systematiquement superieur au synchrone. Chaque approche a ses contextes ou elle excelle, et choisir la mauvaise peut compliquer votre code sans gain de performance. Cette lecon vous aide a determiner quelle approche adopter selon votre situation.
Quand le synchrone suffit
Le client synchrone est le bon choix dans plusieurs scenarios courants :
- Script ponctuel : vous envoyez quelques requetes dans un script de test ou d’exploration. La simplicite du code prime.
- Pipeline sequentiel : chaque requete depend du resultat de la precedente. Le parallelisme n’apporte rien.
- Application Django traditionnelle : si votre stack n’est pas asynchrone, ajouter
asynciouniquement pour les appels API cree de la complexite inutile. - Prototypage rapide : quand vous testez un prompt ou validez un concept, le code synchrone est plus lisible et plus rapide a ecrire.
# Synchrone — parfait pour un pipeline sequentiel
from openai import OpenAI
client = OpenAI(api_key=os.getenv("XAI_API_KEY"), base_url="https://api.x.ai/v1")
# Etape 1 : analyser le texte
analysis = client.chat.completions.create(
model="grok-4",
messages=[{"role": "user", "content": f"Analyse ce texte : {text}"}]
).choices[0].message.content
# Etape 2 : generer un resume base sur l'analyse
summary = client.chat.completions.create(
model="grok-4",
messages=[{"role": "user", "content": f"Resume selon cette analyse : {analysis}"}]
).choices[0].message.content
Dans cet exemple, l’etape 2 a besoin du resultat de l’etape 1. L’asynchrone ne gagnerait rien.
Quand l’asynchrone est necessaire
Passez en asynchrone dans ces situations :
- Traitement par lots : vous envoyez des dizaines ou centaines de requetes independantes. Le gain de temps est proportionnel au nombre de requetes.
- Application web FastAPI/Starlette : votre framework est deja asynchrone. Utiliser un client synchrone bloquerait l’event loop.
- Chatbot avec plusieurs sources : vous interrogez Grok, une base de donnees et une API externe en parallele pour construire une reponse.
- Monitoring en temps reel : vous surveillez plusieurs flux simultanement.
# Asynchrone — traitement de 50 questions en parallele
async def batch_process(questions: list[str]) -> list[str]:
sem = asyncio.Semaphore(5)
async def ask(q: str) -> str:
async with sem:
resp = await client.chat.completions.create(
model="grok-4",
messages=[{"role": "user", "content": q}]
)
return resp.choices[0].message.content
return await asyncio.gather(*[ask(q) for q in questions])
Avec 50 questions et un semaphore de 5, vous traitez 5 requetes en parallele au lieu d’une seule. Si chaque requete prend 8 secondes, le temps total passe de 400 secondes a environ 80 secondes.
Le piege de l’asynchrone premature
Un code asynchrone mal concu est pire qu’un code synchrone bien ecrit. Voici les erreurs courantes :
Bloquer l’event loop
# MAUVAIS : appel synchrone dans une fonction async
async def bad_example():
response = requests.get("https://api.example.com") # bloque tout
return response.json()
La bibliotheque requests est synchrone. L’appeler dans une coroutine bloque l’event loop et annule tout benefice de l’asynchrone. Utilisez httpx ou aiohttp a la place.
Complexite inutile
# MAUVAIS : async pour une seule requete
async def over_engineered():
response = await client.chat.completions.create(...)
return response
# Equivalent synchrone, plus simple
def simple():
response = client.chat.completions.create(...)
return response
Si vous n’avez qu’une seule requete a envoyer, l’asynchrone ajoute de la complexite sans benefice.
Arbre de decision
Pour choisir entre sync et async, posez-vous ces questions dans l’ordre :
- Combien de requetes API envoyez-vous ? Si une seule ou quelques-unes en sequence, restez en synchrone.
- Les requetes sont-elles independantes ? Si chaque requete depend de la precedente, restez en synchrone.
- Votre framework est-il asynchrone ? Si oui (FastAPI, Starlette, aiohttp), utilisez l’asynchrone pour ne pas bloquer l’event loop.
- Le temps de traitement total est-il un probleme ? Si vous traitez des lots et que le temps synchrone est inacceptable, passez en asynchrone.
Points cles a retenir
- Le synchrone convient aux scripts simples, pipelines sequentiels et prototypage
- L’asynchrone est necessaire pour le traitement par lots, les frameworks async et les requetes paralleles
- Ne jamais utiliser de bibliotheques synchrones (
requests) dans du code asynchrone - La complexite ajoutee par l’asynchrone doit etre justifiee par un gain mesurable
- Commencez en synchrone, migrez en asynchrone quand le besoin se confirme