Skip to main content

Getting Started

This guide walks you through running the adapter, configuring it, and pointing your Twilio app at it without making a single code change to your application.

Set up your Bandwidth account

You'll need a Bandwidth Account with Voice enabled, API Credentials, and a voice application before running the adapter.

Run the adapter

Clone the repository and install dependencies (Node.js 20+):

git clone https://github.com/Bandwidth/bw-voice-adapter.git
cd bw-voice-adapter
npm install

Start the adapter:

npm start # adapter listens on :3000

To run the test suite or typecheck:

npm test # automated tests
npm run typecheck

Configure

The adapter is configured entirely through environment variables. Two credential sets are in play: the Twilio-shaped credentials your app presents to the adapter, and the Bandwidth credentials the adapter uses to reach Bandwidth.

Env varMeaning
PUBLIC_BASE_URLPublic HTTPS base of this adapter (how Bandwidth and your app reach it)
CUSTOMER_VOICE_URLYour Twilio voice webhook — where the adapter asks "what now?" for inbound calls
ADAPTER_ACCOUNT_SID / ADAPTER_AUTH_TOKENWhat your Twilio SDK and webhook-signature validation use
BW_ACCOUNT_IDYour Bandwidth account ID
BW_CLIENT_ID / BW_CLIENT_SECRETBandwidth OAuth2 client credentials (used to reach the Bandwidth Voice API)
BW_APPLICATION_IDYour Bandwidth Voice application ID
WEBHOOK_USER / WEBHOOK_PASSWORDBasic-auth credentials Bandwidth presents on inbound /bw/* webhooks; set the same values as the CallbackCreds on your Bandwidth Voice application

Optional:

Env varMeaning
HOSTListen interface; defaults to 127.0.0.1. Set 0.0.0.0 to expose the adapter (containers/production)
EGRESS_ALLOW_PRIVATE=1Allow outbound fetches to loopback/private ranges (local dev only)
BW_ENVIRONMENTtest targets Bandwidth's test hosts; defaults to prod
ADAPTER_LOG=1Enable request logging
info

The adapter keeps call and recording state in memory and runs as a single instance. A recording must be listed before it can be fetched by SID on a fresh instance.

Point your app at the adapter

No application code changes — only configuration:

  1. Point your Twilio SDK / base URL at the adapter. Backend calls your app makes (calls.create(), recording fetches) now resolve through the adapter's Twilio-compatible facade at PUBLIC_BASE_URL.
  2. Point your TwiML webhooks at the adapter. The URLs your voice logic serves (inbound call handler, Gather actions) are what the adapter fetches as it translates each step.
  3. Point a Bandwidth Voice application callback at {PUBLIC_BASE_URL}/bw/initiate. This is how Bandwidth hands inbound calls to the adapter to begin translation. The Bandwidth Voice application's CallbackCreds must match WEBHOOK_USER/WEBHOOK_PASSWORD, or the adapter will reject the callbacks with 401.

Run your existing app unchanged. Its calls now flow over Bandwidth's network.

Verify before you cut over

Before pointing production traffic at the adapter, run a pre-flight check to see which features map cleanly and which need attention:

npm run preflight -- examples/full-pv-app

This prints a migration-complexity score and a per-feature works-as-is / heads-up / blocker breakdown. Swap in a path to your own app to check your real TwiML.

For a walkthrough of migration patterns, the REST facade, callbacks, and the Migration Preflight playground, see the use cases guide.