Générer un article complet ou un long paragraphe avec une API de modèle de langage prend généralement entre vingt et trente secondes. Sans retour visuel, cette attente donne l’impression que l’interface a planté, ce qui pousse une partie des utilisateurs à cliquer plusieurs fois sur le bouton de génération — déclenchant autant d’appels facturés inutiles. Le streaming résout ce problème en affichant le texte au fur et à mesure qu’il est produit par le modèle, comme le fait l’interface de la plupart des assistants conversationnels grand public depuis leur lancement.
Techniquement, mettre en place ce comportement dans l’admin WordPress demande de sortir des sentiers battus de admin-ajax.php, dont la structure de réponse classique n’est pas pensée pour un flux progressif. Voici comment procéder proprement.
Le principe des Server-Sent Events
Les Server-Sent Events (SSE) constituent l’approche la plus simple pour transmettre un flux de données du serveur vers le navigateur sans fermer la connexion entre chaque morceau. Contrairement à une requête classique qui attend la réponse complète avant de la traiter, une connexion SSE reste ouverte et le navigateur reçoit des événements successifs au fil de leur envoi. La plupart des API de modèles de langage proposent une option de streaming qui renvoie précisément un flux de ce type, morceau de texte par morceau de texte.
Le point de terminaison REST WordPress doit alors relayer ce flux au navigateur plutôt que d’attendre la réponse complète du fournisseur avant de répondre lui-même.
Implémenter le relais côté serveur
Sur un point de terminaison REST personnalisé enregistré via register_rest_route(), le relais du flux nécessite de désactiver la bufferisation PHP habituelle, qui accumulerait sinon toute la sortie avant de l’envoyer d’un bloc au navigateur :

add_action( 'rest_api_init', function () {
register_rest_route( 'mon-extension/v1', '/generer-stream', array(
'methods' => 'POST',
'callback' => 'mon_extension_stream_callback',
'permission_callback' => function () {
return current_user_can( 'edit_posts' );
},
) );
} );
function mon_extension_stream_callback( $request ) {
header( 'Content-Type: text/event-stream' );
header( 'Cache-Control: no-cache' );
header( 'X-Accel-Buffering: no' );
while ( ob_get_level() > 0 ) {
ob_end_flush();
}
mon_extension_appel_llm_stream( $request->get_param( 'prompt' ), function ( $morceau ) {
echo 'data: ' . wp_json_encode( array( 'texte' => $morceau ) ) . "\n\n";
flush();
} );
exit;
}
L’en-tête X-Accel-Buffering: no est spécifique aux configurations utilisant Nginx en proxy inverse : sans lui, le serveur web peut lui-même mettre en tampon la réponse et annuler l’effet du streaming côté PHP, même si le code applicatif est correct. C’est une source fréquente de « streaming qui ne streame pas » en production alors qu’il fonctionne en local.
Réceptionner le flux côté client
Côté navigateur, l’API EventSource native gère la réception des événements SSE en GET, mais elle ne permet pas d’envoyer un corps de requête en POST, ce qui pose problème pour transmettre un prompt potentiellement long. En pratique, la plupart des intégrations utilisent plutôt fetch() avec lecture progressive du flux via ReadableStream, ce qui autorise une requête POST classique tout en lisant la réponse morceau par morceau au fur et à mesure de sa réception.
Limites et cas où le streaming n’est pas pertinent
- Le streaming complique la mise en cache : on ne peut pas mettre en cache une réponse tant qu’elle n’est pas entièrement reçue
- Certains proxys et pare-feux applicatifs coupent les connexions longues, ce qui nécessite des tests en conditions réelles d’hébergement
- Pour une génération courte (un titre, un texte alternatif), le gain perçu est marginal et ne justifie pas la complexité ajoutée
Le streaming a surtout du sens pour des générations longues — un article complet, un résumé détaillé — où l’attente sans retour visuel dégraderait sensiblement l’expérience dans l’éditeur.
Le streaming ne rend pas la génération plus rapide ; il rend l’attente supportable.
En résumé
Streamer les réponses IA dans l’admin WordPress demande de sortir du schéma classique de admin-ajax.php, de désactiver la bufferisation PHP et de gérer les particularités du serveur web utilisé en production. La complexité ajoutée se justifie surtout pour les générations longues, où le retour progressif change radicalement la perception du temps d’attente par l’utilisateur, sans pour autant réduire le coût ni le temps réel de traitement côté API.