REST API
A single JSON API for voice + outbound.
JSON over HTTPS for Link AI Voice agents, Mailer campaigns, and the shared workspace primitives. Endpoint catalog, request shape, idempotency keys, and error semantics.
Every endpoint speaks JSON, lives under a single versioned base URL, and is documented below. The shape rarely surprises — if you have integrated against Stripe or Resend, you already know the rhythm.
Base URL & versioning
| Environment | Base URL |
|---|---|
| Production | https://api.linkaiil.com/v1 |
| Staging | https://staging.api.linkaiil.com/v1 |
The /v1 prefix is the major version. Breaking changes ship behind a new prefix (/v2) — the previous version stays online for at least twelve months with security fixes only.
Conventions
- Authentication. Bearer tokens or Clerk session tokens. See Authentication.
- Content type.
application/json; charset=utf-8on requests and responses. Hebrew + Arabic strings travel as plain UTF-8 — no escaping needed. - Identifiers. Every object id carries a typed prefix:
ws_,agt_,call_,cmp_,lead_,evt_. - Idempotency. Send an
Idempotency-Keyheader on anyPOST. Retries with the same key return the cached result for 24 hours. - Pagination. List endpoints accept
limit(default 25, max 100) andcursor. Responses includenext_cursor(or null when exhausted).
Voice endpoints
| Method | Path | Description |
|---|---|---|
GET | /v1/voice/agents | List voice agents in the workspace. |
GET | /v1/voice/agents/:id | Retrieve a single agent (prompt, voice, escalation rules). |
POST | /v1/voice/calls | Place an outbound call. |
GET | /v1/voice/calls/:id | Retrieve a call (status, transcript, recording URL). |
GET | /v1/voice/calls | List calls (filter by agent, status, date range). |
POSTComing soon | /v1/voice/agents | Programmatically create an agent. Dashboard-only for now. |
Example: place a call
curl https://api.linkaiil.com/v1/voice/calls \
-H "Authorization: Bearer $LINKAI_TOKEN" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{
"agent_id": "agt_5fd1a02b",
"to": "+972541234567",
"metadata": { "lead_id": "lead_9182" }
}'{
"id": "call_01HFE9X1G6...",
"agent_id": "agt_5fd1a02b",
"to": "+972541234567",
"status": "queued",
"created_at": "2026-05-21T09:14:22Z",
"metadata": { "lead_id": "lead_9182" }
}Mailer endpoints
| Method | Path | Description |
|---|---|---|
GET | /v1/mailer/campaigns | List campaigns. |
GET | /v1/mailer/campaigns/:id | Retrieve a campaign (state, lead counts, throttle). |
POST | /v1/mailer/campaigns/:id/leads | Push one or more leads into a campaign. |
GET | /v1/mailer/leads/:id | Retrieve a lead (research summary, generated emails, reply state). |
POST | /v1/mailer/leads/:id/research | Kick off (or re-run) deep research for a lead. |
PATCHComing soon | /v1/mailer/leads/:id/emails/:seq | Approve or edit a generated email before send. |
Example: push a lead
await linkai.mailer.campaigns.leads.create("cmp_8fa21b09", {
email: "richard@avishealth.com",
first_name: "Richard",
last_name: "Avis",
company: "Avis Health",
title: "Executive Chairman",
// Free-form metadata travels with every webhook for this lead.
metadata: { source: "import_2026_05" },
});Workspace endpoints
| Method | Path | Description |
|---|---|---|
GET | /v1/whoami | Resolve the calling credential to a workspace + plan + scopes. |
GET | /v1/workspace/usage | Current billing-cycle usage (calls minutes, mailer sends). |
GET | /v1/workspace/members | List workspace members and their roles. |
GET | /v1/webhooks | List configured webhook endpoints (see Webhooks). |
Error envelope
Errors share a single envelope. Always check the HTTP status first, then branch on the error.code field — the message is meant for humans, not pattern matching.
{
"error": {
"code": "validation_failed",
"message": "Field 'to' must be an E.164 phone number.",
"field": "to",
"request_id": "req_01HFE9X..."
}
}400— validation_failed, invalid_request.401— invalid_token, missing_scope.402— plan_limit_exceeded (upgrade to continue).404— resource_not_found.409— conflict (idempotency replay collision).429— rate_limited (see rate limits).5xx— server_error. Retry with backoff; therequest_idis what support will ask for.