Webhooks

Référence des événements

Chaque événement qu’un webhook peut recevoir, avec les champs de son contenu et un exemple.

Chaque évènement, tel que votre point de terminaison le reçoit. Les exemples sont caviardés : identifiants, numéros et adresses sont fictifs. Des champs peuvent s’ajouter avec le temps, ignorez donc ceux que vous ne reconnaissez pas.

Événements SMS

Voici les événements SMS, de désabonnement et de numéro de téléphone. L’inscription d’un point de terminaison, l’enveloppe de chaque événement, les nouvelles tentatives et les signatures sont décrites dans Webhooks.

message.queued

Un message sortant a été accepté et facturé, et va être remis à l’opérateur. Un envoi programmé le déclenche au moment où vous le programmez, avec le statut SCHEDULED et scheduled_at, et part chez l’opérateur à l’heure prévue.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.queued",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "from": "+1416XXXXXXX",
    "to": "+1613XXXXXXX",
    "status": "QUEUED",
    "message_status": "QUEUED"
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
fromVotre numéro HonkIO d’où le message est parti, au format E.164.
toLe numéro du destinataire, au format E.164.
statusLe statut du message à ce moment, en majuscules (la même valeur que message_status).
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.
scheduled_atPour un envoi programmé seulement : l’heure prévue de son départ, en ISO 8601 UTC. Son statut est alors SCHEDULED.

message.sending

Réservé : rarement, voire jamais envoyé. Il ne se déclenche que si un accusé final de l’opérateur indique le statut sending, ce qui n’est pas attendu en pratique.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.sending",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "status": "sending",
    "message_status": "SENDING",
    "to": "+1613XXXXXXX",
    "from": "+1416XXXXXXX",
    "errors": []
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
statusLe statut propre à l’opérateur tiré de son accusé, en minuscules (par exemple delivered, sending_failed, delivery_failed ou expired).
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.
toLe numéro du destinataire, au format E.164.
fromVotre numéro HonkIO d’où le message est parti, au format E.164.
errorsCe que l’opérateur a signalé, sous forme de liste ; vide s’il n’a rien signalé.
errors[].codeLe code d’erreur de l’opérateur, tel quel.
errors[].titleUne brève description de l’erreur.
errors[].detailPlus de détails, quand l’opérateur en donne.

message.sent

L’opérateur a accepté le message pour livraison. Déclenché au retour de l’appel d’envoi, pas par un accusé.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.sent",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "from": "+1416XXXXXXX",
    "to": "+1613XXXXXXX",
    "status": "SENDING",
    "message_status": "SENDING",
    "carrier_message_id": "40319xxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
    "segment_count": 1,
    "cost_cents": 3
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
fromVotre numéro HonkIO d’où le message est parti, au format E.164.
toLe numéro du destinataire, au format E.164.
statusLe statut du message à ce moment, en majuscules (la même valeur que message_status).
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.
carrier_message_idL’identifiant attribué au message par l’opérateur, pour les demandes de soutien.
segment_countLe nombre de segments SMS du message, qui est la base de sa facturation.
cost_centsCe que le message vous a coûté, en cents canadiens.

message.delivered

L’accusé de l’opérateur indique que le message a atteint l’appareil.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.delivered",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "status": "delivered",
    "message_status": "DELIVERED",
    "to": "+1613XXXXXXX",
    "from": "+1416XXXXXXX",
    "errors": []
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
statusLe statut propre à l’opérateur tiré de son accusé, en minuscules (par exemple delivered, sending_failed, delivery_failed ou expired).
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.
toLe numéro du destinataire, au format E.164.
fromVotre numéro HonkIO d’où le message est parti, au format E.164.
errorsCe que l’opérateur a signalé, sous forme de liste ; vide s’il n’a rien signalé.
errors[].codeLe code d’erreur de l’opérateur, tel quel.
errors[].titleUne brève description de l’erreur.
errors[].detailPlus de détails, quand l’opérateur en donne.

message.failed

Le message n’est pas parti. Trois formes selon l’endroit de l’échec : un échec au passage à l’opérateur (CARRIER_UNAVAILABLE, CARRIER_THROTTLED, CARRIER_TIMEOUT, CARRIER_ERROR, INVALID_PHONE_NUMBER, NOT_A_MOBILE_NUMBER) porte error_code et error_message mais pas de tableau errors ; un accusé de l’opérateur porte son statut brut, un tableau errors et un error_code, mais pas de error_message (son error_code est CARRIER_THROTTLED quand l’opérateur a pris le message puis l’a abandonné parce que la file était pleine : ce message est remboursé, et le renvoyer demande une nouvelle Idempotency-Key ; il est CARRIER_LOST, avec un tableau errors vide, quand l’opérateur a pris le message puis l’a perdu, constaté trois jours plus tard sans accusé ni trace chez l’opérateur : remboursé de la même façon) ; un envoi interrompu par un redémarrage du serveur (error_code STALE_QUEUED) ne porte ni to ni from. Un message programmé refusé à l’heure prévue (un destinataire qui s’est désabonné depuis, par exemple) échoue avec le error_code et le error_message de cette vérification, et est remboursé. Un message programmé qui ne peut pas partir avant sa limite (son expires_at, par défaut 24 heures après scheduled_at), parce qu’une pause, une limite d’envoi ou un opérateur qui le ralentissait l’a retenu jusque-là, échoue avec l’error_code SCHEDULED_SEND_EXPIRED et un error_message, et est remboursé. Un échec pour INSUFFICIENT_BALANCE ne déclenche aucun webhook.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.failed",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "from": "+1416XXXXXXX",
    "to": "+1613XXXXXXX",
    "status": "FAILED",
    "message_status": "FAILED",
    "error_code": "INVALID_PHONE_NUMBER",
    "error_message": "The destination is not a valid phone number."
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
statusLe statut propre à l’opérateur tiré de son accusé, en minuscules (par exemple delivered, sending_failed, delivery_failed ou expired).
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.
toLe numéro du destinataire, au format E.164.
fromVotre numéro HonkIO d’où le message est parti, au format E.164.
error_codeLe code d’erreur HonkIO de l’échec, le même que celui du message dans l’API.
error_messageUne explication lisible de error_code.
errorsCe que l’opérateur a signalé, sous forme de liste ; vide s’il n’a rien signalé.
errors[].codeLe code d’erreur de l’opérateur, tel quel.
errors[].titleUne brève description de l’erreur.
errors[].detailPlus de détails, quand l’opérateur en donne.

message.undelivered

L’opérateur a pris le message mais n’a pas pu le livrer : bloqué, expiré, ou appareil injoignable.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.undelivered",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "status": "delivery_failed",
    "message_status": "UNDELIVERED",
    "to": "+1613XXXXXXX",
    "from": "+1416XXXXXXX",
    "errors": [
      {
        "code": "40002",
        "title": "Blocked as spam",
        "detail": "The destination carrier blocked the message."
      }
    ]
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
statusLe statut propre à l’opérateur tiré de son accusé, en minuscules (par exemple delivered, sending_failed, delivery_failed ou expired).
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.
toLe numéro du destinataire, au format E.164.
fromVotre numéro HonkIO d’où le message est parti, au format E.164.
errorsCe que l’opérateur a signalé, sous forme de liste ; vide s’il n’a rien signalé.
errors[].codeLe code d’erreur de l’opérateur, tel quel.
errors[].titleUne brève description de l’erreur.
errors[].detailPlus de détails, quand l’opérateur en donne.

message.received

Quelqu’un a texté l’un de vos numéros HonkIO. Les réponses STOP, START et HELP arrivent aussi ici, avec keyword_action qui indique ce qui en a été fait.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.received",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "from": "+1613XXXXXXX",
    "to": "+1416XXXXXXX",
    "body": "Yes, see you at 3",
    "keyword_action": "ignored",
    "segment_count": 1,
    "cost_cents": 1,
    "message_status": "RECEIVED"
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
fromLe numéro qui vous a texté, au format E.164.
toVotre numéro HonkIO qui a reçu le texto, au format E.164.
bodyLe texte du message.
keyword_actionCe que HonkIO a fait d’un mot-clé de conformité, d’après le premier mot du texte : opted_out (STOP et semblables, suivi d’un évènement opt_out.recorded), reinstated (START ou UNSTOP après un désabonnement, suivi d’un évènement opt_out.reinstated), help (HELP, INFO ou AIDE ; la réponse automatique a été envoyée), ou ignored.
segment_countLe nombre de segments SMS du message, qui est la base de sa facturation.
cost_centsCe que la réception du message vous a coûté, en cents canadiens.
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.

message.cancelled

Un message programmé a été annulé avant son envoi, et les frais ont été remboursés.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.cancelled",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "from": "+1416XXXXXXX",
    "to": "+1613XXXXXXX",
    "status": "CANCELLED",
    "message_status": "CANCELLED",
    "details": {
      "cancelled_at": "2026-10-01T16:58:00.000Z"
    }
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
fromVotre numéro HonkIO d’où le message est parti, au format E.164.
toLe numéro du destinataire, au format E.164.
statusLe statut du message à ce moment, en majuscules (la même valeur que message_status).
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.
details.cancelled_atLe moment de l’annulation du message, en ISO 8601 UTC.

message.rescheduled

Un message programmé a été déplacé à une nouvelle heure.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "message.rescheduled",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "message_id": "clxxxmessagexxxxxxxxxxxxx",
    "from": "+1416XXXXXXX",
    "to": "+1613XXXXXXX",
    "status": "SCHEDULED",
    "message_status": "SCHEDULED",
    "details": {
      "previous_scheduled_at": "2026-10-02T13:00:00.000Z",
      "scheduled_at": "2026-10-03T13:00:00.000Z"
    }
  }
}
Champ de dataSignification
message_idL’identifiant HonkIO du message, tel que renvoyé par POST /v1/messages ou listé par GET /v1/messages.
fromVotre numéro HonkIO d’où le message est parti, au format E.164.
toLe numéro du destinataire, au format E.164.
statusLe statut du message à ce moment, en majuscules (la même valeur que message_status).
message_statusLe statut HonkIO du message, en majuscules : QUEUED, SENDING, DELIVERED, FAILED, UNDELIVERED, RECEIVED, SCHEDULED ou CANCELLED.
details.previous_scheduled_atL’heure planifiée précédente, en ISO 8601 UTC.
details.scheduled_atLa nouvelle heure, en ISO 8601 UTC.

opt_out.recorded

Un abonné a répondu à l’un de vos numéros par un mot-clé de désabonnement (une réponse dont le premier mot est STOP, STOPALL, UNSUBSCRIBE, CANCEL, END, QUIT ou ARRÊT, avec ou sans accent), et les messages vers lui depuis ce numéro sont maintenant bloqués. Se déclenche uniquement pour une réponse par mot-clé : un désabonnement enregistré avec POST /v1/compliance/opt-outs ne le déclenche pas.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "opt_out.recorded",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "phone_number": "+1613XXXXXXX",
    "from_number": "+1416XXXXXXX",
    "keyword": "STOP"
  }
}
Champ de dataSignification
phone_numberL’abonné qui a texté le mot-clé, au format E.164 : la personne à qui cesser ou recommencer d’écrire.
from_numberVotre numéro HonkIO qui a reçu le mot-clé, au format E.164. Un désabonnement vaut pour les messages envoyés depuis ce numéro.
keywordLa réponse de l’abonné, rognée et en majuscules, par exemple STOP ou STOP PLEASE. La réponse entière, pas seulement le mot-clé : elle a été reconnue par son premier mot.

opt_out.reinstated

Un abonné désabonné a répondu START ou UNSTOP, vous pouvez donc de nouveau lui écrire depuis ce numéro. Se déclenche uniquement pour une réponse par mot-clé, et seulement si un désabonnement existait : un START de quelqu’un qui ne s’était jamais désabonné est un simple message.received.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "opt_out.reinstated",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "phone_number": "+1613XXXXXXX",
    "from_number": "+1416XXXXXXX",
    "keyword": "START"
  }
}
Champ de dataSignification
phone_numberL’abonné qui a texté le mot-clé, au format E.164 : la personne à qui cesser ou recommencer d’écrire.
from_numberVotre numéro HonkIO qui a reçu le mot-clé, au format E.164. Un désabonnement vaut pour les messages envoyés depuis ce numéro.
keywordLa réponse de l’abonné, rognée et en majuscules, par exemple START. La réponse entière, pas seulement le mot-clé : elle a été reconnue par son premier mot.

phone_number.suspended

Le loyer mensuel n’a pas pu être prélevé, le numéro a donc été suspendu. Rechargez votre solde pour le récupérer avant la fin du délai de grâce.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "phone_number.suspended",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "phone_number": "+1416XXXXXXX",
    "reason": "insufficient_balance",
    "monthly_cost_cents": 299
  }
}
Champ de dataSignification
phone_numberVotre numéro HonkIO, au format E.164.
reasonToujours insufficient_balance : le loyer du mois n’a pas pu être prélevé.
monthly_cost_centsLe loyer mensuel du numéro, en cents canadiens.

phone_number.released

Le numéro a quitté votre compte et ne peut pas être récupéré. Cessez d’y acheminer quoi que ce soit.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "phone_number.released",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "phone_number": "+1416XXXXXXX",
    "reason": "customer_released",
    "rent_owed_cents": 0
  }
}
Champ de dataSignification
phone_numberVotre numéro HonkIO, au format E.164.
reasonsuspended_grace_expired quand une suspension a dépassé son délai de grâce, customer_released quand vous l’avez libéré vous-même, admin_released quand le personnel de HonkIO l’a libéré.
rent_owed_centsLoyer maintenant dû pour ce numéro, en cents canadiens. Il correspond au loyer mensuel du numéro lorsqu’un numéro suspendu a été libéré, et vaut 0 lorsqu’un numéro actif l’a été.

toll_free_verification.changes_requested

HonkIO a examiné votre demande de vérification sans frais et demande des modifications avant de la transmettre à l’opérateur. Modifiez-la selon reviewer_note et soumettez-la de nouveau ; rien de plus n’est facturé.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "toll_free_verification.changes_requested",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "verification_id": "tfv_xxxxxxxxxxxxxxxxxxxxxxxx",
    "status": "CHANGES_REQUESTED",
    "phone_numbers": [
      {
        "id": "clxxxnumberxxxxxxxxxxxxxx",
        "phone_number": "+1833XXXXXXX"
      }
    ],
    "reviewer_note": "The opt-in screenshot does not show the SMS checkbox. Add one that does."
  }
}
Champ de dataSignification
verification_idL’identifiant de la demande de vérification sans frais (tfv_...), tel que renvoyé par POST /v1/toll-free-verifications.
statusL’état de la demande après la décision : CHANGES_REQUESTED, APPROVED ou REJECTED, selon l’événement.
phone_numbersLes numéros sans frais couverts par la demande.
phone_numbers[].idL’identifiant du numéro, tel que listé par GET /v1/phone-numbers.
phone_numbers[].phone_numberLe numéro sans frais, au format E.164.
reviewer_noteCe que HonkIO vous demande de modifier, tel qu’affiché dans le tableau de bord.

toll_free_verification.approved

L’opérateur a approuvé votre demande de vérification sans frais : tous les numéros qu’elle couvre peuvent maintenant envoyer des SMS.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "toll_free_verification.approved",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "verification_id": "tfv_xxxxxxxxxxxxxxxxxxxxxxxx",
    "status": "APPROVED",
    "phone_numbers": [
      {
        "id": "clxxxnumberxxxxxxxxxxxxxx",
        "phone_number": "+1833XXXXXXX"
      }
    ]
  }
}
Champ de dataSignification
verification_idL’identifiant de la demande de vérification sans frais (tfv_...), tel que renvoyé par POST /v1/toll-free-verifications.
statusL’état de la demande après la décision : CHANGES_REQUESTED, APPROVED ou REJECTED, selon l’événement.
phone_numbersLes numéros sans frais couverts par la demande.
phone_numbers[].idL’identifiant du numéro, tel que listé par GET /v1/phone-numbers.
phone_numbers[].phone_numberLe numéro sans frais, au format E.164.

toll_free_verification.rejected

L’opérateur a refusé votre demande de vérification sans frais. Corrigez ce que reason indique et soumettez-la de nouveau, sans frais supplémentaires.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "toll_free_verification.rejected",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "verification_id": "tfv_xxxxxxxxxxxxxxxxxxxxxxxx",
    "status": "REJECTED",
    "phone_numbers": [
      {
        "id": "clxxxnumberxxxxxxxxxxxxxx",
        "phone_number": "+1833XXXXXXX"
      }
    ],
    "reason": "Opt-in workflow does not show how consent is collected."
  }
}
Champ de dataSignification
verification_idL’identifiant de la demande de vérification sans frais (tfv_...), tel que renvoyé par POST /v1/toll-free-verifications.
statusL’état de la demande après la décision : CHANGES_REQUESTED, APPROVED ou REJECTED, selon l’événement.
phone_numbersLes numéros sans frais couverts par la demande.
phone_numbers[].idL’identifiant du numéro, tel que listé par GET /v1/phone-numbers.
phone_numbers[].phone_numberLe numéro sans frais, au format E.164.
reasonLa raison du refus, telle que l’opérateur l’a donnée (habituellement en anglais).

Événements de compte

Sept événements de compte ne portent aucun message : account.delivery_warning lorsque plus de 10 % de vos 50 derniers messages réels ont échoué chez l’opérateur ; account.sending_paused lorsqu’une pause automatique se déclenche (channel vaut sms ou email ; une pause courriel ajoute bounce_rate_pct ou complaint_rate_pct) ; account.spend_warning lorsque les dépenses réelles d’une heure dépassent le plus élevé de 5 $ et de la moitié d’une journée typique ; account.inbound_email_capped lorsque le courriel reçu atteint le plafond quotidien du compte, au plus une fois par 24 heures ; account.inbound_sms_capped lorsque les textos reçus atteignent le plafond quotidien du compte, au plus une fois par 24 heures ; account.auto_topup_succeeded lorsqu’un prélèvement de rechargement automatique crédite votre solde ; account.auto_topup_paused lorsque le rechargement automatique se met en pause. Chacun est aussi envoyé par courriel. Leur contenu figure dans la référence ci-dessous.

account.delivery_warning

Plus de 10 % de vos 50 derniers messages réels ont échoué chez l’opérateur. Envoyé avant toute pause automatique, au plus une fois par période de pause. Aussi envoyé par courriel.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "account.delivery_warning",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "failure_rate_pct": 14,
    "failed": 7,
    "sample": 50
  }
}
Champ de dataSignification
failure_rate_pctLa part de l’échantillon qui a échoué, en pourcentage arrondi.
failedLe nombre de messages de l’échantillon qui ont échoué chez l’opérateur.
sampleLe nombre de vos messages réels les plus récents examinés.

account.sending_paused

Une pause automatique a arrêté l’envoi réel jusqu’à paused_until. Le mode test n’est pas touché. Aussi envoyé par courriel.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "account.sending_paused",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "channel": "sms",
    "paused_until": "2026-09-25T14:00:00.000Z",
    "reason": "FAILURE_RATE"
  }
}
Champ de dataSignification
channelL’envoi arrêté : sms ou email. L’autre canal n’est pas en pause.
paused_untilLe moment où l’envoi réel reprend de lui-même, en ISO 8601 UTC.
reasonPourquoi : OPT_OUT_RATE ou FAILURE_RATE pour les SMS ; BOUNCE_RATE ou COMPLAINT_RATE pour les courriels.
bounce_rate_pctPauses de courriel pour BOUNCE_RATE seulement : votre taux récent de rebonds réels, en pourcentage.
complaint_rate_pctPauses de courriel pour COMPLAINT_RATE seulement : votre taux récent de plaintes réelles, en pourcentage.

account.spend_warning

Vos dépenses réelles de la dernière heure ont dépassé le plus élevé de 5 $ et de la moitié d’une journée habituelle. Aussi envoyé par courriel.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "account.spend_warning",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "spent_last_hour_cents": 1250,
    "typical_daily_cents": 400,
    "threshold_cents": 500
  }
}
Champ de dataSignification
spent_last_hour_centsVos dépenses réelles de la dernière heure, en cents canadiens.
typical_daily_centsCe que votre compte dépense habituellement en une journée, en cents canadiens, en moyenne sur ses envois réels de la dernière semaine ; 0 tant qu’il n’a pas deux jours d’envois réels, ou s’il n’en a eu aucun cette semaine-là.
threshold_centsLa dépense en une heure qui déclenche cet avertissement pour votre compte, en cents canadiens.

account.inbound_email_capped

Le courriel reçu par ce compte a atteint son plafond quotidien. Le courriel supplémentaire est stocké comme refusé et n’est pas facturé jusqu’à ce que la fenêtre de 24 heures avance.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "account.inbound_email_capped",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "limit": "messages",
    "cap": 1000,
    "window_hours": 24,
    "received_in_window": 1000,
    "managed_address_enabled": true
  }
}
Champ de dataSignification
limitLe plafond atteint : messages (le nombre quotidien de messages) ou megabytes (le plafond quotidien de Mo facturables, les Mo entamés après le premier Mo de chaque message ; cap et received_in_window sont alors en Mo).
capLe plafond quotidien atteint : le remplacement propre à votre compte, ou la valeur par défaut de la plateforme.
window_hoursLa fenêtre glissante sur laquelle le plafond est compté, en heures. Toujours 24.
received_in_windowLe nombre de messages reçus par votre compte dans la fenêtre, au moment où le plafond a été atteint. Pour account.inbound_sms_capped, des segments de message (un long texto en compte plusieurs).
managed_address_enabledSi votre adresse entrante gérée accepte encore le courriel. Désactivez-la depuis la boîte de réception si ce trafic ne devrait pas s’y rendre.

account.inbound_sms_capped

Les textos reçus par ce compte ont atteint leur plafond quotidien, compté en segments de message (un long texto en compte plusieurs). Les textos supplémentaires sont stockés sans leur contenu et ne sont pas facturés jusqu’à ce que la fenêtre de 24 heures avance. STOP, START et HELP continuent de fonctionner.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "account.inbound_sms_capped",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "cap": 1000,
    "window_hours": 24,
    "received_in_window": 1000
  }
}
Champ de dataSignification
capLe plafond quotidien atteint : le remplacement propre à votre compte, ou la valeur par défaut de la plateforme.
window_hoursLa fenêtre glissante sur laquelle le plafond est compté, en heures. Toujours 24.
received_in_windowLe nombre de messages reçus par votre compte dans la fenêtre, au moment où le plafond a été atteint. Pour account.inbound_sms_capped, des segments de message (un long texto en compte plusieurs).

account.auto_topup_succeeded

Un prélèvement de rechargement automatique a réussi et votre solde a été crédité. Le reçu est aussi envoyé par courriel.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "account.auto_topup_succeeded",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "attempt_id": "ata_a1b2c3d4e5f6a1b2c3d4e5f6",
    "trigger": "threshold",
    "amount_cents": 2500,
    "tax_cents": 325,
    "total_cents": 2825,
    "balance_cents": 3100
  }
}
Champ de dataSignification
attempt_idL’identifiant de la tentative de rechargement automatique, tel que listé par GET /v1/auto-topup. Sur account.auto_topup_paused, c’est la tentative qui a causé la pause, ou null si aucun prélèvement n’était en cause.
triggerCe qui a déclenché le prélèvement : threshold quand votre solde est passé sous votre seuil, rent quand il ne couvrait pas un loyer exigible dans les 24 heures.
amount_centsLe montant crédité à votre solde, en cents canadiens, avant taxe.
tax_centsLa taxe de vente ajoutée au prélèvement, en cents canadiens.
total_centsLe total prélevé sur votre carte, en cents canadiens.
balance_centsVotre solde après le crédit, en cents canadiens.

account.auto_topup_paused

Le rechargement automatique a été mis en pause et ne prélèvera plus avant que vous le réactiviez avec Recharger pour reprendre, dans la section Rechargement automatique de la page de facturation. Une pause pour examen du compte est levée par le soutien de HonkIO. Aussi envoyé par courriel.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "account.auto_topup_paused",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "reason": "DECLINED",
    "attempt_id": "ata_a1b2c3d4e5f6a1b2c3d4e5f6"
  }
}
Champ de dataSignification
reasonPourquoi il s’est mis en pause, en majuscules : DECLINED, AUTHENTICATION_REQUIRED, EXPIRED_CARD, CARD_REMOVED, BILLING_ADDRESS, ACCOUNT_REVIEW, ADMIN, REFUND ou CHARGE_LIMIT.
attempt_idL’identifiant de la tentative de rechargement automatique, tel que listé par GET /v1/auto-topup. Sur account.auto_topup_paused, c’est la tentative qui a causé la pause, ou null si aucun prélèvement n’était en cause.

Événements de courriel

Abonnez-vous aux événements de courriel comme aux événements SMS. Les livraisons sont signées exactement comme décrit dans Vérifier les signatures.

email.queued

Un courriel a été accepté et facturé, et il est en file, ou planifié si vous avez passé scheduled_at.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.queued",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ],
      "subject": "Your receipt",
      "tags": [
        {
          "name": "category",
          "value": "receipt"
        }
      ],
      "status": "queued",
      "is_commercial": false
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
email.subjectLa ligne d’objet.
email.tagsLes étiquettes posées sur le courriel, sous forme de liste de paires name et value ; vide s’il n’y en a pas.
email.statusqueued, ou scheduled quand le courriel attend scheduled_at. Absent pour les courriels envoyés en lot.
email.batch_idCourriels envoyés avec POST /v1/emails/batch seulement : le lot auquel appartient le courriel.
email.is_commercialSi vous avez marqué le courriel comme commercial (LCAP), ce qui décide du pied de page et de l’en-tête de désabonnement.

email.sent

Le fournisseur de courriel a accepté le message pour livraison.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.sent",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ],
      "subject": "Your receipt",
      "tags": []
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
email.ses_message_idL’identifiant du message chez le fournisseur de courriel, pour les demandes de soutien. Présent sur les évènements que le fournisseur signale.
email.subjectLa ligne d’objet.
email.tagsLes étiquettes posées sur le courriel, sous forme de liste de paires name et value ; vide s’il n’y en a pas.

email.delivered

Le serveur de courriel du destinataire a accepté le message.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.delivered",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "to": [
        "ada@example.com"
      ],
      "from": "receipts@mail.acme.ca",
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000",
      "tags": [
        {
          "name": "category",
          "value": "receipt"
        }
      ]
    },
    "details": {
      "delivered_at": "2026-10-01T17:00:03.512Z",
      "smtp_response": "250 2.0.0 OK",
      "processing_time_ms": 1204,
      "recipients": [
        "ada@example.com"
      ],
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.toLes adresses des destinataires, sous forme de liste.
email.fromL’adresse d’expédition du courriel.
email.ses_message_idL’identifiant du message chez le fournisseur de courriel, pour les demandes de soutien. Présent sur les évènements que le fournisseur signale.
email.tagsLes étiquettes posées sur le courriel, sous forme de liste de paires name et value ; vide s’il n’y en a pas.
details.delivered_atLe moment où le serveur du destinataire a accepté le message, en ISO 8601 UTC.
details.smtp_responseLa réponse SMTP du serveur du destinataire, telle quelle.
details.processing_time_msLa durée de la livraison depuis l’acceptation, en millisecondes.
details.recipientsLes adresses de destinataires visées par ce rapport.
details.ses_message_idLe même identifiant de fournisseur que email.ses_message_id.

email.delivery_delayed

Le serveur du destinataire diffère le message ; la livraison est encore retentée. Plusieurs peuvent arriver pour un même courriel.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.delivery_delayed",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "to": [
        "ada@example.com"
      ],
      "from": "receipts@mail.acme.ca",
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000",
      "tags": [
        {
          "name": "category",
          "value": "receipt"
        }
      ]
    },
    "details": {
      "delay_type": "MailboxFull",
      "expiration_time": "2026-10-02T17:00:00.000Z",
      "recipients": [
        {
          "email_address": "ada@example.com",
          "status": "4.2.2",
          "diagnostic_code": "smtp; 452 4.2.2 Mailbox full"
        }
      ],
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.toLes adresses des destinataires, sous forme de liste.
email.fromL’adresse d’expédition du courriel.
email.ses_message_idL’identifiant du message chez le fournisseur de courriel, pour les demandes de soutien. Présent sur les évènements que le fournisseur signale.
email.tagsLes étiquettes posées sur le courriel, sous forme de liste de paires name et value ; vide s’il n’y en a pas.
details.delay_typeLe type de retard signalé par le fournisseur, par exemple MailboxFull, SpamDetected ou TransientCommunicationFailure.
details.expiration_timeLe moment où le fournisseur cessera de réessayer et fera rebondir le message, en ISO 8601 UTC.
details.recipientsLes destinataires dont la livraison est retardée, un objet chacun.
details.recipients[].email_addressL’adresse d’un destinataire retardé.
details.recipients[].statusLe code de statut SMTP pour ce destinataire.
details.recipients[].diagnostic_codeL’explication du serveur du destinataire, quand il en donne une.
details.ses_message_idLe même identifiant de fournisseur que email.ses_message_id.

email.bounced

Le message a rebondi. Un rebond permanent supprime l’adresse ; un rebond temporaire, non.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.bounced",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "to": [
        "ada@example.com"
      ],
      "from": "receipts@mail.acme.ca",
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000",
      "tags": [
        {
          "name": "category",
          "value": "receipt"
        }
      ]
    },
    "details": {
      "bounce_type": "Permanent",
      "bounce_subtype": "General",
      "diagnostic_code": "smtp; 550 5.1.1 user unknown",
      "suppressed": true,
      "transient": false,
      "recipients": [
        "ada@example.com"
      ],
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.toLes adresses des destinataires, sous forme de liste.
email.fromL’adresse d’expédition du courriel.
email.ses_message_idL’identifiant du message chez le fournisseur de courriel, pour les demandes de soutien. Présent sur les évènements que le fournisseur signale.
email.tagsLes étiquettes posées sur le courriel, sous forme de liste de paires name et value ; vide s’il n’y en a pas.
details.bounce_typePermanent, Transient ou Undetermined.
details.bounce_subtypeLa classification plus fine du fournisseur, par exemple General, NoEmail ou MailboxFull.
details.diagnostic_codeL’explication du serveur du destinataire pour le premier destinataire rebondi, quand il en donne une.
details.suppressedtrue quand l’adresse a été ajoutée à votre liste de suppression (tout rebond permanent).
details.transienttrue pour un rebond temporaire, qui ne supprime pas l’adresse.
details.recipientsLes adresses de destinataires visées par ce rapport.
details.ses_message_idLe même identifiant de fournisseur que email.ses_message_id.

email.complained

Un destinataire a signalé le message comme pourriel. L’adresse est supprimée et enregistrée comme désabonnement.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.complained",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "to": [
        "ada@example.com"
      ],
      "from": "receipts@mail.acme.ca",
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000",
      "tags": [
        {
          "name": "category",
          "value": "receipt"
        }
      ]
    },
    "details": {
      "complained_at": "2026-10-01T18:12:00.000Z",
      "recipients": [
        "ada@example.com"
      ],
      "ses_message_id": "0101019xxxxxxxxx-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx-000000"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.toLes adresses des destinataires, sous forme de liste.
email.fromL’adresse d’expédition du courriel.
email.ses_message_idL’identifiant du message chez le fournisseur de courriel, pour les demandes de soutien. Présent sur les évènements que le fournisseur signale.
email.tagsLes étiquettes posées sur le courriel, sous forme de liste de paires name et value ; vide s’il n’y en a pas.
details.complained_atLe moment de la plainte, en ISO 8601 UTC.
details.recipientsLes adresses de destinataires visées par ce rapport.
details.ses_message_idLe même identifiant de fournisseur que email.ses_message_id.

email.rejected

Le message a été refusé avant ou pendant l’envoi, par les vérifications de HonkIO ou par le fournisseur de courriel, et les frais sont remboursés. Un refus de nos vérifications porte failure_code et failure_message ; un refus signalé par le fournisseur porte reason.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.rejected",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ]
    },
    "details": {
      "failure_code": "DOMAIN_NOT_VERIFIED",
      "failure_message": "The sending domain is not verified."
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
details.failure_codeLe code HonkIO qui explique le refus ou l’échec du courriel.
details.failure_messageUne explication lisible de failure_code.
details.reasonRefus signalés par le fournisseur de courriel seulement (à la place de failure_code) : la raison du fournisseur.
email.ses_message_idL’identifiant du message chez le fournisseur de courriel, pour les demandes de soutien. Présent sur les évènements que le fournisseur signale.

email.failed

Le courriel n’a pas pu être envoyé pour une raison qui ne tient pas au destinataire, comme une erreur de facturation ou du fournisseur, et les frais sont remboursés.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.failed",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ]
    },
    "details": {
      "failure_code": "SES_ERROR",
      "failure_message": "The provider did not accept the message."
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
details.failure_codeLe code HonkIO qui explique le refus ou l’échec du courriel.
details.failure_messageUne explication lisible de failure_code.

email.opened

La première ouverture du courriel : le pixel de suivi s’est chargé. Seulement quand le suivi des ouvertures est activé ; certains logiciels chargent les images automatiquement, une ouverture est donc un indice, pas une preuve. Les ouvertures suivantes ne déclenchent aucun webhook.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.opened",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ]
    },
    "details": {
      "ua": "Mozilla/5.0 (iPhone; CPU iPhone OS 18_0 like Mac OS X)"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
details.uaL’agent utilisateur qui a chargé le pixel ou suivi le lien, ou null.

email.clicked

Le premier clic sur un lien suivi du courriel, quand le suivi des clics est activé. Les clics suivants ne déclenchent aucun webhook.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.clicked",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ]
    },
    "details": {
      "url": "https://acme.ca/orders/1042",
      "ua": "Mozilla/5.0 (Macintosh; Intel Mac OS X 14_5)"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
details.urlLe lien suivi, tel qu’écrit dans votre courriel.
details.uaL’agent utilisateur qui a chargé le pixel ou suivi le lien, ou null.

email.unsubscribed

Un destinataire d’un courriel commercial s’est désabonné par son lien ou son en-tête, et il est maintenant supprimé pour ce domaine d’envoi.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.unsubscribed",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ]
    },
    "details": {
      "recipient": "ada@example.com",
      "from_domain": "mail.acme.ca"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
details.recipientL’adresse qui s’est désabonnée.
details.from_domainLe domaine d’envoi pour lequel l’adresse est maintenant supprimée.

email.cancelled

Un courriel planifié a été annulé avant son envoi, et les frais ont été remboursés.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.cancelled",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ]
    },
    "details": {
      "cancelled_at": "2026-10-01T16:58:00.000Z"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
details.cancelled_atLe moment de l’annulation, en ISO 8601 UTC.

email.rescheduled

Un courriel planifié a été déplacé à une nouvelle heure.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.rescheduled",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "clxxxemailxxxxxxxxxxxxxxx",
      "from": "receipts@mail.acme.ca",
      "to": [
        "ada@example.com"
      ],
      "tags": []
    },
    "details": {
      "previous_scheduled_at": "2026-10-02T13:00:00.000Z",
      "scheduled_at": "2026-10-03T13:00:00.000Z"
    }
  }
}
Champ de dataSignification
email.idL’identifiant HonkIO du courriel, tel que renvoyé par POST /v1/emails.
email.fromL’adresse d’expédition du courriel.
email.toLes adresses des destinataires, sous forme de liste.
email.tagsLes étiquettes posées sur le courriel, sous forme de liste de paires name et value ; vide s’il n’y en a pas.
details.previous_scheduled_atL’heure planifiée précédente, en ISO 8601 UTC.
details.scheduled_atLa nouvelle heure, en ISO 8601 UTC.

email.received

Un courriel est arrivé sur l’un de vos domaines de réception ou sur votre adresse entrante gérée. Métadonnées seulement ; récupérez le corps par son id.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email.received",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "email": {
      "id": "rcv_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
      "from": "ada@example.com",
      "from_name": "Ada Lovelace",
      "to": [
        "support@abc123defg.inbound.honkio.ca"
      ],
      "cc": [],
      "subject": "Re: Your order",
      "message_id": "<abc123@example.com>",
      "in_reply_to": "<orig456@mail.acme.ca>",
      "received_at": "2026-10-01T17:00:00.000Z",
      "size_bytes": 12345,
      "domain_id": null,
      "verdicts": {
        "spf": "PASS",
        "dkim": "PASS",
        "dmarc": "GRAY",
        "spam": "PASS"
      },
      "attachments": [
        {
          "id": "rat_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
          "filename": "invoice.pdf",
          "content_type": "application/pdf",
          "size_bytes": 48213,
          "inline": false
        }
      ]
    }
  }
}
Champ de dataSignification
email.idL’identifiant du courriel reçu (rcv_…). Récupérez son corps avec GET /v1/emails/received/:id.
email.fromL’adresse de l’expéditeur, telle que donnée par l’en-tête From.
email.from_nameLe nom d’affichage de l’expéditeur, ou null.
email.toLes adresses de l’en-tête To.
email.ccLes adresses de l’en-tête Cc.
email.subjectLa ligne d’objet.
email.message_idLe Message-ID RFC 5322, avec ses chevrons. Pour répondre dans le même fil, envoyez-le comme en-tête In-Reply-To (et à la fin de References) dans la table headers de l’API d’envoi.
email.in_reply_toLe Message-ID auquel ce courriel répond, ou null.
email.received_atLe moment où le message nous est parvenu, en ISO 8601 UTC.
email.size_bytesLa taille du message brut, en-têtes compris.
email.domain_idL’identifiant du domaine de réception, ou null pour votre adresse entrante gérée.
email.verdictsLes résultats d’authentification et de pourriel de la vérification à la réception. PASS, FAIL, GRAY ou PROCESSING_FAILED.
email.verdicts.spfLe résultat SPF pour l’expéditeur d’enveloppe.
email.verdicts.dkimLe résultat de la signature DKIM.
email.verdicts.dmarcLe résultat DMARC pour le domaine de From.
email.verdicts.spamLe résultat de l’analyse antipourriel. Un message détecté comme virus n’est jamais livré.
email.attachmentsLes pièces jointes, métadonnées seulement. Téléchargez chacune avec GET /v1/emails/received/:id/attachments/:attachment_id dans les 40 jours.
email.attachments[].idL’identifiant de la pièce jointe (rat_…).
email.attachments[].filenameLe nom du fichier tel qu’envoyé, ou attachment-N s’il n’en avait pas.
email.attachments[].content_typeLe type de contenu déclaré.
email.attachments[].size_bytesLa taille en octets.
email.attachments[].inlinetrue pour une partie intégrée, comme une image incorporée.

email_domain.verified

Les enregistrements DNS d’un domaine d’envoi sont validés et il peut envoyer.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email_domain.verified",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "domain": {
      "id": "clxxxdomainxxxxxxxxxxxxxx",
      "domain": "mail.acme.ca",
      "region": "ca-central-1"
    }
  }
}
Champ de dataSignification
domain.idL’identifiant HonkIO du domaine de courriel.
domain.domainLe nom de domaine.
domain.regionLa région d’où le domaine envoie (ca-central-1).

email_domain.verification_failed

Un domaine d’envoi a échoué la vérification, ou l’a perdue lors d’une vérification ultérieure de ses enregistrements.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email_domain.verification_failed",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "domain": {
      "id": "clxxxdomainxxxxxxxxxxxxxx",
      "domain": "mail.acme.ca",
      "status": "temporarily_failed"
    },
    "details": {
      "failure_reason": "DKIM records not found",
      "revalidation": true
    }
  }
}
Champ de dataSignification
domain.idL’identifiant HonkIO du domaine de courriel.
domain.domainLe nom de domaine.
domain.statusfailed quand un autre compte a depuis vérifié le même domaine, temporarily_failed quand une nouvelle vérification d’un domaine déjà vérifié a échoué ; absent quand une première vérification a échoué.
details.failure_reasonPourquoi la vérification a échoué, par exemple quels enregistrements sont introuvables.
details.revalidationtrue quand il s’agissait d’une nouvelle vérification d’un domaine déjà vérifié. Absent sinon.

email_domain.receiving_verified

L’enregistrement MX entrant d’un domaine a été trouvé. Le courrier envoyé vers lui vous parvient désormais.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email_domain.receiving_verified",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "domain": {
      "id": "clxxxdomainxxxxxxxxxxxxxx",
      "domain": "reply.acme.ca"
    }
  }
}
Champ de dataSignification
domain.idL’identifiant HonkIO du domaine de courriel.
domain.domainLe nom de domaine.

email_domain.receiving_failed

L’enregistrement MX entrant est manquant depuis plus longtemps que le délai de grâce. La réception sur ce domaine est coupée jusqu’à ce que l’enregistrement soit rétabli et le domaine revérifié.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "email_domain.receiving_failed",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "domain": {
      "id": "clxxxdomainxxxxxxxxxxxxxx",
      "domain": "reply.acme.ca",
      "status": "failed"
    },
    "details": {
      "failure_reason": "Inbound MX missing on reply.acme.ca",
      "revalidation": true
    }
  }
}
Champ de dataSignification
domain.idL’identifiant HonkIO du domaine de courriel.
domain.domainLe nom de domaine.
domain.statusToujours failed : l’enregistrement MX entrant est manquant depuis plus longtemps que le délai de grâce. La réception reste coupée jusqu’à ce que l’enregistrement soit rétabli et le domaine revérifié.
details.failure_reasonPourquoi la vérification a échoué, par exemple quels enregistrements sont introuvables.
details.revalidationtrue quand il s’agissait d’une nouvelle vérification d’un domaine déjà vérifié. Absent sinon.

Événements push

Neuf événements couvrent les notifications (push.queued, push.sent, push.failed, push.fell_back, push.cancelled, push.rescheduled), les appareils (push_device.deactivated) et les applications (push_app.credentials_invalid, push_app.vapid_key_replaced). Ils sont décrits, avec leur déclencheur et leurs champs de données, sous webhooks push.

Événements Notify

Deux événements couvrent les notifications : notification.delivered et notification.failed. Chacun est décrit ci-dessous avec ses champs de données ; webhooks Notify explique leur lien avec les événements des envois derrière une notification.

notification.delivered

Un canal a livré la notification : channel l’indique, et l’identifiant du SMS, du courriel ou du push envoyé est renseigné. Survient une fois par notification ; l’envoi derrière elle déclenche aussi ses propres événements.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "notification.delivered",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "id": "ntf_xxxxxxxxxxxxxxxxxxxxxxxx",
    "user_id": "user_1042",
    "status": "delivered",
    "channel": "email",
    "message_id": null,
    "email_id": "clxxxemailxxxxxxxxxxxxxxx",
    "push_id": null,
    "attempts": [
      {
        "channel": "sms",
        "outcome": "skipped",
        "reason": "no_phone_number"
      },
      {
        "channel": "email",
        "outcome": "delivered",
        "reason": null
      }
    ],
    "livemode": true
  }
}
Champ de dataSignification
idL’identifiant de la notification, tel que renvoyé par POST /v1/notify et lu par GET /v1/notifications/:id.
user_idLe user_id auquel la notification a été envoyée : votre identifiant pour le destinataire.
statusLe statut final de la notification, en minuscules : delivered ou failed, selon l’événement.
channelLe canal qui l’a livrée, l’un des canaux de attempts ; null si aucun ne l’a fait.
message_idL’identifiant du SMS qui l’a livrée, tel que listé par GET /v1/messages ; null sauf si channel vaut sms.
email_idL’identifiant du courriel qui l’a livrée, tel que listé par GET /v1/emails ; null sauf si channel vaut email.
push_idL’identifiant du push qui l’a livrée ; null sauf si channel vaut push.
attemptsLes canaux essayés, dans l’ordre : jusqu’à celui qui l’a livrée, ou tous les canaux si aucun ne l’a fait.
attempts[].channelLe canal essayé.
attempts[].outcomeCe qui s’est passé sur ce canal, en minuscules : delivered, skipped (la personne n’y était pas joignable, ou il ne pouvait pas servir), refused (le canal a refusé l’envoi) ou failed.
attempts[].reasonPourquoi, pour tout résultat autre que delivered : une raison en minuscules pour un canal ignoré, comme no_phone_number ou no_email, ou le code d’erreur propre au canal, comme NO_CONSENT ou EMAIL_SUPPRESSED. null si delivered.
livemodetrue pour une notification envoyée avec une clé réelle, false avec une clé de test, comme dans l’enveloppe.

notification.failed

Aucun canal n’a livré la notification : chaque canal de son ordre a été ignoré, refusé ou a échoué, et attempts indique pourquoi pour chacun. Survient une fois par notification.

json
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "type": "notification.failed",
  "created": "2026-09-24T12:00:00.000Z",
  "account_id": "clxxxaccountxxxxxxxxxxxxx",
  "livemode": true,
  "data": {
    "id": "ntf_xxxxxxxxxxxxxxxxxxxxxxxx",
    "user_id": "user_1042",
    "status": "failed",
    "channel": null,
    "message_id": null,
    "email_id": null,
    "push_id": null,
    "attempts": [
      {
        "channel": "sms",
        "outcome": "refused",
        "reason": "NO_CONSENT"
      },
      {
        "channel": "email",
        "outcome": "skipped",
        "reason": "no_email"
      }
    ],
    "livemode": true
  }
}
Champ de dataSignification
idL’identifiant de la notification, tel que renvoyé par POST /v1/notify et lu par GET /v1/notifications/:id.
user_idLe user_id auquel la notification a été envoyée : votre identifiant pour le destinataire.
statusLe statut final de la notification, en minuscules : delivered ou failed, selon l’événement.
channelLe canal qui l’a livrée, l’un des canaux de attempts ; null si aucun ne l’a fait.
message_idL’identifiant du SMS qui l’a livrée, tel que listé par GET /v1/messages ; null sauf si channel vaut sms.
email_idL’identifiant du courriel qui l’a livrée, tel que listé par GET /v1/emails ; null sauf si channel vaut email.
push_idL’identifiant du push qui l’a livrée ; null sauf si channel vaut push.
attemptsLes canaux essayés, dans l’ordre : jusqu’à celui qui l’a livrée, ou tous les canaux si aucun ne l’a fait.
attempts[].channelLe canal essayé.
attempts[].outcomeCe qui s’est passé sur ce canal, en minuscules : delivered, skipped (la personne n’y était pas joignable, ou il ne pouvait pas servir), refused (le canal a refusé l’envoi) ou failed.
attempts[].reasonPourquoi, pour tout résultat autre que delivered : une raison en minuscules pour un canal ignoré, comme no_phone_number ou no_email, ou le code d’erreur propre au canal, comme NO_CONSENT ou EMAIL_SUPPRESSED. null si delivered.
livemodetrue pour une notification envoyée avec une clé réelle, false avec une clé de test, comme dans l’enveloppe.