Skip to content
EN
Open app

API

5 min read
Copy as Markdown
View as MarkdownOpen the raw .md file.md

One outbound call from your system — a CRM event, a form, a missed-call callback. A list on a schedule is Campaigns, not this endpoint.

The agent’s Outgoing settings still apply. This request picks the number, the agent, and optional extra context for this call.

  1. Plan includes Allow Outbound Calls.
  2. API key with the Calls group.
  3. A trunk (or VoIP phone) to dial from — Your own carrier / Voice Logica numbers.
  4. The agent id — from the agent URL on My Agents, or Copy on a campaign row.
POST https://api.voicelogica.ai/api/v1/phones/calls/initiate-call
x-api-key: YOUR_API_KEY
Content-Type: application/json

Resellers: optional x-company-id to act on a subsidiary. Without it, the key’s own company is used.

Send destinationNumber and agentId. Send sipTrunkId or voipPhoneId unless the company already has an outbound route / default trunk that can carry the call — if neither is sent and no trunk can be resolved, the API returns that no active SIP trunk or VoIP phone was specified.

Trunk (usual):

Terminal window
curl -X POST https://api.voicelogica.ai/api/v1/phones/calls/initiate-call \
-H "x-api-key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"sipTrunkId": "your_sip_trunk_id",
"destinationNumber": "+14155552671",
"agentId": "your_agent_id"
}'

VoIP phone id still works — the server resolves it to a trunk.

Success is { "callId": "..." }. If the destination is outside 09:00–21:00 local time, you may get "scheduled": true plus scheduleTime and reason. Open Calls and listen.

destinationNumber in E.164 (+14155552671).

Required for an AI outbound call

FieldWhat it does
destinationNumberNumber to call.
agentIdAgent that talks. Required for AI outbound; optional only for isInternalCall.

Call source — send one, or rely on the company outbound default

FieldWhat it does
sipTrunkIdTrunk from Telephony → Trunks. Prefer this.
voipPhoneIdLegacy line id. Resolved to a trunk.
callerIdE.164 or SIP URI shown to the recipient. Must be a number that trunk is allowed to present.

This call only

FieldWhat it does
contextForAiAppended to the system prompt for this call.
dynamicVariablesString key/value pairs the prompt can use ({{customer_name}}).
superVariablesTyped values: { placeholder, value, type } — text / number / boolean / date / time.
metadataYour tracking. Stored on the call. Keys starting scenario_ are stripped.
emailAddressWhere to send the summary / recording.
welcomeMessageOverrideSpoken instead of the agent greeting.
isWelcomeMessageAIGeneratedAI writes the greeting for this call.
scheduledAtISO date. Call later instead of now.
maxRetries1–3 if busy / no answer / voicemail. Default 3.
retryDelayMinutes30–1440. Default 30.
additionalPhoneNumbersExtra numbers on the same request.

Do not send fromNumber. The public contract is sipTrunkId / voipPhoneId.

Inbound is never restricted.

  • Time (on) — 09:00–21:00 in the destination country’s local time. Outside that, the call is blocked or scheduled. Bypass: overrideTimeRestriction: true.
  • Day (on) — weekends / holidays may be blocked by destination country. Bypass: overrideDayRestriction: true.
  • Anti-harassment (off unless you send useAntiHarassmentProtection: true) — max 3 successful and 3 failed calls per number per day, 1 hour between successful calls, max 5 successful per week, no duplicate active/scheduled call. Campaign Allowed test numbers bypass this.

Bypassing time or day rules can break local law. Turn anti-harassment on for any repeated-contact job.

The body is { "error": "<code>", "reason": "<message>" }.

CodeMeaning
call_already_in_progressA live or scheduled call to this number already exists.
agent_not_found / voip_phone_not_foundBad id.
daily_call_limit_reached3 successful calls to this number today (anti-harassment).
failed_call_limit_reached3 failed attempts today.
cooldown_period_activeWait 1 hour after a successful call to this number.
weekly_call_limit_reached5 successful calls this week.
call_already_scheduled / failed_to_schedule_callSchedule conflict.
callee_opted_outThis number asked not to be called again.
insufficient_credits / no_seconds_available / no_channels_available / no_concurrent_calls_availablePlan / credits.
maximum_authentication_attempts_exceededPhone deactivated after repeated auth failures.

402 is billing. 400 is a bad request or a protection. 500 is the calls server — retry later.

const response = await fetch('https://api.voicelogica.ai/api/v1/phones/calls/initiate-call', {
method: 'POST',
headers: { 'x-api-key': 'YOUR_API_KEY', 'Content-Type': 'application/json' },
body: JSON.stringify({
destinationNumber: '+14155552671',
agentId: 'your_agent_id',
sipTrunkId: 'your_sip_trunk_id',
contextForAi: 'Customer asked about order ORD123',
dynamicVariables: { customer_name: 'Ada', order_id: 'ORD123' },
useAntiHarassmentProtection: true,
}),
});
const result = await response.json();
if (result.callId) console.log(result.callId);
else console.error(result.error, result.reason);

Schedule + retries:

{
"destinationNumber": "+14155552671",
"agentId": "your_agent_id",
"sipTrunkId": "your_sip_trunk_id",
"scheduledAt": "2026-09-16T14:30:00Z",
"maxRetries": 2,
"retryDelayMinutes": 120
}

scheduledAt is converted to the destination country’s zone. Protections still apply unless you override them.

  • 400 “no active SIP trunk” — send sipTrunkId, or add a trunk with numbers and an outbound default.
  • scheduled: true when you expected now — destination local time is outside 09:00–21:00.
  • Agent talks over “hello” — Outgoing Who speaks first, not this payload.
  • Call missing on Calls — wrong company (x-company-id), or the request never returned a callId.
fromNumber used to work

The public body is sipTrunkId or voipPhoneId. Send the trunk id from Telephony → Trunks.

I posted now and got scheduled: true

Time or day restriction. Wait for the window, or set overrideTimeRestriction / overrideDayRestriction only if you are allowed to.

Write developers@voicelogica.ai — extra test credits and help on the integration.