This guide explains how to exercise the two phone-related channels of this repo on your machine. Both require a public HTTPS (and for Twilio, WSS) URL, so you will use a tunnel (ngrok, Cloudflare Tunnel, localtunnel, etc.).
- Backend running (
cd backend && npm run dev), default port4000 - Optional: open
http://localhost:4000/status(or your tunnel host) to confirm which channels and webhooks are active before placing test calls OPENAI_API_KEYwith access to the Realtime / phone features you use- A tunnel that gives you
https://something.example(and the matchingwss://host for Twilio Media Streams)
- Twilio requests TwiML from your server:
POST/GET https://<host>/twilio-phone/incoming-call - Twilio opens a WebSocket to
TWILIO_WEBHOOK_URL(must bewss://...in production; for local tunnels,wss://<same-ngrok-host>/twilio-phone/media-stream)
TWILIO_PHONE_ENABLE=true
TWILIO_WEBHOOK_URL=wss://YOUR_TUNNEL_HOST/twilio-phone/media-stream
OPENAI_API_KEY=sk-...
OPENAI_MODEL=gpt-realtime-1.5Example with ngrok:
ngrok http 4000Copy the HTTPS URL (e.g. https://abc123.ngrok-free.app). Your WebSocket URL is the same host with wss://:
wss://abc123.ngrok-free.app/twilio-phone/media-stream
Set TWILIO_WEBHOOK_URL to that wss://.../twilio-phone/media-stream value.
- Phone number → Voice configuration
- A call comes in: Webhook URL
https://abc123.ngrok-free.app/twilio-phone/incoming-call, HTTP POST (GET also works with this app)
- Place a test call to the Twilio number.
- Backend logs should show
[TwilioPhone]lines and MCP/OpenAI connection logs. - Implementation entry points:
src/service/twilio-phone/(initTwilioPhoneChannel)src/foundation/websocket/endpoints/twilio-phone/
This path is different from Twilio: audio goes Connect → OpenAI over SIP; your Node app only receives the HTTP webhook from OpenAI and then calls accept + the OpenAI Realtime WebSocket for tools/session events.
- OpenAI sends
POST https://<your-backend>/amazon-connect-phone/incoming-call(unless you changeAMAZON_CONNECT_PHONE_WEBHOOK_BASE_PATH) - Your app responds and drives the call via the Realtime Calls API (see
src/service/amazon-connect-phone/openai-sip-webhook/)
AMAZON_CONNECT_PHONE_ENABLE=true
OPENAI_API_KEY=sk-...
OPENAI_MODEL=gpt-realtime-1.5
# Optional: custom path
# AMAZON_CONNECT_PHONE_WEBHOOK_BASE_PATH=/amazon-connect-phoneOptional Amazon Connect contact attributes when the model hangs up (SDK):
AMAZON_CONNECT_SDK_ENABLE=true
AMAZON_CONNECT_INSTANCE_ID=your-instance-id
AWS_REGION=us-east-1
AWS_ACCESS_KEY_ID=...
AWS_SECRET_ACCESS_KEY=...Same idea as Twilio: expose port 4000 and use the HTTPS URL as the base for the OpenAI webhook.
Example webhook URL you register in the OpenAI dashboard (Realtime / SIP / phone integration):
https://abc123.ngrok-free.app/amazon-connect-phone/incoming-call
Exact clicks change often; you typically:
- OpenAI: Complete SIP / phone onboarding so OpenAI gives you a SIP endpoint and lets you set the webhook URL above for
realtime.call.incoming. - Amazon Connect: Use a SIP connection (or SIP rule / external transfer pattern) so calls can reach OpenAI’s SIP trunk as described in OpenAI’s Connect integration guide.
- User-to-User (UUI) / attributes: If you pass hex-encoded JSON in the SIP
User-to-Userheader, this repo decodes it inopenai-sip-webhook/webhook/incoming-call.ts(same idea asphone-sales-ai-copilot).
Use AWS and OpenAI documentation as the source of truth for trunk FQDN, authentication, and Connect contact flow blocks.
- Trigger a test call through Connect into OpenAI SIP.
- Your tunnel should show a POST to
.../twilio-phone/incoming-call(Twilio) or.../amazon-connect-phone/incoming-call(Connect + OpenAI). - Backend logs should include
[AmazonConnectPhone] realtime.call.incoming receivedand accept/WS logs.
- Channel bootstrap:
src/service/amazon-connect-phone/index.ts(initAmazonConnectPhoneChannel) - Webhook + accept + WS:
src/service/amazon-connect-phone/openai-sip-webhook/ - Connect SDK helper:
src/foundation/amazon-connect/
| Item | Twilio channel | Amazon Connect + OpenAI SIP channel |
|---|---|---|
| This repo serves | TwiML + /twilio-phone/media-stream WS |
Only OpenAI webhook + OpenAI Realtime WS to OpenAI |
| Audio path | Twilio ↔ your server ↔ OpenAI | Connect ↔ OpenAI SIP ↔ OpenAI (your server is control-plane) |
| Env flags | TWILIO_PHONE_ENABLE, TWILIO_WEBHOOK_URL |
AMAZON_CONNECT_PHONE_ENABLE |
| Tunnel needs | https + wss to same host |
https for webhook |
See also: Architecture and Amazon Connect + OpenAI webhook.