BE VOICEby Binary Elements

For developers

API keys and basics

Every request to the BE Voice API and the MCP server is signed in with an API key from your console. This page covers getting a key and the rules every request shares.

How to get an API key

  1. Sign in to the console and open Settings → Integrations.
  2. Under API keys, click + New API key.
  3. Give it a Name that says where it's used, such as Booking app or Office assistant, then click Create.
  4. Copy the key straight away and store it somewhere safe, such as your app's secret store. It is shown once only.
  5. Click Done.
The New API key dialog with the name Booking app typed in, and Cancel and Create buttons
Name the key after the app that will use it.
The API keys panel listing the Booking app key by its first characters, when it was created, Active status and a Revoke button
Afterwards the console shows only the key's first characters, so you can tell keys apart.

How to revoke a key

  1. Open Settings → Integrations.
  2. Find the key under API keys and click Revoke, then confirm.

Anything using that key stops working immediately: requests answer 401 unauthorized. Revoked keys stay in the list, marked Revoked. If a key may have leaked, revoke it and make a new one.

Your app can also manage keys with a key: POST /v1/tenants/{account_id}/api-keys with {"name": "…"} returns a new key once, GET lists them and DELETE …/api-keys/{key_id} revokes one. Your account ID (it starts tnt_) is under Settings → Business.

Sending requests

Base address
https://voice.binaryelements.com. The API is under /v1/ and the MCP server is at /mcp.
Sign-in
Send the key in every request: Authorization: Bearer bevk_xxxxxxxx…. Keys start with bevk_. A missing, wrong or revoked key gets 401.
JSON
Request bodies are JSON (send Content-Type: application/json), up to 128 KB. Field names you don't need can be left out, but unknown fields are refused with 400 invalid_json, so a typo never goes unnoticed. Replies are JSON in UTF-8, with times in RFC 3339.
Phone numbers
In E.164: +61400000000, not 0400 000 000.
Your account only
A key sees only your business's calls and settings. Asking for something that isn't yours answers 404, the same as something that doesn't exist.
curl https://voice.binaryelements.com/v1/calls/cal_7h2kq9m4x8pz3vd61wtn \
  -H "Authorization: Bearer $BE_VOICE_KEY"

Errors

Every error has the same shape: a stable code for your program and a message for people.

HTTP/1.1 422 Unprocessable Entity
{"error": {"code": "do_not_call", "message": "+61400000000 is on this account's do-not-call list"}}
StatusWhat it means
400invalid_json: the body isn't JSON, or has a field the endpoint doesn't take.
401unauthorized: no key, a malformed header, or a wrong or revoked key.
403module_off: the feature isn't part of your account (see below).
404not_found: no such thing on your account.
409The request doesn't fit the call's state now, such as call_ended or not_live.
422A value was refused. The code says which: invalid_to, invalid_task, do_not_call and so on. Each endpoint's guide lists its codes.
429tenant_busy: your account already has as many calls going out at once as it allows. Try again when one ends.
500internal: something went wrong on our side. Try again; if it keeps happening, contact us.

Placing a call only once: Idempotency-Key

A network error can leave you unsure whether a call was placed. Send an Idempotency-Key header (any unique string up to 255 characters, such as a UUID or your own job ID) with POST /v1/calls:

  • The first request places the call and answers 201.
  • The same key with the same body returns the original call with 200. Nobody is rung twice.
  • The same key with a different body is refused: 422 idempotency_mismatch.
curl https://voice.binaryelements.com/v1/calls \
  -H "Authorization: Bearer $BE_VOICE_KEY" \
  -H "Idempotency-Key: booking-48213-reminder" \
  -d @call.json

IDs

IDs are opaque strings with a prefix that says what they are. Store them as text; don't parse them.

tnt_…
Your account.
cal_…
A call.
evt_…
A webhook event. Use it to spot a delivery you've already handled.
key_…, msg_…, agt_…, evt_…
An API key, a message, an AI agent, a webhook event.

Rate limits

To keep things fair and to stop a runaway script, the API and MCP have two limits:

LimitStandardCounted for
Requests300 a minuteEach API key, and each connected app, separately.
Calls placed30 a minuteYour whole account, through the API and MCP together.

Over a limit, the request is refused with 429 rate_limited and a Retry-After header saying how many seconds to wait. Wait that long and try again; an Idempotency-Key makes retrying a call safe. Through MCP, place_call returns a tool error saying when to try again, and the assistant can wait and retry. If your account needs higher limits, contact us. Using the console isn't limited.

Other limits you might meet:

  • Calls at once. Your account may have a limit on calls going out at the same time. A call over it is refused with 429 tenant_busy; nothing is queued.
  • Polling. Rather than asking for a call's result over and over, use ?wait= on the result (see Follow, steer and get results) or a webhook.
  • Sizes. Each field of a call's brief has its own limit, listed in Place an AI call.

Seeing your usage

Settings → Integrations → API and MCP usage shows, for the dates you choose, how many requests were made, how many were over the limit and how many calls were placed. Group it by key or connected app, by channel (API or MCP) or by day, and click Export CSV to download it.

The API and MCP usage panel grouped by key or app, listing Booking app with 6 requests and ChatGPT (connected app) with 3, none over the limit
Usage by key or connected app, with the limits underneath.

Your keys can read the same report: GET /v1/reports/api-usage, or /v1/reports/api-usage.csv for a CSV. Each account sees only its own usage.

What your account needs

To useYour account needs
Placing calls with a task or callback_url, GET /v1/calls/{id}/result, POST /v1/calls/{id}/steer, and the MCP serverCalls through the API and MCP
Reading a call (GET /v1/calls/{id}), hanging up, listing your calls, listing voices, managing your keysAny API key
Your AI agent using your API during a call; campaigns from your systemAI agents, and Campaigns for campaigns. See Integrations for agents.

Without the feature, the API answers 403 module_off with a message naming it. If your account doesn't include it, contact us.

Still stuck? Contact us and tell us which page you were on.