API Documentation

Authentication

All API requests require authentication using an API key. Include your API key in the Authorization header:

Authorization: Bearer va_your_api_key_here

You can create and manage API keys in the API Keys section.

Base URL

/api/v1

Rate Limiting

API requests are rate-limited to 1000 requests per minute per API key.

Rate limit headers are included in responses:

  • X-RateLimit-Limit - Maximum requests allowed
  • X-RateLimit-Remaining - Remaining requests in window
  • X-RateLimit-Reset - Unix timestamp when limit resets

Response Format

All responses follow a standard format:

Success Response:

{
  "success": true,
  "data": { ... },
  "meta": {
    "timestamp": "2024-01-01T00:00:00.000Z",
    "request_id": "uuid-here"
  }
}

Error Response:

{
  "success": false,
  "error": "Error message",
  "details": { ... },
  "meta": {
    "timestamp": "2024-01-01T00:00:00.000Z",
    "request_id": "uuid-here"
  }
}

Endpoints

Agents

GET/agents

List all agents for your organization

Query Parameters:

  • enabled - Filter by enabled status (true/false)
  • limit - Number of results (default: 50, max: 100)
  • offset - Pagination offset (default: 0)
Example Request
curl -X GET "https://your-domain.com/api/v1/agents?enabled=true&limit=10" \
  -H "Authorization: Bearer va_your_api_key"
GET/agents/:id

Get agent details by ID

POST/agents

Create a new agent

Example Request
curl -X POST "https://your-domain.com/api/v1/agents" \
  -H "Authorization: Bearer va_your_api_key" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Customer Service Agent",
    "system_prompt": "You are a helpful customer service agent...",
    "description": "Handles customer inquiries",
    "starting_message": "Hello! How can I help you today?",
    "enabled": true,
    "voice_settings": {
      "stability": 0.5,
      "similarity_boost": 0.75
    }
  }'

Request Body Fields:

  • name (required) - Agent name
  • system_prompt (required) - System prompt for the agent
  • description (optional) - Agent description
  • starting_message (optional) - Initial message to start conversations
  • enabled (optional) - Whether agent is enabled (default: true)
  • voice_settings (optional) - ElevenLabs voice settings object
  • dtmf_rules (optional) - DTMF input rules configuration
PATCH/agents/:id

Update an agent (partial update - only include fields to update)

Updatable Fields:

  • name - Agent name
  • description - Agent description
  • system_prompt - System prompt
  • starting_message - Initial message
  • voice_settings - Voice settings
  • dtmf_rules - DTMF rules
  • enabled - Enable/disable status
DELETE/agents/:id

Delete an agent (only if no active tasks)

Tasks

GET/tasks

List tasks with optional filtering

Query Parameters:

  • agent_id - Filter by agent ID
  • status - Filter by status (pending, in_progress, completed, failed)
  • limit - Number of results (default: 50, max: 100)
  • offset - Pagination offset (default: 0)
POST/tasks

Create a new task

Example Request
curl -X POST "https://your-domain.com/api/v1/tasks" \
  -H "Authorization: Bearer va_your_api_key" \
  -H "Content-Type: application/json" \
  -d '{
    "agent_id": "uuid-here",
    "name": "Call customer",
    "to_number": "+1234567890",
    "description": "Follow up call",
    "starting_message": "Hello, this is a call from our company",
    "context_data": {
      "customer_name": "John Doe",
      "order_id": "12345"
    },
    "priority": 0,
    "scheduled_at": null,
    "webhook_url": "https://your-app.com/webhooks",
    "webhook_events": ["call_started", "call_completed"]
  }'
GET/tasks/:id

Get task details including agent information

PATCH/tasks/:id

Update a task (only allowed for pending tasks)

Updatable Fields:

  • name - Task name
  • description - Task description
  • to_number - Phone number (E.164 format)
  • starting_message - Initial message
  • context_data - Context data object
  • priority - Priority level
  • scheduled_at - Scheduled execution time
  • webhook_url - Webhook URL
  • webhook_events - Array of webhook events
DELETE/tasks/:id

Delete a task (only allowed for pending or failed tasks)

POST/tasks/:id/execute

Execute a pending task (initiate phone call)

Example Response
{
  "success": true,
  "data": {
    "call_id": "uuid-here",
    "message": "Call initiated"
  }
}
POST/tasks/:id/reset

Reset a task status to pending (allows re-execution)

Only works for tasks that are not already pending

Calls

GET/calls

List calls with optional filtering

Query Parameters:

  • task_id - Filter by task ID
  • agent_id - Filter by agent ID
  • status - Filter by status (initiated, in_progress, completed, failed)
  • limit - Number of results (default: 50, max: 100)
  • offset - Pagination offset (default: 0)
GET/calls/:id

Get call details including transcript and report

GET/calls/:id/transcript

Get call transcript (returns stored transcript if available)

POST/calls/:id/transcript

Manually fetch and process transcript from ElevenLabs API

Fetches transcript from ElevenLabs, processes it, generates report, and stores in database. Returns transcript, extracted data, and report.

GET/calls/:id/report

Get call report (generated on-the-fly if not exists)

GET/calls/:id/recording

Get audio recording URL for a completed call

Returns a proxy URL that handles authentication. The recording must be available (call status: completed or failed).

Example Request
curl -X GET "https://your-domain.com/api/v1/calls/{call_id}/recording" \
  -H "Authorization: Bearer va_your_api_key"

Note: Use /calls/:id/recording/stream to stream the audio directly.

GET/calls/:id/live

Get WebSocket connection information for live transcript streaming

POST/calls/:id/end

End/terminate an active call

Example Request
curl -X POST "https://your-domain.com/api/v1/calls/{call_id}/end" \
  -H "Authorization: Bearer va_your_api_key"
POST/calls/:id/cancel

Cancel an active call (marks as failed)

Live Transcript Streaming

Connect to a WebSocket endpoint to receive real-time transcript updates during active calls.

Connection

First, get the WebSocket URL for a call:

GET /api/v1/calls/:id/live
Authorization: Bearer va_your_api_key

Response:
{
  "success": true,
  "data": {
    "websocket_url": "ws://localhost:3008/ws/calls/{call_id}",
    "call_id": "{call_id}",
    "temp_token": "base64_encoded_token",
    "connection_info": {
      "url": "ws://localhost:3008/ws/calls/{call_id}",
      "auth_method": "query_param",
      "auth_param": "api_key",
      "temp_auth_param": "session_token",
      "example": "ws://localhost:3008/ws/calls/{call_id}?api_key=YOUR_API_KEY",
      "example_session": "ws://localhost:3008/ws/calls/{call_id}?session_token=TEMP_TOKEN",
      "message_format": "json",
      "message_types": [
        "connected",
        "transcript_update",
        "call_status_update",
        "error"
      ]
    }
  }
}

Authentication: You can connect using either your API key (?api_key=YOUR_API_KEY) or a temporary session token (?session_token=TEMP_TOKEN) returned in the response. The session token is valid for 5 minutes and is useful for browser-based applications.

WebSocket Connection

Connect to the WebSocket URL with your API key or session token:

// Using API key
const ws = new WebSocket('ws://localhost:3008/ws/calls/{call_id}?api_key=YOUR_API_KEY');

// Or using session token (from /calls/:id/live response)
const ws = new WebSocket('ws://localhost:3008/ws/calls/{call_id}?session_token=TEMP_TOKEN');

ws.on('message', (data) => {
  const message = JSON.parse(data);
  
  switch(message.type) {
    case 'connected':
      console.log('Connected to live transcript stream');
      break;
    case 'transcript_update':
      console.log('Transcript update:', message.data.transcript);
      break;
    case 'call_status_update':
      console.log('Call status:', message.data.status);
      break;
    case 'error':
      console.error('Error:', message.error);
      break;
  }
});

Message Types

  • connected - Sent when connection is established
  • transcript_update - Real-time transcript updates during the call
  • call_status_update - Call status changes (in_progress, completed, failed)
  • error - Error messages

Keepalive

Send a ping message to keep the connection alive:

ws.send(JSON.stringify({ type: 'ping' }));

Webhooks

You can configure webhooks on tasks to receive notifications when call events occur.

Configuration

When creating or updating a task, include:

  • webhook_url - Your webhook endpoint URL (must be HTTPS)
  • webhook_events - Array of events to subscribe to:
    • call_started - When call is initiated
    • call_completed - When call completes successfully
    • call_failed - When call fails

Webhook Payload

{
  "event_type": "call_completed",
  "task_id": "uuid-here",
  "call_id": "uuid-here",
  "status": "completed",
  "data": {
    "transcript_excerpt": "...",
    "report_excerpt": "..."
  }
}

Retry Logic

Webhooks are sent with a 10-second timeout. If your endpoint doesn't respond within 10 seconds, the webhook is considered failed. Failed webhooks are logged but do not block call processing.

Error Codes

400 - Bad Request (validation error)
401 - Unauthorized (invalid or missing API key)
403 - Forbidden (insufficient permissions)
404 - Not Found (resource doesn't exist)
429 - Too Many Requests (rate limit exceeded)
500 - Internal Server Error
503 - Service Unavailable (external service error)

Additional Notes

Field Naming

  • Agent prompts use system_prompt (not prompt)
  • Tasks and agents support starting_message for initial conversation messages
  • Voice settings use voice_settings object (ElevenLabs format)
  • DTMF rules use dtmf_rules object

Phone Number Format

All phone numbers must be in E.164 format: +[country code][number]

Example: +1234567890 (US), +442071234567 (UK)

Task Status

  • pending - Task created but not executed
  • in_progress - Call is active
  • completed - Call completed successfully
  • failed - Call failed or was cancelled

Call Status

  • initiated - Call initiated but not yet connected
  • in_progress - Call is active
  • completed - Call completed successfully
  • failed - Call failed or was cancelled

Recording Access

Recording URLs returned by the API are proxy endpoints that handle authentication automatically. For streaming audio directly, use the /calls/:id/recording/stream endpoint.

Session vs API Key Authentication

Most endpoints use API key authentication. However, some management endpoints require session authentication:

  • API Keys management (GET, POST, DELETE, regenerate)
  • Organizations management (GET, PATCH, create)
  • Users management (GET, invite)

These endpoints use session cookies instead of API keys for security reasons.

Code Examples

JavaScript (Fetch)

const response = await fetch('https://your-domain.com/api/v1/agents', {
  headers: {
    'Authorization': 'Bearer va_your_api_key',
    'Content-Type': 'application/json'
  }
});

const data = await response.json();
console.log(data);

Python (Requests)

import requests

headers = {
    'Authorization': 'Bearer va_your_api_key',
    'Content-Type': 'application/json'
}

response = requests.get(
    'https://your-domain.com/api/v1/agents',
    headers=headers
)

data = response.json()
print(data)

cURL

curl -X GET "https://your-domain.com/api/v1/agents" \
  -H "Authorization: Bearer va_your_api_key"