vendredi 25 septembre 2026

À propos

Contact

Extensions

wp_remote_post non bloquant : un webhook sortant sans ralentir la réponse

Notifier un service tiers qu'une commande vient d'être validée ne devrait jamais faire attendre le client final le temps que ce tiers réponde.

Par Clément Hadrot • 1 août 2022 • 5 min de lecture • Aucun commentaire
wp_remote_post non bloquant : un webhook sortant sans ralentir la réponse

Une extension de billetterie associative envoie une notification à un service de comptabilité externe chaque fois qu’une commande est validée, pour que le trésorier de l’association garde une vue à jour sans ressaisie manuelle. Le service tiers, hébergé par un petit prestataire, répond parfois en moins d’une seconde, mais peut aussi prendre jusqu’à huit secondes en cas de pic de charge de son côté. Tant que cet appel restait bloquant, l’acheteur final devait patienter ces huit secondes avant de voir sa page de confirmation de commande, ce qui inquiétait légitimement une partie des visiteurs qui rechargeaient la page ou fermaient l’onglet en pensant à une erreur.

Le problème du webhook bloquant

Par défaut, wp_remote_post() attend la réponse complète du serveur distant avant de rendre la main au script PHP appelant. Cela a du sens quand le résultat de l’appel conditionne la suite du traitement, par exemple une validation de paiement dont il faut connaître l’issue immédiatement. Mais pour une simple notification informative, dont le résultat n’a aucune influence sur ce qui s’affiche à l’acheteur, cette attente est du temps perdu, entièrement à la charge de l’expérience utilisateur.

La recette non bloquante

L'essentiel à retenir : L'argument blocking à false rend l'appel immédiat côté PHP ; On perd alors toute lecture du résultat, un compromis assumé ; Cette approche ne remplace pas une file d'attente pour un webhook critique
function notifier_comptabilite_commande_validee( int $commande_id ) {
    $payload = array(
        'commande_id' => $commande_id,
        'montant'     => obtenir_montant_commande( $commande_id ),
        'date'        => current_time( 'mysql', true ),
    );

    wp_remote_post( 'https://compta-partenaire.example/webhooks/commande', array(
        'body'      => wp_json_encode( $payload ),
        'headers'   => array( 'Content-Type' => 'application/json' ),
        'timeout'   => 0.5,
        'blocking'  => false,
        'sslverify' => true,
    ) );
}

Deux arguments méritent une attention particulière ici. D’abord blocking à false, qui indique à l’API HTTP de WordPress de ne pas attendre la réponse du serveur distant : le script PHP continue son exécution immédiatement après l’envoi de la requête, sans se soucier du résultat. Ensuite timeout, réduit volontairement à une demi-seconde : en mode non bloquant, ce délai ne sert plus qu’à borner le temps que WordPress passe à établir la connexion et à transmettre les données avant de rendre la main, pas à attendre une réponse complète.

Ce que l’on perd, et pourquoi c’est un compromis assumé

La conséquence directe du mode non bloquant est qu’aucune vérification du résultat n’est possible dans le script appelant : impossible de savoir si le service distant a bien reçu et traité la notification, impossible de récupérer un code d’erreur ou un message de validation. C’est un compromis acceptable uniquement quand l’information transmise est secondaire pour l’utilisateur final et peut, en cas d’échec silencieux, être rattrapée autrement.

Prévoir un filet de sécurité

Pour éviter qu’un échec silencieux du webhook ne se traduise par une comptabilité durablement désynchronisée sans que personne ne s’en aperçoive, il est recommandé de conserver localement une trace de chaque notification envoyée, avec son statut, et de proposer un mécanisme de resynchronisation manuelle ou périodique :

function notifier_comptabilite_commande_validee( int $commande_id ) {
    update_post_meta( $commande_id, '_notif_compta_tentee_le', current_time( 'mysql', true ) );

    $payload = array( /* ... */ );

    wp_remote_post( 'https://compta-partenaire.example/webhooks/commande', array(
        'body'     => wp_json_encode( $payload ),
        'headers'  => array( 'Content-Type' => 'application/json' ),
        'timeout'  => 0.5,
        'blocking' => false,
    ) );
}

// Une tâche quotidienne vérifie les commandes sans accusé de réception reçu par un autre canal
// (par exemple un rappel périodique côté service tiers) et les renvoie si nécessaire.

Sur ce projet associatif, le service tiers propose de son côté un accusé de réception asynchrone via son propre webhook entrant vers WordPress, ce qui permet de fermer la boucle : la notification sortante est envoyée sans bloquer l’acheteur, et sa bonne réception est confirmée quelques secondes plus tard par un appel entrant séparé, traité lui de façon classique.

Quand ne pas utiliser cette approche

  • Pour tout appel dont le résultat conditionne une décision immédiate, comme une vérification de fraude ou un calcul de taxe, qui doivent rester bloquants malgré leur coût en temps.
  • Pour un webhook dont la fiabilité de livraison est contractuellement garantie envers un partenaire, où une file d’attente avec accusé de réception explicite, par exemple via Action Scheduler, offre un contrôle bien plus robuste qu’un simple appel non bloquant sans suivi.
  • Sur des hébergements mutualisés dont la configuration réseau ferme parfois les connexions sortantes très rapidement après le retour du script PHP appelant, ce qui peut, dans de rares cas, interrompre l’envoi avant qu’il n’atteigne réellement le serveur distant.

Ne jamais faire attendre un client pour une information qui ne le concerne pas directement, c’est une règle de bon sens qui se code en une seule ligne d’argument.

En résumé

Le mode non bloquant de wp_remote_post() résout élégamment le cas d’une notification sortante purement informative, en évitant qu’un service tiers lent ne dégrade l’expérience de l’utilisateur final. Ce gain de rapidité a un prix, l’absence totale de vérification du résultat, qu’il faut compenser par une trace locale et, si l’enjeu métier le justifie, un mécanisme de resynchronisation périodique.

Partager :

À propos de l'auteur

Clément Hadrot

Développeur WordPress, passionné par Elementor, le FSE et l’automatisation par IA.

Voir tous ses articles

Dans la même veine

À lire aussi