Developers · API
v1Phone numbers
Every agent answers on one phone number. This page covers requesting a number for an agent through the API, reading its status, and what happens until it is connected.
How it works
- Create the agent (Agents). Its
regiondecides which number it gets —krfor a Korean 050 number,cafor a Canadian number. - Request a number with
POST /v1/agents/{agentId}/number. The response is a receipt withstatus: "queued", not a number. - Poll
GET /v1/agents/{agentId}/number, or watchnumberonGET /v1/agents/{agentId}— it staysnulluntil the number is connected. - Once
statusisconnected, the agent answers calls onnumber.
Request a number
POST /v1/agents/{agentId}/number — opens with early access; until then, request on the early-access page. No body is required; the agent's region picks the number. Add an Idempotency-Key header so a retry cannot queue a second request (API reference).
curl -s -X POST "$LS_BASE_URL/v1/agents/$AGENT_ID/number" \
-H "Authorization: Bearer $LS_API_KEY" \
-H "Idempotency-Key: number-dental-00123-1"const BASE_URL = process.env.LS_BASE_URL;
const API_KEY = process.env.LS_API_KEY;
const res = await fetch(`${BASE_URL}/v1/agents/${agentId}/number`, {
method: 'POST',
headers: {
Authorization: `Bearer ${API_KEY}`,
'Idempotency-Key': 'number-dental-00123-1',
},
});
const receipt = await res.json();
console.log(res.status, receipt.status); // 202 queuedimport os, requests
BASE_URL = os.environ["LS_BASE_URL"]
API_KEY = os.environ["LS_API_KEY"]
res = requests.post(
f"{BASE_URL}/v1/agents/{agent_id}/number",
headers={
"Authorization": f"Bearer {API_KEY}",
"Idempotency-Key": "number-dental-00123-1",
},
)
receipt = res.json()
print(res.status_code, receipt["status"]) # 202 queued202 Accepted
{
"requestId": "num_8f2c1d40",
"agentId": "8f2c1d40-5b7a-4c31-9e08-1a2b3c4d5e6f",
"region": "kr",
"status": "queued",
"number": null,
"requestedAt": "2026-10-08T02:15:00.000Z",
"estimatedBy": "2026-10-09T09:00:00.000Z",
"earlyAccess": true,
"message": "Number provisioning is in early access. Numbers are connected within one business day. Poll this resource or watch number on the agent."
}
The response also carries Location: /v1/agents/{agentId}/number and Retry-After: 3600 — poll no more often than that.
Read the status
GET /v1/agents/{agentId}/number — the same object, with the current status.
curl -s "$LS_BASE_URL/v1/agents/$AGENT_ID/number" \
-H "Authorization: Bearer $LS_API_KEY"const status = await (
await fetch(`${BASE_URL}/v1/agents/${agentId}/number`, {
headers: { Authorization: `Bearer ${API_KEY}` },
})
).json();
if (status.status === 'connected') console.log(status.number);status = requests.get(
f"{BASE_URL}/v1/agents/{agent_id}/number",
headers={"Authorization": f"Bearer {API_KEY}"},
).json()
if status["status"] == "connected":
print(status["number"])Once connected:
{
"requestId": "num_8f2c1d40",
"agentId": "8f2c1d40-5b7a-4c31-9e08-1a2b3c4d5e6f",
"region": "kr",
"status": "connected",
"number": "050312345678",
"requestedAt": "2026-10-08T02:15:00.000Z",
"connectedAt": "2026-10-09T01:40:12.000Z"
}
The same number appears in number on GET /v1/agents/{agentId}, so code that already reads the agent needs no change.
Statuses
status | Meaning | What to do |
|---|---|---|
queued | Accepted, waiting to be provisioned | Poll, or wait for the email |
verification_required | A business verification must be completed before a Korean number can be assigned | Open verification.url in the response and complete it; the request continues on its own |
provisioning | A number is being connected | Poll |
connected | The agent answers on number | Make a test call (Quickstart, step 6) |
failed | We could not connect a number | message says why; email support@livespeech.ai with the agentId |
Business days follow the agent's region — Korea Standard Time for kr, Pacific Time for ca.
Calling it twice
POSTwhile a request isqueuedorprovisioninganswers200with the existing receipt — nothing new is queued, so retries are safe even without an idempotency key.POSTon an agent that already has a number answers409 NUMBER_ALREADY_CONNECTEDwith the current number.GETbefore any request answers404 NUMBER_NOT_REQUESTED.
Failure responses
| Status | code | When | What to do |
|---|---|---|---|
404 | NUMBER_NOT_REQUESTED | Reading status before any request | Request a number first |
409 | NUMBER_ALREADY_CONNECTED | The agent already has a number | Nothing to do — the response carries it |
409 | AGENT_TERMINATED | The agent is terminated | Create a new agent |
422 | REGION_UNSUPPORTED | No numbers in the agent's region yet | kr and ca are available during early access |
401 and 403 follow the rules in Errors & limits. Another account's agent answers 403 without revealing whether it exists.
Releasing a number
Releasing a number from an agent is not in the API yet. To release one, email support@livespeech.ai with the agentId; terminating an agent with a number attached is held with 502 CARRIER_RELEASE_FAILED until the number is released (Agents).