The AI receptionist uses function calling to take action during a call. Every intent maps to one of four action types, and the AI picks the right one from the description you write.
The three built-in intents
Every new tenant gets these three seeded automatically:
talk_to_human— caller asks to speak with a person, or the AI cannot resolve the request. Transfers the call to your persona’svoice_handoff_number.leave_message— caller wants the owner to call them back. The summary email at end-of-call is tagged as a voicemail.end_call— caller is finished. The call ends.
You can edit their descriptions or disable them via PATCH /v1/voice/intents/:id. You cannot rename them — the name is the function-call identifier exposed to the AI.
Custom intents
A custom intent is what lets the AI do business-specific work. Examples:
book_appointment— capture date / time / party size and POST to a webhook.quote_price— answer a price question from a knowledge base entry.escalate_to_owner— transfer to a different number than the default for VIP cases.
Action types
action | Behavior |
|---|---|
transfer | Transfers the call. Destination is always the persona’s voice_handoff_number — the AI cannot supply a number. |
message | Records the request as a voicemail-style intent. Surfaces in the post-call summary. |
webhook | POSTs the call context + intent args to your endpoint with HMAC-SHA256 signature. |
end_call | Ends the call after a short acknowledgement. |
action_config schema
// transfer
{ }
// message
{ }
// webhook
{ "url": "https://your-app.example.com/voice/book" }
// HTTPS only. Private/reserved IP ranges are blocked at runtime.
// end_call
{ }
Webhook payload
{
"call_id": "01HXY3M0KEXAMPLECALLID",
"tenant_id": "01HXY3M0KEXAMPLETENANT",
"intent": "book_appointment",
"args": { "date": "2026-05-12", "time": "14:00", "party_size": 4 },
"from_number": "+14155551234"
}
Headers:
x-senderz-event: voice.intentx-senderz-signature: <hex HMAC-SHA256 of body using INTERNAL_AUTH_SECRET>
Verify the signature server-side before acting on the payload.
Language scoping
Each intent has a language field — en, es-MX, tr-TR, or all. Custom intents only show up in the AI’s tool list for matching languages. Built-ins are always all.
If you have an English-only menu, set language: "en". If you want it available regardless of what the caller speaks, leave it all.
Confidence + fallback
When the AI’s confidence in matching an intent is below the persona’s confidence_threshold (default 1.0), it falls back to talk_to_human rather than guessing. Tune the threshold per persona via PUT /v1/ai/persona.