Skip to content

Webhooks

A webhook is a web address of yours. When something happens in VoDialer, we send a message to it. Messages are signed, so your system can check they are ours. See verify signatures.

  1. Open Setup, then Integrations, then Connections. Under “Connect something”, find Webhooks and press Connect.
  2. Fill in Address to call. It must be a public http or https address.
  3. Fill in Events to send, one per line. For everything, type vd.>.
  4. Optional: tick the campaigns under Only these campaigns. Leave all unticked for every campaign.
  5. Leave Send full phone numbers off unless you need them. See below.
  6. Press Connect. A box shows Your signing secret, which starts with whsec_. Copy it now. It is shown once.
  7. Press Test on the new connection. We send a signed vd.test.ping event and the row says whether your address answered with a 2xx code.

Names have the form vd.group.event. A * matches one part. A > at the end matches everything after it. You can list up to 100 names.

You write You get
vd.call.ended Only that event.
vd.call.* Every call event.
vd.journey.> Every event about a person’s journey.
vd.> Every event.

Some events you will likely want:

Event When
vd.call.placed, vd.call.answered, vd.call.ended A call starts, is answered, ends.
vd.call.recording_stored A recording is saved.
vd.journey.fact_recorded The bot learns a fact.
vd.journey.disposition_set A result is saved for a person.
vd.journey.transfer_requested, transfer_bridged, transfer_completed A hand-over starts, connects, ends.
vd.journey.closed A person’s journey ends.
vd.compliance.dnc_added A number is added to the do-not-call list.
vd.qa.scored A call is scored.

The full list with examples is in the event catalogue and on the For developers tab. A campaign filter skips events that carry no campaign, such as transcript lines.

Each message is a POST with a JSON body, the same envelope for every event: id, tenant_id, at, source, subject and data.

POST /hooks/vodialer HTTP/1.1
Content-Type: application/json
X-VoDialer-Event: vd.call.placed
X-VoDialer-Delivery: 0192b2c0-0000-7000-8000-0000000000f2
X-VoDialer-Signature: t=1791208991,v1=9c1f2ab6…
{
"id": "0192b2c0-0000-7000-8000-0000000000ee",
"tenant_id": "0192b2c0-0000-7000-8000-00000000000a",
"at": "2026-10-05T14:03:11Z",
"source": "call-control",
"subject": "vd.call.placed",
"data": {
"call_id": "0192b2c0-0000-7000-8000-0000000000c1",
"campaign_id": "0192b2c0-0000-7000-8000-0000000000e1",
"journey_id": "0192b2c0-0000-7000-8000-0000000000d1",
"direction": "outbound",
"from_number": "…0143",
"to_number": "…0718"
}
}

X-VoDialer-Delivery stays the same on every retry of one message. The signature time is fresh on every try.

Without Send full phone numbers, any phone number in a message becomes … and its last four digits. That covers keys such as to_number and any value that is a plain + number. Spoken words in transcript lines are not scanned, so a number a person says aloud stays in the text.

Your address must answer with a 2xx code within 10 seconds. Any other answer, including a 4xx, is a failure.

  • Retries wait 10 seconds, then double each time up to 2 hours, with 25% of random spread. If you send Retry-After in seconds, we wait that long, up to an hour.
  • After 24 hours the message is given up. Retry in the Delivery log (Try again in the older layout) gives it a fresh 24 hours.
  • After 50 failures in a row, the connection shows “Needs attention” and stops. Switch on re-arms it.

We call only public addresses. We refuse private, loopback, link-local and internal addresses, numeric addresses, and addresses that contain a user name or password. We do not follow redirects: a 3xx is a failure.