Skip to main content

calls

calls.agent_duel

Agent-vs-Agent Test Call

Effects: write

Start an agent-vs-agent VOICE test call: two AI voice agents share one LiveKit room — a 'caller' persona agent pursues a task brief against the 'callee' business agent under test. Use to evaluate booking flows, latency, and conversation quality without a human caller.

The CALLER agent should have an EMPTY voice_greeting (it must stay silent until the callee greets) and voice_filler_enabled=false.
Afterwards inspect both call_ids with agents.traces_list / calls.get_transcript. A subscribe-only listen token is returned for listening in live.

Arguments

ArgumentTypeRequiredDescription
callee_agent_idintegeryesAgent under test (answers and greets first). From agents.list.
caller_agent_idintegeryesCustomer-persona agent that places the call. Must be a different agent, active, with empty voice_greeting.
max_duration_sintegernoHard cap on the call in seconds (30-900, default 300). (min 30.0; max 900.0)
taskstringyesThe caller's brief — objective, persona details (name, phone), and when to end the call. Woven into its prompt as call instructions.

calls.dispatch_agent

Dispatch an agent to any call surface

Effects: external_api

Send a workspace AI agent into a live call — ONE tool for every surface; target decides where: a meet.google.com link → Google Meet bot; a Telegram @group / t.me link / chat_id / t.me/call slug → Telegram group voice chat or conference; 'new' → creates a NEW Telegram conference call and returns its shareable link; a WhatsApp group JID (digits@g.us) → WhatsApp group call; a live session UUID (from calls.list_active), or thread_id of a running call → WAKES the agent on the bot already in that call instead of spawning a second one. For a Meet link the router also checks for a bot already in that meeting and wakes it rather than double-joining. Always pass agent_id (from agents.list). For a live TRANSLATOR use calls.dispatch_translator instead.

Arguments

ArgumentTypeRequiredDescription
agent_idintegeryesID of an active agent in this workspace (from agents.list). Any active agent can be dispatched — a voice trigger is NOT required.
channel_account_idintegernoTelegram routes: workspace Telegram account that joins/founds the call. Optional with exactly one Telegram account; required with several.
greetingstringnoFirst line the agent speaks on a 1:1 call. Omit to use the agent's configured default greeting.
instructionsstringnoTask brief for the agent, e.g. 'take notes and answer questions about the roadmap'. On a spawn it is woven into the voice system prompt; on a wake it is the kickoff turn the agent responds to. OMIT for a generic listening/greeting agent.
start_immediatelybooleannoSpawn routes only: if true the agent starts talking as soon as it joins instead of waiting to be addressed. OMIT (default false) to stay silent until addressed. Wake routes always speak immediately.
targetstringnoWhere to send the agent: a meet.google.com link, a Telegram @group / t.me link / chat_id / t.me/call slug, 'new' for a fresh Telegram conference, a WhatsApp group JID (digits@g.us), or a live session UUID to wake the agent on a running call. Omit only when passing thread_id.
thread_idintegernoInbox thread id of a RUNNING call — wakes the agent on the bot already in it. Alternative to a session UUID target.
titlestringnotarget='new' only: label for the new conference.
vision_modestringnoScreen-share capture mode (Meet + Telegram spawns): 'off', 'on_demand' (agent can call vision_query), 'continuous_0_3fps' (ambient scene captures each turn). OMIT to use 'off' (the default). (one of off, on_demand, continuous_0_3fps)

calls.dispatch_translator

Dispatch a live translator to any call surface

Effects: external_api

Send a live speech translator to a call. target decides where: a meet.google.com link → Google Meet bot; a Telegram @group / t.me link / chat_id → Telegram group voice chat; 'new' (or omitted) → creates a native DialogBrain meeting with translation on and returns the join + guest links; a native meeting call_id or /meeting/ URL → enables translation on that running meeting. Always pass target_language (ISO code); optional app_languages (extra subtitle-only languages), sentence_length (short|medium|long, native only), silent (subtitles without voice, Google Meet only), source_language (the meeting's spoken language, ISO code — improves recognition; omit for autodetect), tts_provider + tts_voice (the translator's voice; omit for the workspace default).

Arguments

ArgumentTypeRequiredDescription
agent_idintegernoGoogle Meet ONLY, and required there: the active agent the bot session is recorded against (calls.send_to_meet needs one). Get it from agents.list. Telegram and native meetings ignore it — they arm translation on a call that already exists.
app_languagesarraynoExtra subtitle-only languages (max 4).
comeback_phrasestringnoAttention-recall phrase.
sentence_lengthstringnoNative meetings only: short|medium|long buffering (default medium).
silentbooleannoGoogle Meet only: true = subtitles without speaking into the call. OMIT for a normal speaking translator.
source_languagestringnoThe call's spoken language (ISO code, e.g. 'en', 'ru'). When set, speech recognition runs in that language's dedicated mode for better accuracy. REQUIRED in practice for languages autodetect does not cover (e.g. 'vi', 'th', 'id', 'tl'). Omit when participants may speak multiple languages (autodetect). All routes.
targetstringnoWhere to send the translator: a meet.google.com link, a Telegram @group / t.me link / chat_id, 'new' for a fresh native meeting, or an existing native meeting call_id or /meeting/ URL. Omit for a new native meeting.
target_languagestringyesPrimary spoken translation target (ISO code, e.g. 'th').
titlestringnonative_new only: meeting title.
tts_providerstringnoTranslator VOICE provider (cartesia, openai, yandex, deepgram, ...). Omit for the workspace default translation voice. Google Meet + native new meetings.
tts_voicestringnoSpecific voice id for tts_provider (e.g. 'alena', 'nova'). Omit for the provider default.

calls.get_transcript

Get Call Transcript

Effects: read

Get the structured transcript and final state of a voice call by call_id. Returns per-turn rows in chronological order, call status (active/completed/failed/abandoned), duration, and an outcome field telling whether the recipient picked up (answered/no_answer/busy/declined/failed/unknown). answered_at is non-null once the recipient picked up. Returns active turns if the call is still in progress.

Arguments

ArgumentTypeRequiredDescription
call_idstringyesCall ID returned by calls.make in _meta.call_id. (max 64.0)

calls.hangup

Hang Up Call

Effects: external_api

Hang up an active voice call by call_id. Use after calls.make when the agent decides to terminate before the callee does, or to abort a stuck call. Idempotent: returns success if the call is already terminal.

Arguments

ArgumentTypeRequiredDescription
call_idstringyesCall ID returned by calls.make in _meta.call_id. (max 64.0)
reasonstringnoShort internal reason for ending the call (e.g. 'campaign timeout'). Stored on voice_sessions.metadata. (max 200.0)

calls.list_active

List Active Calls

Effects: read

List active voice calls in this workspace. Use before calls.make on a Telegram account (only one MTProto call per account at a time) to check whether the line is free.

Arguments

ArgumentTypeRequiredDescription
channelstringnoFilter by voice channel. OMIT to include all channels. (one of telegram, twilio, android)
channel_account_idintegernoFilter by channel_account.id (the calling Telegram account or Twilio number). Combine with channel for a per-line busy check.

calls.list_history

List Call History

Effects: read

Search historical voice calls in this workspace by participant name, contact_id, thread, channel, source, and/or date range. Returns one row per call (NOT per turn) with call_id, duration_seconds, outcome, direction, started_at, source, channel_label, and parent_thread_id (the originating chat thread for Telegram-group / Twilio-outbound / Meet calls). Pair with calls.get_transcript(call_id) for the full per-turn transcript. Use this instead of messages.read_history for cross-thread call queries — group calls and Meet sessions live on per-call sub-threads, not on the parent chat thread.

Arguments

ArgumentTypeRequiredDescription
channelstringnoFilter by message-level channel of the call thread: 'telegram' (1:1 voice or group call sub-thread), 'twilio_voice', 'meet_voice', 'livechat_voice', 'whatsapp' (native WhatsApp calls — these coalesce into the contact's messaging thread). OMIT to include all voice channels. (one of telegram, twilio_voice, meet_voice, livechat_voice, whatsapp)
contact_idstringnoFilter by exact entity_id (from contacts.find). Mutually exclusive with participant_name when both target the same person.
limitintegernoMaximum calls to return (default 20, max 100).
participant_namestringnoFilter to calls whose parent thread has a participant matching this name (substring match against entity.title). Resolves group calls via the parent group's roster, not the per-call thread's speaker list.
sincestringnoISO date or datetime lower bound (inclusive). Default: 90 days ago. Naive timestamps are interpreted as UTC.
sourcestringnoFilter by voice_sessions.source: 'telegram' (1:1 + group), 'whatsapp' (native WhatsApp voice), 'twilio' (PSTN), 'meet' (Google Meet bot), 'livechat' (in-app voice), 'android' (Android device). OMIT to include all sources. (one of telegram, twilio, meet, livechat, android, whatsapp)
thread_idintegernoRestrict to calls on this thread OR with this thread as their originating parent (Telegram group → call sub-thread back-link, Twilio outbound source_thread_id back-link).
untilstringnoISO date or datetime upper bound (inclusive). Default: now.

calls.make

Make Voice Call

Effects: send, external_api

Place an outbound AUDIO/VOICE phone call via Twilio (PSTN) or Telegram (MTProto 1:1 call). Use this any time the user asks to 'call', 'ring', 'phone', 'dial', or have a spoken conversation. Do NOT use messages.send when the user asks to call someone — a call is real-time voice, not a text message. You conduct the conversation as the voice agent using the provided greeting and instructions.

Arguments

ArgumentTypeRequiredDescription
appstringnoAndroid package that places the call (generic — any app with a dispatch recipe, or manual UI dispatch). Example: 'com.whatsapp'. Used only when channel='android'. Ignored for other channels.
channelstringnoVoice transport: 'twilio' or 'telnyx' (phone via PSTN — both require phone_number in E.164; pick the carrier the workspace has connected), 'telegram' (MTProto 1:1 call — requires telegram_user_id, NOT a phone number or thread_id), 'maxru' (Max.ru voice call — requires maxru_user_id), 'android' (Android device voice call — requires phone_number in E.164), or 'whatsapp' (WhatsApp voice call via the workspace's connected WhatsApp account — requires phone_number in E.164). OMIT to auto-select based on the current thread (e.g. inside a Telegram DM → uses 'telegram'). (one of twilio, telnyx, telegram, maxru, android, whatsapp)
contact_idintegernoLINE only: the contact entity ID for storing the confirmed display name after placement. Ignored for other channels/apps.
greetingstringyesThe first sentence the agent speaks immediately when the call connects. ALWAYS provide a greeting — without it the caller hears silence. Keep it short and natural. Example: 'Hi, this is Diana calling from DialogBrain. Do you have a moment to chat?' (max 500.0)
instructionsstringnoWhat to do during the call — objective, questions, tone. The AI generates a natural opening and guides the conversation. Example: 'Call about invoice #1234. Ask if they received it and when payment is expected. Be friendly and professional.' (max 2000.0)
maxru_user_idstringnoDestination Max.ru user/chat ID. Required when channel='maxru'.
phone_numberstringnoDestination phone number in E.164 format (e.g., '+15551234567', '+66812345678'). Required when channel='twilio'.
report_backstringnoWhen to re-invoke you after the call ends. 'on_answer' (default) = only if the call was answered, 'always' = even on missed/failed calls, 'never' = fire and forget. Transcript is always stored regardless of this setting.
skip_dispatchbooleannoSet true after you placed the call manually with the android_* UI tools — skips the automatic recipe and attaches straight to the already-live call. OMIT for the normal automatic dispatch. Used only when channel='android'. Ignored for other channels.
target_display_namestringnoLINE only: the contact's LINE display name to place the voice call to (resolved by the planner from the contact). Ignored for other channels/apps. (max 200.0)
telegram_user_idstringnoDestination Telegram user ID (decimal int64 as string, e.g. '123456789'). Required when channel='telegram'. The caller account must have had prior interaction with this user — a cold contact cannot be reached via voice.
voice_agent_idintegernoID of the agent that conducts the call (an id from agents.list). If omitted, uses the workspace's default voice-capable agent when one exists. Pass this when the call fails with 'No voice agent configured'.

calls.meet_browser

Attach to a meet-bot's Google Meet browser

Effects: external_api

Attach to a Google Meet bot's live browser to diagnose and recover a bot that isn't visibly joining. Pass the meet session's call_id; returns a page_id. Then drive the bot's Meet page with the generic browser tools (browser.snapshot / browser.click / browser.take_screenshot / browser.evaluate / browser.console_messages / browser.network_requests) using that page_id — read the snapshot to see whether the bot is in the lobby, blocked, or admitted, and click guest-side controls to recover a stalled join. Note: host admission ('Admit') happens in the host's own browser and is not present on the bot's page.

Arguments

ArgumentTypeRequiredDescription
call_idstringyesThe meet session's call_id (UUID), e.g. from calls.send_to_meet's session_id or calls.list_active.

calls.mute_translation_tts

Mute/unmute a call's translator TTS

Effects: external_api

Mute or unmute an active call's live-translation TTS. scope='call' (default, Google Meet sessions ONLY): the translator goes silent INSIDE the call — participants hear no bot voice, in-flight audio is cut immediately, but translation audio + subtitles remain available in the app (listen overlay). scope='everywhere' (any channel): stop synthesizing entirely from the next utterance — subtitles only, no audio anywhere. muted=false reverses either. Translation itself keeps running throughout.

Arguments

ArgumentTypeRequiredDescription
call_idstringyesThe active call / Meet session call_id (UUID) — e.g. from calls.send_to_meet's session_id or calls.list_active.
mutedbooleanyestrue to mute, false to unmute.
scopestringno'call' (default; Google Meet only): silent in the call only — app audio + subtitles keep flowing. 'everywhere' (any channel): no TTS synthesis at all (subtitles only). OMIT to use the 'call' default. (one of call, everywhere)

calls.set_translation_language

Set a call's live translation language

Effects: external_api

Change the target language of an active voice/Meet call's live translator on the fly — no hangup or re-dispatch (also arms translator mode if it isn't already on). Pass the call_id and an ISO language code, e.g. 'th' (Thai), 'ru' (Russian), 'es' (Spanish), 'en' (English). Takes effect within ~10ms — speak and the translation switches to the new language.

Arguments

ArgumentTypeRequiredDescription
call_idstringyesThe active call / Meet session call_id (UUID) — e.g. from calls.send_to_meet's session_id or calls.list_active.
languagestringyesTarget language ISO code: 'th' (Thai), 'ru' (Russian), 'es' (Spanish), 'en' (English), etc.

calls.set_translation_languages

Set a call's extra app-only translation languages

Effects: external_api

Set the EXTRA target languages an active voice/Meet call's translator produces for the APP ONLY (subtitles + listenable audio in the inbox — NOT spoken into the call). Operators switch between them in the UI. Pass call_id and app_languages (ISO codes, e.g. ['de','fr']); pass [] to drop all extras. Max 4. The primary spoken language is managed by calls.set_translation_language. Takes effect within ~10ms; new languages translate NEW speech only.

Arguments

ArgumentTypeRequiredDescription
app_languagesarrayyesExtra app-only target languages (ISO codes), e.g. ['de','fr','es']. Pass [] to remove all extras. Max 4.
call_idstringyesThe active call / Meet session call_id (UUID) — e.g. from calls.send_to_meet's session_id or calls.list_active.

calls.transfer

Transfer Phone Call

Effects: external_api

Transfer the current phone call to a person on another number (e.g. 'let me put you through to a manager'). Only works on a live PHONE call, and only to a number the operator has pre-approved for this agent. Say one short sentence to the caller first ('connecting you now'), THEN call this. It rings the destination and returns when they pick up — which can take most of a minute — and only then do you leave the call. If nobody answers you are told so and are still on the line with the caller.

Arguments

ArgumentTypeRequiredDescription
call_idstringnoWhich call to transfer. Omit inside a live voice turn — it is taken from the call. Required over MCP. (max 100.0)
tostringyesThe phone number to transfer the caller to, E.164 (e.g. '+15551234567'). Must be pre-approved for this agent. (max 20.0)

calls.wait

Wait for Call to End

Effects: read

Block until a voice call ends (status changes from 'active') or timeout elapses. Returns ended=true with final state when the call has ended; ended=false on timeout (re-issue to keep waiting). The returned state includes outcome so callers can branch on pickup vs. no-answer (answered/no_answer/busy/declined/failed/unknown). Default timeout 90s; cap 110s — bounded by nginx proxy_read_timeout 120s on /mcp.

Arguments

ArgumentTypeRequiredDescription
call_idstringyesCall ID returned by calls.make in _meta.call_id. (max 64.0)
timeout_secondsintegernoMax seconds to wait. Default 90, cap 110 (bounded below nginx 120s proxy_read_timeout). On expiry returns ended=False with status='active' so the caller can re-issue to keep waiting. (min 5.0; max 110.0)