Webhooks
Recevez les événements Certivant en temps réel dans vos propres systèmes lorsque les vérifications changent de statut — configuration, vérification de la signature HMAC, calendrier des nouvelles tentatives et référence complète des types d'événements.

Ce que cela permet de faire
Un webhook est une URL vers laquelle nous envoyons une requête POST chaque fois qu'un événement se produit dans votre organisation Certivant. Au lieu d'interroger notre API pour détecter les changements (« la vérification est-elle terminée ? »), vous nous fournissez une URL, et nous vous prévenons dès que cela arrive. Les événements de webhook vous permettent de garder vos propres systèmes synchronisés : parcours d'intégration des clients, bases de données de risque LBC-FT, étiquettes CRM, tableaux de bord de conformité internes.
Où le trouver
KYC → Webhooks dans la barre latérale gauche. (Les événements KYB sont envoyés vers les mêmes points de terminaison de webhooks : il n'existe pas de configuration distincte pour le KYB.)
Configuration
Choisissez une URL de votre côté
Votre point de terminaison doit :
- Accepter les requêtes POST en HTTPS avec
Content-Type: application/json. - Répondre rapidement par
2xx(en moins de 5 secondes) pour accuser réception. - Vérifier l'en-tête de signature (étape suivante) avant de faire confiance à la charge utile.
Ajoutez l'URL dans Certivant
KYC → Webhooks → Ajouter un point de terminaison. Un champ s'ouvre sur place : collez l'URL et cliquez sur Enregistrer (la même URL peut être modifiée ultérieurement sous Paramètres → KYC/B). La carte Points de terminaison webhook affiche le point de terminaison par défaut de l'organisation, les points de terminaison propres à chaque formulaire et le secret de signature.

Copiez le secret de signature
Après l'enregistrement, un secret de signature s'affiche une seule fois. Copiez-le immédiatement : il ne sera plus affiché. Si vous le perdez, renouvelez-le pour en obtenir un nouveau.
Vérifiez les signatures de votre côté
Chaque requête comporte un en-tête X-Certivant-Signature-V2 de la forme t=<unix time>,v1=<hex>. La valeur v1 est le HMAC-SHA256 de l'heure Unix, d'un point et du corps brut de la requête, signé avec le secret que vous venez de copier. Vérifiez-la, et rejetez les événements dont l'heure diffère de plus de cinq minutes de votre propre horloge, avant d'analyser le contenu. La méthode, accompagnée d'exemples de code dans plusieurs langages, se trouve dans le guide développeur.
L'en-tête historique X-KYC-Signature-Legacy, qui ne signait que le corps, n'est
plus envoyé (il a été supprimé le 24 October 2026). Si votre récepteur le vérifie
encore, chaque événement échouera désormais à la vérification : passez à
X-Certivant-Signature-V2.
Pseudo-code :
const sig = req.headers["x-certivant-signature"];
const expected = hmac("sha256", secret).update(rawBody).digest("hex");
if (!timingSafeEqual(sig, expected)) return 401;
Ne sautez pas cette étape. Sans vérification de la signature, quiconque devine l'URL de votre point de terminaison peut vous envoyer de faux événements.
Testez depuis le tableau de bord
Sur la page Développeur, ouvrez la section Événements de webhook. Choisissez un événement dans la liste Événement de test — kyc.webhook.test (par défaut), kyc.request.created, kyc.request.approved, kyc.request.rejected ou kyc.request.escalated — puis cliquez sur Envoyer un événement de test. Certivant envoie un événement synthétique à votre point de terminaison, signé exactement comme un véritable événement (X-Certivant-Signature-V2, avec votre secret de webhook) et portant test: true pour que vous puissiez le distinguer. Vérifiez que votre point de terminaison répond par un code 2xx.

Types d'événements
| Événement | Quand |
|---|---|
kyc.request.created | Une demande de vérification a été créée (tableau de bord, API ou formulaire public). |
kyc.request.documents_ready | Le demandeur a téléversé tous les documents requis ; le traitement a commencé. |
kyc.request.approved | Le statut final est APPROVED (automatique ou manuel). |
kyc.request.rejected | Le statut final est REJECTED. |
kyc.request.escalated | Envoyé à l'examen manuel. |
kyc.request.cancelled | Un examinateur a annulé la demande avant son terme. |
kyb.* | Même structure que kyc.*, mais pour les vérifications d'entreprises. |
monitoring.alert.created | Une nouvelle alerte de surveillance a été émise pour un demandeur déjà approuvé. |
monitoring.alert.resolved | Un examinateur a résolu une alerte. |
form.submitted | Une soumission de formulaire public. Utile lorsque vous utilisez le formulaire pour une collecte de données non liée au KYC. |
webhook.test | L'événement de test synthétique envoyé par le bouton Tester. Il est toujours émis, quels que soient les abonnements. |
La liste complète et les charges utiles JSON sont documentées sous KYC → Développeur → Événements de webhook.
Structure de la charge utile
Chaque événement a la même enveloppe :
{
"id": "evt_2k3f9a...",
"type": "kyc.request.approved",
"createdAt": "2026-05-27T14:30:00Z",
"organizationId": "org_abc123",
"data": { /* event-specific payload */ }
}
Le champ data varie selon le type d'événement. Par exemple, kyc.request.approved transporte :
{
"request": { "id": "kyr_...", "status": "APPROVED", "type": "INDIVIDUAL", ... },
"applicant": { "id": "ka_...", "fullName": "Jane Doe", "email": "...", ... },
"decision": { "by": "auto" | "manual", "reviewerId": "user_..." | null, "note": "..." | null },
"policy": {
"id": "pol_..." | null,
"name": "default-kyc-policy",
"version": 3 | null,
"isDefault": true,
"decision": "approve" | "reject" | "escalate" | "live_verification",
"rulesFired": ["tier1-disqualified", "approve-by-score"],
"reason": "High-risk country",
"liveVerificationRequired": true
}
}
Le bloc policy (sur kyc.request.approved / rejected / escalated) indique quelle politique de risque a décidé de la demande et quelles règles se sont déclenchées. isDefault: true signifie que la politique par défaut de Certivant a été exécutée (id / version correspondent à la ligne de politique par défaut de votre organisation, ou valent null si elle n'a pas encore été créée) ; une politique personnalisée renvoie son id, son name et sa version enregistrés. rulesFired liste les identifiants des règles qui ont correspondu, dans l'ordre d'évaluation — conditionnez vos automatisations en aval à partir de ces éléments. reason correspond au motif de la règle gagnante, lorsqu'elle en a défini un. decision: "live_verification" (avec liveVerificationRequired: true, sur kyc.request.escalated) signifie que la politique demande une vérification d'identité en direct avant toute décision finale : la demande attend en examen manuel jusqu'à ce que l'appel décide. Voir Concevoir une politique de risque.
Si vous fonctionnez en mode partenaire (une organisation qui sert de nombreux clients finaux), chaque enveloppe d'événement transporte aussi subTenantName et subTenantExternalId — les étiquettes définies sur la demande lors de sa création via l'API — afin que votre gestionnaire puisse acheminer le résultat vers le bon client final. Voir la référence des webhooks développeur pour l'emplacement exact de ces champs.
Nouvelles tentatives
Si votre point de terminaison renvoie une réponse autre que 2xx (ou dépasse le délai), nous réessayons avec un intervalle croissant :
attempt 1: immediately
attempt 2: 30 seconds later
attempt 3: 5 minutes later
attempt 4: 30 minutes later
attempt 5: 2 hours later
attempt 6: 6 hours later
attempt 7: 24 hours later
Après 7 échecs, nous marquons l'événement comme permanently_failed et cessons de réessayer. Les événements en échec apparaissent dans le tableau de bord des webhooks avec leur dernière erreur ; vous pouvez en renvoyer manuellement n'importe lequel avec Réessayer.
Votre point de terminaison doit être idempotent. Nous ne dédupliquons pas les
nouvelles tentatives de notre côté : votre point de terminaison verra le même
événement plusieurs fois si ses premières tentatives ont expiré alors qu'elles ont
fini par réussir. Identifiez les événements par leur id et ignorez ceux que vous
avez déjà traités.
Plusieurs points de terminaison
Vous pouvez enregistrer plusieurs points de terminaison (par exemple un pour votre CRM, un pour votre entrepôt de données LBC-FT). Chacun peut s'abonner à un ensemble différent de types d'événements. Les secrets de signature sont propres à chaque point de terminaison : renouveler l'un ne casse pas les autres.
Webhooks par formulaire
Le webhook de l'organisation se déclenche pour chaque événement pertinent. Les formulaires publics peuvent AUSSI disposer d'une URL de webhook propre au formulaire dans leurs paramètres — utile lorsqu'un formulaire alimente un système distinct. Les webhooks par formulaire s'exécutent en plus de ceux de l'organisation.
La page KYC → Webhooks affiche désormais les deux au même endroit : l'URL de webhook de l'organisation en haut, et une ligne pour chaque URL de webhook de formulaire en dessous — vous voyez ainsi tous les endroits où les événements sont livrés, sans avoir à chercher dans les paramètres de chaque formulaire.
Le tableau de bord des webhooks
KYC → Webhooks liste chaque point de terminaison avec :
- URL du point de terminaison + nom convivial.
- Statut — actif / en pause / en échec.
- Dernière livraison — moment où le dernier événement a été envoyé en POST.
- Taux de réussite — % des tentatives ayant renvoyé 2xx au cours des 7 derniers jours.
- Livraisons récentes — tableau des événements récents avec code de statut, latence et corps de la réponse.
Mettez un point de terminaison en pause pour arrêter les livraisons sans perdre sa configuration.
Dépannage
Mon point de terminaison est submergé de requêtes
Les points de terminaison sont appelés une fois par événement, mais une organisation active peut en déclencher des dizaines par minute. Rendez votre point de terminaison asynchrone : acceptez la requête POST, répondez immédiatement 2xx, puis traitez la charge utile en dehors du cycle de vie de la requête. Si vous devez nous ralentir, réglez l'option Livraisons simultanées maximales du point de terminaison.
La vérification de la signature échoue systématiquement
Trois causes fréquentes :
- L'analyse du corps avant la vérification de la signature. Utilisez les octets bruts. Pour les utilisateurs d'Express +
body-parser, définissezbodyParser.raw({ type: 'application/json' })spécifiquement pour la route du webhook. - Mauvais secret. Renouvelez-le et collez-le à nouveau.
- Suppression ou transformation du corps par un intergiciel (gzip, BOM, encodage). La signature porte sur les octets exacts que nous avons envoyés.
Les événements semblent dupliqués
Les nouvelles tentatives sont déclenchées par des réponses trop lentes. Identifiez les événements par event.id pour garantir l'idempotence.
L'ordre des événements compte, mais je les reçois dans le désordre
Nous ne garantissons pas un ordre strict entre les types d'événements. Pour l'ordre par demandeur, utilisez le champ createdAt de l'événement ; l'ordre au sein du cycle de vie d'un même demandeur est monotone.
Voir aussi
- Journal d'audit — chaque envoi de webhook est aussi consigné ici.
- Développeur (clés d'API) — si vous préférez récupérer l'état via l'API REST plutôt que recevoir des envois.
- Formulaires — aperçu et publication — webhooks par formulaire.
Vérification d'identité en direct
Planifiez, animez, enregistrez et rejouez des sessions de vérification vidéo en direct dans Certivant, depuis un navigateur — aucun téléchargement d'application n'est requis pour le demandeur.
Développeur — clés d'API et API REST
Émettez et gérez des clés d'API, configurez leurs portées, et utilisez l'API REST de Certivant pour créer des demandes de vérification et synchroniser le statut KYC depuis vos propres systèmes, par programmation.