Webhook event reference
Event envelopes, payload fields, deduplication and delivery behavior.
Envelope and signature
Every request contains event, timestamp (Unix seconds) and data. The signature covers timestamp + "." + the exact raw JSON body. Headers include X-MonCha-Event, X-MonCha-Timestamp and X-MonCha-Signature. Verify before parsing/processing the event. Use the receiver example in the Webhooks guide.
{
"event": "booking.created",
"timestamp": 1791504000,
"data": {
"booking_id": "11111111-1111-4111-8111-111111111111",
"chatbot_id": "22222222-2222-4222-8222-222222222222",
"name": "Example visitor",
"email": "[email protected]",
"phone": "+15550100100",
"requested_slot": "2026-10-20T09:00:00Z"
}
}Event payload fields
Some values can be null. Payload variants reflect how the event was created; do not require inferred-lead fields on a form-created lead or assume every handoff contains the same text field. Ignore unknown optional fields to tolerate additions.
| Event | data fields and variations |
|---|---|
| lead.created | lead_id, session_id, chatbot_id, name, email, phone, country, region. Inferred/scored leads can also include score, band, category, summary, sentiment, company, external_user_id, qualification and captured_via. |
| conversation.handoff | session_id and chatbot_id. Explicit handoff can include last_message; model-triggered handoff can include question, answer, topic and source. |
| message.unanswered | session_id, chatbot_id, question and answer. |
| ticket.created | ticket_id, subject, contact_id, email, name and session_id. |
| booking.created | booking_id, chatbot_id, name, email, phone and requested_slot. |
Delivery and duplicate handling
Delivery is best effort with a 10-second request timeout and no durable automatic retry queue. Redirects and private destinations are rejected. The dashboard shows the last delivery status/time rather than a complete delivery ledger.
- Acknowledge valid events promptly and move slow work to your own queue.
- Use event type plus the relevant resource ID and your own operation rules to avoid duplicate effects. There is no promised unique event_id in the current envelope.
- For missed events, reconcile against the relevant dashboard or supported public API instead of assuming automatic replay.
- Select a specific bot for bot-specific events, or all bots when that is the intended scope.