SMS Provider Connectors¶
Floh supports two SMS providers as built-in connectors: Twilio (primary) and Vonage (secondary). Both support general SMS messaging and OTP verification via their respective Verify APIs.
Twilio¶
Setup¶
- Create a Twilio account at twilio.com.
- Note your Account SID and Auth Token from the Twilio Console dashboard.
- Purchase or configure a phone number (long code, toll-free, or short code) with SMS capability.
- In Floh Admin → Connectors, create a new connector of type twilio.
- Fill in the connection config:
accountSid— Your Twilio Account SIDauthToken— Your Twilio Auth Token (stored encrypted)fromNumber— The Twilio phone number to send from (E.164 format, e.g.+14155551234)verifyServiceSid(optional) — A Twilio Verify Service SID to enable provider-managed OTP mode
Twilio Verify (Optional)¶
When verifyServiceSid is configured, the verify_contact step with deliveryChannel: "sms" delegates OTP issuance and verification to Twilio's Verify API instead of self-issuing codes. Benefits:
- Carrier-level fraud signals (SIM-swap detection)
- Provider-side attempt budgets and per-number throttling
- Voice and email fallback channels (configured on the Verify Service)
To set up:
- In the Twilio Console, navigate to Verify → Services and create a service.
- Copy the Service SID (starts with
VA...). - Paste it into the connector's
verifyServiceSidfield.
Without verifyServiceSid, OTPs are self-issued (generated, hashed, and dispatched by Floh).
Webhook Configuration¶
Configure Twilio to send delivery status callbacks and inbound messages to Floh:
- Status Callback URL:
https://<your-floh-domain>/api/sms/webhook/<connectorId> - Inbound Message URL:
https://<your-floh-domain>/api/sms/inbound/<connectorId>
Set these on your Twilio phone number's configuration page under "Messaging" → "A message comes in" (for inbound) and per-message via the API (for status callbacks — Floh sets this automatically on each send).
Twilio webhooks are authenticated via X-Twilio-Signature (HMAC-SHA1 over the callback URL + sorted form parameters, using the connector's authToken). Floh verifies this signature using crypto.timingSafeEqual before processing any webhook payload. Unsigned or mismatched requests are rejected with HTTP 403.
A2P 10DLC Registration (US)¶
For US-destined messages from local long codes, carriers require A2P 10DLC registration:
- Register your brand in the Twilio Console under Messaging → Trust Hub → Brands.
- Create a Campaign (use case) under Messaging → Trust Hub → Campaigns.
- Associate your Twilio phone number with the campaign.
Without registration, US carriers will filter messages from unregistered 10DLC numbers. Toll-free and short code numbers have separate registration processes.
Vonage¶
Setup¶
- Create a Vonage account at vonage.com.
- Note your API Key and API Secret from the Vonage Dashboard.
- Purchase or configure a virtual number with SMS capability.
- In Floh Admin → Connectors, create a new connector of type vonage.
- Fill in the connection config:
apiKey(required) — Your Vonage API keyapiSecret(required) — Your Vonage API secret (stored encrypted)from(required) — Default sender: either an E.164 phone number (e.g.+14155551234) or an alphanumeric sender ID (2–11 characters, e.g.FlohAlerts) depending on country and carrier agreementsigningSecret(required for webhooks) — Webhook signing secret for JWT verification of inbound/status callbacks (stored encrypted). If absent, Vonage webhook routes reject all requests for this connectorapplicationId(optional) — Vonage Application ID, required for Vonage Verify v2 flowsprivateKey(optional) — Application private key PEM, required for Vonage Verify v2 flows (stored encrypted)
Vonage Verify v2 (Optional)¶
When both applicationId and privateKey are configured on the connector, the verify_contact step automatically uses Vonage Verify v2 for provider-managed OTP mode. Implicit activation: unlike Twilio (which requires an explicit verifyServiceSid), Vonage activates provider-verify mode as soon as the Verify credentials are present. To use Vonage for basic SMS only (without provider-managed OTP), leave applicationId and privateKey empty.
Benefits of Vonage Verify v2:
- Server-side rate limiting and attempt budgets
- Fraud detection signals
- Silent auth and other advanced channels (if configured on the Vonage Application)
Webhook Configuration¶
Configure Vonage to send status callbacks and inbound messages to Floh:
- Status URL:
https://<your-floh-domain>/api/sms/webhook/<connectorId> - Inbound URL:
https://<your-floh-domain>/api/sms/inbound/<connectorId>
Set these on your Vonage Application's Messages capability settings.
Vonage webhooks are authenticated via JWT (HS256) signed with the signingSecret. Floh verifies the signature including the iat claim (rejects tokens older than 5 minutes).
A2P 10DLC Registration (US)¶
US carriers require A2P 10DLC registration for local long codes, regardless of provider:
- Register your brand in the Vonage Dashboard under Trust & Safety → Brands.
- Create a Campaign for your use case.
- Associate your Vonage virtual number with the campaign.
The process mirrors Twilio's — without registration, US carriers will filter messages from unregistered 10DLC numbers.
Opt-Out Compliance¶
Both providers require opt-out compliance for US/UK/EU messaging:
- STOP keyword handling: Floh automatically processes inbound
STOP,STOPALL,UNSUBSCRIBE,CANCEL,END, andQUITmessages. Recipients who send these are recorded in the opt-out store and will not receive further messages. The platform-internalcritical_alertcategory bypasses opt-out by design (see Critical Alert Hook below). - START/UNSTOP: Recipients can re-subscribe by sending
START,YES, orUNSTOP. - Opt-out is per-connector: A recipient who opts out of one connector's number can still receive messages from a different connector. Note: TCPA opt-outs attach to the recipient–brand relationship, not to a specific phone number. If your organization uses multiple SMS connectors under the same brand, operators are responsible for ensuring cross-connector suppression (e.g. by configuring all connectors to use the same sender number, or by maintaining an external suppression list). A platform-wide opt-out store is tracked in #446.
Quiet Hours¶
Quiet hours are not currently enforced by Floh (#445). Workflow authors should use condition steps or scheduling to avoid sending non-urgent messages outside business hours for the recipient's timezone.
Which Provider to Choose¶
| Criteria | Twilio | Vonage |
|---|---|---|
| Global coverage | Excellent | Excellent |
| Verify API (OTP) | Verify v2 (mature) | Verify v2 |
| Delivery receipts | Real-time webhooks | Real-time webhooks |
| Test credentials | Yes (magic numbers) | Yes (sandbox) |
| Pricing | Current rates | Current rates |
| A2P 10DLC support | Full, integrated | Full, integrated |
Recommendation: Use Twilio as the primary connector for its mature ecosystem and test tooling. Add Vonage as a secondary for multi-vendor resilience or procurement diversity.
Critical Alert Hook¶
The CriticalAlertService reuses whichever SMS connector is named in the system settings (Admin → Critical Alerts → SMS Connector). It dispatches platform-level alerts for:
- Connector authentication failures (consecutive 401s exceeding threshold)
- Stuck critical-severity workflow runs
- Webhook signature verification failure spikes
Recipients of critical alerts are restricted to the on-call phone numbers configured in Admin → Critical Alerts → Recipients; they are never drawn from workflow contact lists or the opt-out store. Critical alerts bypass opt-out checks and are rate-limited per event type (default 15-minute cooldown) plus per recipient (60-second cooldown). They are off by default and must be explicitly enabled.