How-to

Twilio integration

Complete guide to integrating Twilio for outbound campaigns, inbound call handling, recording, and warm transfers.

Prerequisites

  1. Twilio account — Sign up at twilio.com and note your Account SID and Auth Token.
  2. Phone numbers — Purchase one or more Twilio phone numbers with voice capability enabled.
  3. Webhook access — Your Breeze Buddy server must be reachable from the public internet (or via ngrok in development).
  4. Register numbers — Add your Twilio numbers via the Numbers API with provider: "twilio".
Environment VariableDescription
TWILIO_ACCOUNT_SIDYour Twilio Account SID
TWILIO_AUTH_TOKENYour Twilio Auth Token
TWILIO_PHONE_NUMBERDefault outbound caller ID (optional)

Outbound calls

Twilio outbound calls support two modes depending on whether pod isolation is enabled:

With Pod Isolation (Production)

calls.create(url=webhook)
Smart Router allocates pod
Returns TwiML with pod WS URL
WebSocket audio stream
Voice Pipeline

Without Pod Isolation (Development)

calls.create(twiml=inline)
Static WebSocket URL
WebSocket audio stream
Voice Pipeline

TwiML configuration

The TwiML response instructs Twilio to open a bidirectional WebSocket stream to the voice pipeline:

twiml-response.xml
xml
<Response>
  <Connect>
    <Stream url="wss://your-domain.com/agent/voice/breeze-buddy/ws/twilio">
      <Parameter name="lead_id" value="uuid-of-lead" />
    </Stream>
  </Connect>
</Response>

Stream Parameters

The lead_id parameter is passed as WebSocket metadata when the stream connects. The pipeline uses it to look up the template, variables, and configuration.

WebSocket endpoint

WS /agent/voice/breeze-buddy/ws/twilio
ParameterValue
Encodingμ-law (G.711)
Sample Rate8000 Hz
ChannelsMono
Frame formatBase64 in JSON

Callbacks

POST /twilio/callback/details
POST /twilio/callback/status
POST /twilio/callback/twiml-fallback
CallbackEndpointPurpose
RecordingPOST /twilio/callback/detailsDelivers the recording URL
StatusPOST /twilio/callback/statusReports call outcome (completed, no-answer, busy, failed)
TwiML FallbackPOST /twilio/callback/twiml-fallbackServes fallback TwiML when Smart Router is unavailable

Recording

Twilio supports native call recording via the record=True parameter:

twilio_outbound.py
python
client.calls.create(
    to=customer_number,
    from_=outbound_number,
    twiml=twiml_response,
    record=True,
    recording_status_callback=f"{base_url}/twilio/callback/details",
    status_callback=f"{base_url}/twilio/callback/status"
)

Error handling & retry logic

StatusAction
completedLead marked FINISHED — recording stored
no-answerLead marked RETRY — re-enters backlog after cooldown
busyLead marked RETRY — re-enters backlog after cooldown
failedLead marked RETRY — logged for investigation
canceledLead marked RETRY — typically a system cancellation

Retry Limits

Retries are governed by the template’s max_retries setting. Once exhausted, the lead moves to FINISHED with an appropriate failure outcome.

Warm transfer

Twilio warm transfer uses the Conference API for a seamless handoff:

AI triggers transfer
Customer placed in conference
Agent dialed into conference
AI disconnects
Customer + Agent continue

No Audio Gap

With the Conference API, the customer experiences minimal interruption while the live agent is being connected.

Trial Account Limitations

Twilio trial accounts can only call verified phone numbers and include a “trial” prefix in TTS. Upgrade your account before running production campaigns.

Next steps

Was this helpful?