My App

POST /api/v1/voice-webhook

Central voice webhook handler for Telnyx call lifecycle events

Voice Webhook

Processes all Telnyx call lifecycle events — call initiated, answered, ended, transcription complete, etc. Updates call records, triggers post-call actions (GHL notes, tags, ingestion).

Volume: ~6K runs/week | Auth: None (Telnyx webhook)

Request

POST /api/v1/voice-webhook
Content-Type: application/json

Body Parameters

FieldTypeRequiredDescription
call_idstringTelnyx call ID
eventstringEvent type (see below)
callobjectFull call object from Telnyx
transcriptstringCall transcript
summarystringAI-generated call summary
sentimentstringSentiment analysis result
duration_msnumberCall duration in milliseconds
duration_secondsnumberCall duration in seconds
disconnection_reasonstringWhy the call ended
call_statusstringCurrent call status
recording_urlstringURL to call recording
custom_analysis_dataobjectCustom analysis results
variablesobjectResolved variables from the call
location_idstringGHL location ID
contact_idstringGHL contact ID
assistant_idstringAssistant that handled the call
directionstringinbound or outbound
tostringDestination number
fromstringSource number
call_typestringType of call
campaign_idstringCampaign ID
public_log_urlstringPublic call log URL
call_successbooleanWhether the call was successful
start_timestampstringISO timestamp of call start
end_timestampstringISO timestamp of call end

Event Types

EventDescription
call_initiatedCall has been placed
call_answeredCall was answered
call_endedCall has ended
call_machine_detectionVoicemail/machine detected
transcription_completeFull transcript available
analysis_completeAI analysis finished

Responses

Missing call_id or event

{ "event": "done", "call_id": "done", "path": "none" }

Call Ended (with post-processing)

{
  "status": "processed",
  "event": "call_ended",
  "call_id": "telnyx_call_uuid",
  "actions": ["call_updated", "ghl_note_added", "tag_applied", "ingested"]
}

Event Recorded

{
  "status": "recorded",
  "event": "call_initiated",
  "call_id": "telnyx_call_uuid"
}

Test with cURL

Call initiated event

curl -X POST http://localhost:3000/api/v1/voice-webhook \
  -H "Content-Type: application/json" \
  -d '{
    "call_id": "call_test_001",
    "event": "call_initiated",
    "direction": "outbound",
    "to": "+15559876543",
    "from": "+15551234567",
    "location_id": "loc_123",
    "assistant_id": "asst_456"
  }'

Call ended event

curl -X POST http://localhost:3000/api/v1/voice-webhook \
  -H "Content-Type: application/json" \
  -d '{
    "call_id": "call_test_001",
    "event": "call_ended",
    "duration_seconds": 180,
    "transcript": "Agent: Hello! How can I help?\nCaller: I need to reschedule...",
    "summary": "Customer called to reschedule appointment",
    "sentiment": "positive",
    "call_success": true,
    "location_id": "loc_123",
    "contact_id": "contact_789",
    "assistant_id": "asst_456"
  }'

Pipeline Flow

  1. Validate call_id and event present
  2. Upsert call record in DB (Prisma)
  3. For call_ended:
    • Fetch SubAccount access token
    • Add GHL contact note with transcript/summary
    • Apply call outcome tag to GHL contact
    • Send to ingestion pipeline
    • Update call record with final data
  4. For other events: record and return

On this page