Skip to Content

Webhook event types

Subscribe to any combination of these events when configuring a webhook. All payloads are workspace-scoped — workspace_id is either the brand’s UUID or the __org__ sentinel for intentionally org-level rows (the empty-string shape is no longer emitted).

Delivery events

Fired when a message’s delivery status changes. On the internal event bus these flow as channel_delivery_status (plus dot-namespaced per-channel variants), and the classifier marks them PASSIVE so they never count toward MAU. The outbound webhook flattens them to the names below.

EventTriggerKey data fields
delivery.sentMessage queued for deliverymessage_id, campaign_id, contact_id, channel
delivery.deliveredProvider confirmed deliverymessage_id, campaign_id, contact_id, channel, delivered_at
delivery.failedPermanent delivery failuremessage_id, contact_id, channel, error_code, error_reason
delivery.bouncedEmail bouncedmessage_id, contact_id, bounce_type (hard/soft), bounce_reason
delivery.openedRecipient opened the messagemessage_id, contact_id, channel, opened_at
delivery.clickedRecipient clicked a linkmessage_id, contact_id, channel, link_url, clicked_at
delivery.repliedRecipient replied (WhatsApp, SMS)message_id, contact_id, channel, reply_text
delivery.readMessage marked as read (WhatsApp, RCS)message_id, contact_id, channel, read_at

Since the workspace-scoped delivery substrate rolled out (2026-05-22), delivery webhooks carry workspace_id reliably — providers preserve it via echoed metadata (MSG91 variables, SendGrid custom_args, Razorpay notes, Cashfree subscription_tags), URL-encoded callback paths (POS, shipping, Shopify), or a DB lookup fallback (Stripe, Clerk).

Contact events

Fired when contact data changes.

EventTriggerKey data fields
contact.createdNew contact addedcontact_id, email, phone, source (sdk/api/import/webhook)
contact.updatedContact properties changedcontact_id, changes (object with old/new values per field)
contact.deletedContact removedcontact_id, deletion_reason
contact.mergedTwo contacts mergedsurviving_id, merged_id, merge_source

Segment events

Fired when contacts enter or leave segments.

EventTriggerKey data fields
segment.enteredContact matched segment rulescontact_id, segment_id, segment_name
segment.exitedContact stopped matching segment rulescontact_id, segment_id, segment_name

Campaign events

Fired when campaign state changes.

EventTriggerKey data fields
campaign.startedCampaign began sendingcampaign_id, campaign_name, segment_id, channel
campaign.completedCampaign finished sendingcampaign_id, total_sent, total_delivered, total_bounced
campaign.pausedCampaign manually pausedcampaign_id, paused_by

Billing events

Fired when billing-relevant events occur.

EventTriggerKey data fields
billing.credit_lowCredit balance dropped below thresholdcurrent_balance, threshold, workspace_id
billing.plan_changedSubscription plan changedold_plan, new_plan, effective_at

Filtering tips

  • Subscribe to delivery.* to pipe delivery data into your analytics warehouse
  • Subscribe to contact.created + contact.updated to keep your CRM in sync
  • Subscribe to billing.credit_low to auto-top-up credits via your payment flow
  • Start with 2-3 event types and expand as needed — you can update subscriptions anytime

What’s next