PesaBridge
Docs/En production/Webhooks

En production

Webhooks

Livraisons d'événements signées et relancées : points de terminaison, types d'événements, vérification en quatre langages, tests et rejeu.

6 min de lecture

Sur cette page
  1. Points de terminaison
  2. Types d'événements
  3. À quoi ressemble une livraison
  4. Vérifier chaque livraison
  5. Relances et doublons
  6. Tester et rejouer

Points de terminaison

Créez un ou plusieurs points de terminaison avec POST /partner/webhooks/endpoints (name, url, events sous forme de liste séparée par des virgules ou *, et mode). Chacun reçoit son propre secret de signature, affiché une seule fois à la création. Modifiez-les, supprimez-les et listez-les avec les appels /partner/webhooks/endpoint…, ou dans la console.

Types d'événements

ÉvénementEnvoyé lorsque
charge.createdUn débit par demande de paiement a été créé.
charge.completedLe client a approuvé et l'argent a été transféré.
charge.declinedLe client a refusé la demande.
charge.expiredLa demande a expiré sans réponse.
checkout.completedUne session de paiement hébergé a été payée.
c2b.confirmationUn client a payé directement votre caisse ou votre paybill.

À quoi ressemble une livraison

En-têteValeur
X-PesaBridge-EventLe type d'événement, par exemple charge.completed.
X-PesaBridge-SignatureHMAC-SHA256 en hexadécimal du corps brut de la requête, avec le secret de signature du point de terminaison.
X-PesaBridge-TimestampHeure Unix de la signature de la livraison.
X-PesaBridge-Signature-V2t=<timestamp>,v1=<hex HMAC-SHA256 of "<timestamp>.<raw body>"> : résistant au rejeu.
X-PesaBridge-DeliveryIdentifiant de livraison : journalisez-le et utilisez-le pour ignorer les doublons.

Vérifier chaque livraison

Calculez le HMAC sur les octets exacts reçus, avant d'analyser le JSON, et comparez en temps constant. Préférez la V2 et rejetez les horodatages de plus de cinq minutes.

Node.js
import crypto from "node:crypto";
// Express: app.post("/webhook", express.raw({ type: "application/json" }), handler)
function verified(req, secret) {
  const [t, v1] = (req.get("X-PesaBridge-Signature-V2") || "").split(",").map((p) => p.split("=")[1]);
  if (!t || Math.abs(Date.now() / 1000 - Number(t)) > 300) return false;
  const want = crypto.createHmac("sha256", secret).update(`${t}.${req.body}`).digest("hex");
  return v1?.length === want.length && crypto.timingSafeEqual(Buffer.from(v1), Buffer.from(want));
}
Python
import hmac, hashlib, time

def verified(raw_body: bytes, headers, secret: str) -> bool:
    parts = dict(p.split("=", 1) for p in headers.get("X-PesaBridge-Signature-V2", "").split(",") if "=" in p)
    t, v1 = parts.get("t"), parts.get("v1", "")
    if not t or abs(time.time() - int(t)) > 300:
        return False
    want = hmac.new(secret.encode(), f"{t}.".encode() + raw_body, hashlib.sha256).hexdigest()
    return hmac.compare_digest(v1, want)
PHP
<?php
$raw = file_get_contents("php://input");
parse_str(str_replace(",", "&", $_SERVER["HTTP_X_PESABRIDGE_SIGNATURE_V2"] ?? ""), $sig);
$ok = isset($sig["t"], $sig["v1"]) && abs(time() - (int)$sig["t"]) <= 300
   && hash_equals(hash_hmac("sha256", $sig["t"] . "." . $raw, getenv("PB_WHSEC")), $sig["v1"]);
http_response_code($ok ? 200 : 401);
Go
package webhook

import ("crypto/hmac"; "crypto/sha256"; "encoding/hex")

// Verified checks the V1 signature: hex HMAC-SHA256 of the raw body.
func Verified(raw []byte, sig, secret string) bool {
    m := hmac.New(sha256.New, []byte(secret))
    m.Write(raw)
    return hmac.Equal([]byte(hex.EncodeToString(m.Sum(nil))), []byte(sig))
}

Relances et doublons

Répondez par un code 2xx dans les 10 secondes. Toute autre réponse, ou un délai dépassé, entraîne une relance avec un délai exponentiel (1, 2, 4, 8 et 16 minutes, jusqu'à 6 tentatives), après quoi la livraison est marquée failed. À cause des relances, un même événement peut arriver deux fois : rendez votre traitement idempotent sur X-PesaBridge-Delivery ou sur charge_ref.

Nous livrons uniquement vers des adresses HTTPS publiques. Les adresses de réseaux privés et internes sont refusées.

Tester et rejouer

  • POST /partner/webhooks/test envoie un événement de test à un point de terminaison.
  • GET /partner/webhooks/deliveries liste les livraisons récentes avec leur code de statut et leurs tentatives.
  • POST /partner/webhooks/resend rejoue une livraison après la correction de votre traitement.
  • Le récepteur Echo (GET /partner/echo/url) capture et vérifie automatiquement les livraisons sans serveur de votre part.

Nos ingénieurs répondent aux questions d'intégration. Envoyez-nous la référence de la requête et nous retrouverons l'appel exact.

Contacter le support