Trois fois plus long : c’est devenu le temps d’upload d’une image dans la médiathèque, le jour où un plugin de génération automatique de légendes via un modèle de vision par IA a été activé pour accélérer le travail de la rédaction. Un utilisateur n’accepte pas d’attendre aussi longtemps avant qu’une image n’apparaisse enfin dans la grille.
Avant l’activation du plugin, l’upload d’une image de taille standard prenait environ deux secondes, le temps de générer les différentes tailles de miniatures. Après activation, ce temps est passé à six secondes en moyenne, avec des pointes à plus de dix secondes selon les images, rendant l’expérience d’ajout de média nettement plus pénible pour la rédaction.
Symptôme : un upload qui semble figé
Le navigateur affichait une barre de progression complète très rapidement — l’envoi du fichier lui-même vers le serveur ne posait aucun problème — mais l’interface restait ensuite bloquée sur un indicateur de traitement pendant plusieurs secondes supplémentaires, avant que la miniature et la légende générée n’apparaissent enfin dans la médiathèque.
Diagnostic : un appel bloquant au modèle de vision

Le code du plugin accrochait sa logique au hook add_attachment, avec un appel HTTP synchrone vers une API de description d’image par IA, dont la réponse conditionnait directement la fin du traitement d’upload perçu par l’utilisateur :
add_action( 'add_attachment', function ( $attachment_id ) {
$chemin = get_attached_file( $attachment_id );
$reponse = wp_remote_post( 'https://api.vision-ia.example/decrire', [
'timeout' => 15,
'body' => [ 'image' => base64_encode( file_get_contents( $chemin ) ) ],
] );
if ( ! is_wp_error( $reponse ) ) {
$legende = json_decode( wp_remote_retrieve_body( $reponse ), true )['legende'];
update_post_meta( $attachment_id, '_wp_attachment_image_alt', $legende );
}
});
Le timeout de 15 secondes, fixé côté wp_remote_post(), dessinait déjà le pire scénario possible : chaque upload d’image restait suspendu jusqu’à 15 secondes en cas de lenteur de l’API externe, sans possibilité pour WordPress de continuer son traitement pendant ce temps. Le hook add_attachment se déclenche en effet de façon synchrone, dans le même cycle de requête que l’upload lui-même, ce qui rendait ce blocage inévitable avec cette implémentation.
Correctif : différer l’appel à l’API de vision
Le traitement a été extrait du cycle de requête d’upload et confié à Action Scheduler, avec un état intermédiaire affiché à l’utilisateur pendant le traitement en arrière-plan :
add_action( 'add_attachment', function ( $attachment_id ) {
update_post_meta( $attachment_id, '_legende_ia_statut', 'en_attente' );
as_enqueue_async_action( 'generer_legende_ia', [ $attachment_id ] );
});
add_action( 'generer_legende_ia', function ( $attachment_id ) {
$chemin = get_attached_file( $attachment_id );
$reponse = wp_remote_post( 'https://api.vision-ia.example/decrire', [
'timeout' => 30,
'body' => [ 'image' => base64_encode( file_get_contents( $chemin ) ) ],
] );
if ( ! is_wp_error( $reponse ) ) {
$legende = json_decode( wp_remote_retrieve_body( $reponse ), true )['legende'];
update_post_meta( $attachment_id, '_wp_attachment_image_alt', $legende );
}
update_post_meta( $attachment_id, '_legende_ia_statut', 'termine' );
});
L’interface de la médiathèque a été complétée d’un badge « légende en cours de génération », interrogé toutes les quelques secondes via un appel Ajax léger, plutôt que de faire attendre l’utilisateur sur l’appel lui-même.
Résultat mesuré
| Mesure | Appel synchrone | Traitement différé |
|---|---|---|
| Temps d’upload perçu | 6 s en moyenne, pics à 10 s+ | 2 s, identique à avant activation du plugin |
| Délai d’apparition de la légende | Immédiat (bloquant) | 3 à 8 s en arrière-plan, sans blocage |
Prévention pour tout appel à une API IA externe
- Aucun appel réseau vers un service externe dont le temps de réponse n’est pas garanti ne devrait rester sur le chemin critique d’une action utilisateur directe comme un upload.
- Un traitement différé avec état visible (badge, notification) offre une meilleure expérience qu’un traitement synchrone rapide mais fragile face aux lenteurs occasionnelles du service tiers.
- Un
timeoutgénéreux (30 secondes) devient acceptable une fois le traitement sorti du cycle de requête utilisateur, puisqu’il ne bloque plus personne.
La qualité d’une légende générée par IA n’a d’intérêt que si son obtention ne dégrade pas l’expérience qu’elle est censée enrichir.
En résumé
Ce billet ne juge pas la pertinence des légendes produites par le modèle de vision, uniquement l’architecture technique de leur génération. Déplacer un appel à une API externe hors du cycle de requête synchrone reste, sur ce type de fonctionnalité enrichie par IA, un réflexe à appliquer systématiquement plutôt qu’après avoir constaté la dégradation en production.