twilio, and Fonoster sends the same WebSocket messages Twilio sends. A
Pipecat bot that uses TwilioFrameSerializer runs as it is.
Use this when you already have the bot, or when your framework expects raw audio. To write new call
logic, the Voice SDK is simpler: Fonoster does the speech for you.
What works
With thetwilio protocol, Fonoster speaks the bidirectional Media Streams messages:
- Audio is μ-law at 8000 Hz, mono, base64 in
media.payload, both ways. Caller audio hastrack: "inbound". - Barge-in works the Twilio way.
clearempties the queued audio, and every pendingmarkis echoed back. - Keypresses arrive as
dtmfwithdtmf.track: "inbound_track"anddtmf.digit. - Hanging up: close the WebSocket and Fonoster hangs up the call.
start map to Fonoster’s:
What isn’t supported
Thetwilio protocol carries audio, marks and keypresses only. Fonoster ignores any other message
and the call continues.
- No TwiML. Fonoster doesn’t fetch or run TwiML. The stream’s URL is the WebSocket itself.
- No speech layer. Fonoster doesn’t transcribe the caller or speak text for your bot. Your bot brings its own speech-to-text and text-to-speech, as it does on Twilio. The stream’s voice and speech settings don’t apply.
- No call control. Your bot can’t transfer the call, put it on hold or send keypresses. If you
need those, use the
fonosterprotocol with the Voice SDK. - Audio is μ-law 8 kHz only. The audio format setting applies to
fonosterstreams.
Point Fonoster at your bot
1
Give your bot a public WebSocket address
Fonoster dials your bot from the internet. Deploy the bot, or run it behind a tunnel, and note
the WebSocket URL it serves, such as
wss://bot.example.com/ws. Fonoster won’t dial
localhost or a private IP.2
Create a stream with the twilio protocol
- Dashboard
- SDK
- CLI
- Go to Streams and choose New stream.
- Name it, for example
Pipecat bot. - Enter the bot’s WebSocket address in URL.
- Set Protocol to Twilio.
- Choose Create stream.
3
Point a number at the stream
Go to Numbers, open the number, and under When this number is called, send it to
choose Stream, then your stream. See Numbers and routing for the
SDK and CLI.
4
Call the number
Your bot receives
connected and start, then the caller’s audio, just as it would from
Twilio.Run a Pipecat bot
A Pipecat bot built for Twilio needs no Fonoster-specific code.parse_telephony_websocket
recognizes Fonoster’s start message as Twilio’s, and TwilioFrameSerializer handles the audio,
marks and clear.
The one setting to check is how the bot hangs up. By default, TwilioFrameSerializer hangs up by
calling Twilio’s REST API with your Twilio credentials, which can’t end a Fonoster call. Turn that
off and let the bot close the WebSocket instead. Fonoster hangs up when the socket closes:
bot.py
EndTaskFrame, Pipecat closes the WebSocket and the
call ends. Fonoster’s tests run an unmodified Pipecat bot (pipecat-ai 1.12.0) this way: it hears the
caller, the caller hears it, clear stops playback on barge-in, keypresses reach it, and it hangs
up.
Hang up through the Twilio-compatible endpoint
Hang up through the Twilio-compatible endpoint
Where the operator turns it on, Fonoster also serves Twilio’s hang-up call:
See Twilio compatibility: Hanging up.Closing the socket works on every install, so you don’t need this to hang up.
POST {base}/2010-04-01/Accounts/{accountSid}/Calls/{callSid}.json with Status=completed and
HTTP Basic auth. {accountSid} is your workspace’s access key ID. It answers 200, or 404
with code 20404 when the call has already ended.Your install’s configuration sets how Basic auth is checked:- Workspace API keys: the user is an API key ID (
AP…) and the password its secret. The key must belong to the workspace in the URL. - One fixed pair (on your own install): the user and the URL’s
accountSidare the pair’saccountSid, which must be your workspace’s access key ID, and the password itsauthToken.
auto_hang_up at it with base_url. This example uses a fixed pair:Next steps
Verify request signatures
Check that each connection comes from Fonoster.
Twilio compatibility
Every Media Streams message and field Fonoster sends and accepts.
Build a stream with the Voice SDK
Need transfers or text-in, text-out speech? Use the
fonoster protocol.Numbers and routing
Send a number’s calls to your stream.