Requête exemple
Réponse exemple
POST /v1/webhooks enregistre un nouvel endpoint webhook dans le workspace courant. Une fois créé, Coffrify envoie une requête HTTP POST signée vers l'url fournie chaque fois qu'un des events souscrits se produit. À la création, le serveur génère automatiquement un secret de signature (préfixé whsec_, 32 octets en hexadécimal) et l'active immédiatement (is_active: true, signing_version: "v1"). Comportement notable : ce secret n'est renvoyé en clair qu'une seule fois, dans la réponse de création. Il sert à vérifier les signatures HMAC des livraisons ; conservez-le côté serveur dès réception. Si events est omis ou vide, le webhook est souscrit par défaut au seul événement transfer.downloaded. Un workspace ne peut pas dépasser 25 webhooks.
Authentification
Cet endpoint exige le scope webhooks:manage (le scope webhooks:read ne suffit pas, il ne couvre que la lecture). Présentez votre clé API via l'en-tête Authorization: Bearer <clé>. Les clés acceptées sont de la forme cof_live_… / cof_test_… (complètes), cof_rk_live_… / cof_rk_test_… (restreintes) ou cof_mcp_live_… / cof_mcp_test_… (jeton MCP). Comme toutes les écritures de l'API, cet appel honore l'en-tête Idempotency-Key : réutiliser la même clé renvoie la réponse stockée sans recréer de webhook.
Corps de la requête
| Champ | Type | Requis | Description |
|---|---|---|---|
| name | string | Oui | Nom lisible du webhook (affiché dans le tableau de bord et les logs de livraison). |
| url | string | Oui | URL HTTPS de destination des livraisons. Doit être une URL absolue valide (validée via new URL()), sinon erreur validation_error. |
| events | string[] | Non | Liste des types d'événements souscrits. Chaque entrée doit appartenir au catalogue d'événements (VALID_EVENT_TYPES). Si omis ou tableau vide, défaut = ["transfer.downloaded"]. |
| description | string | Non | Description libre du webhook. null si non fourni. |
Les champs secret, signing_version (v1), is_active (true) et retry_policy ne sont pas acceptés en entrée à la création : ils sont fixés par le serveur. La retry_policy par défaut est {"max_attempts": 10, "max_duration_hours": 72, "backoff_base_seconds": 60}. Exemples de types valides : transfer.created, transfer.downloaded, transfer.expired, transfer.scan_infected (plan Pro), workspace.plan_changed, member.invited, api_key.rotated, coffre.accessed (plan Pro). Récupérez la liste complète via GET /v1/webhooks/event-catalog.
Réponse
En cas de succès, le statut HTTP est 201. Le corps reprend le webhook créé : id, name, description, url, events, is_active, signing_version, retry_policy et created_at, plus le champ secret en clair (présent uniquement dans cette réponse de création). Utilisez secret pour calculer/vérifier la signature HMAC des futures livraisons et id pour les opérations ultérieures (mise à jour, test, rotation de secret, consultation des livraisons).
Erreurs
| Code HTTP | code | Quand | Comment résoudre |
|---|---|---|---|
| 400 | validation_error | name ou url manquant ; url non parsable ; un ou plusieurs events hors catalogue (Invalid events: …). | Fournir name et une url absolue valide ; n'utiliser que des types listés par GET /v1/webhooks/event-catalog. |
| 401 | invalid_api_key | Clé absente, malformée ou introuvable. | Envoyer une clé valide via Authorization: Bearer … au bon préfixe (cof_live_, cof_rk_live_, cof_mcp_live_…). |
| 401 | revoked_api_key / expired_api_key | Clé révoquée, inactive ou expirée. | Générer une nouvelle clé API. |
| 403 | scope_missing | La clé ne porte pas le scope webhooks:manage. | Utiliser une clé disposant du scope webhooks:manage. |
| 403 | ip_not_allowed | Appel depuis une IP hors de l'allowlist de la clé. | Appeler depuis une IP autorisée ou ajuster l'allowlist de la clé. |
| 409 | validation_error | Le workspace atteint déjà 25 webhooks (Max 25 webhooks per workspace). | Supprimer un webhook inutilisé via DELETE /v1/webhooks avant d'en créer un nouveau. |
| 429 | rate_limited | Quota de requêtes par minute du workspace dépassé. | Respecter l'en-tête Retry-After puis réessayer. |
| 500 | internal_error | Erreur côté base de données lors de l'insertion. | Réessayer ; si persistant, contacter le support avec le x-request-id de la réponse. |
Voir aussi
GET/v1/webhooks/event-catalogListe complète des types d'événements souscriptibles, avec famille, stabilité et plan requis.POST/v1/webhooks/{id}/testEnvoie une livraison de test vers l'endpoint pour valider la réception et la vérification de signature.POST/v1/webhooks/{id}/rotate-secretRégénère le secret de signature d'un webhook existant (rotation périodique recommandée).