Securing Twilio Credentials and Building Multi-Tenant SMS Relay Infrastructure
This session focused on establishing secure credential management for Twilio integration and laying groundwork for a cascading SMS relay system. The problem: a critical carrier-level limitation preventing phone line forwarding required us to implement application-layer message routing instead. Here's the technical approach we took.
The Problem: Carrier Constraints Force Application-Layer Routing
Our initial architecture assumed we could configure SIM-based call forwarding for a customer support line, with a cascading fallback chain: primary responder → secondary responder → backup (858-335-4807). The carrier informed us this wasn't possible at their infrastructure level—they couldn't layer multiple forwarding rules in the way we needed.
The solution: implement a Twilio-based SMS and call relay at the application layer. This gives us:
- Programmatic control over message routing logic
- Ability to log and audit all communications
- Flexible cascading rules without carrier constraints
- Webhook-driven integration with our existing calendar/scheduling system
Credential Storage: Environment Isolation and Access Control
We added Twilio credentials to the shared secrets file at /Users/cb/Documents/repos/.secrets/repos.env, securing the file with restrictive permissions:
chmod 600 /Users/cb/Documents/repos/.secrets/repos.env
The 600 permission (read/write for owner only) ensures that only the user who owns the process can read these credentials, preventing accidental exposure through world-readable file permissions. This is essential for any environment containing:
TWILIO_ACCOUNT_SIDTWILIO_AUTH_TOKEN- Any other API credentials with account-level access
We documented the credential locations in /Users/cb/.claude/projects/-Users-cb-Documents-repos/memory/reference_twilio_credentials.md so future development sessions can quickly locate them without exposing values in logs or chat history.
Architecture: Why Twilio for SMS Relay?
Twilio provides several advantages over a bare HTTP-based SMS gateway:
- Webhook flexibility: Inbound messages trigger HTTP POST callbacks to our application, allowing real-time conditional routing
- Stateful conversation tracking: We can bind message threads to calendar events and crew assignments
- Compliance and audit trails: Twilio maintains detailed logs of all messages, useful for dispute resolution and regulatory compliance
- Failover and redundancy: Twilio handles infrastructure resilience; we don't manage carrier relationships directly
- Multi-region support: For future expansion, Twilio's global network is already provisioned
Intended Integration Points
Once the relay is built, Twilio webhooks will tie into our existing Google Apps Script infrastructure:
-
Crew Magic-Link Flow: When a captain receives an inbound SMS via the relay, a webhook triggers a GAS function that looks up the crew member in
ShipCaptainCrew, generates a time-limited magic link, and SMS's it back—all without exposing passwords or links in email. - Calendar Event Binding: Inbound messages are tagged with the event ID from our Jada booking calendar. This allows the maintenance hub to display SMS conversations alongside event details.
- Cascading Availability Check: Before routing to a responder, the relay queries the calendar to check their availability status (on duty, on call, or off). If primary is unavailable, it automatically escalates.
Why Not AWS SNS or Sendgrid?
We evaluated these alternatives:
- AWS SNS: Great for push notifications and bulk SMS, but doesn't provide the robust webhook/IVR/call-routing features we need for a customer support relay. Would require us to build that logic ourselves.
- Sendgrid: Primarily email-focused; their SMS offering is newer and lacks the call-handling features.
- Twilio: Mature, well-documented, and purpose-built for conversational communications. The Programmable Voice and Programmable Messaging APIs are exactly what we need.
Next Steps: Building the Relay Logic
With credentials now secured and documented, the next phase involves:
- Webhook Handler: Create a GAS endpoint (or Node.js handler if scaling requires it) that receives Twilio webhooks. This will parse inbound messages and route them based on event ID and responder availability.
- Availability Query: Build the logic that checks our Google Calendar against responder schedules. The jada-agent daemon already maintains calendar state; we'll query it via the same API it uses internally.
- Response Generation: Templates for automated acknowledgments ("Your message has been received. Sergio will respond within 2 hours.") and escalation notices ("Primary responder unavailable. Escalating to backup.").
- Audit Logging: Store all inbound and outbound messages in a Firestore collection (or Google Sheets for simplicity) so the maintenance hub can display conversation history.
- E2E Testing: Simulate crew magic-link flow: send SMS → relay receives it → generates link → sends it back → crew clicks link → claims role in Firestore.
Security Considerations
Since credentials are now in place, we need to ensure they're never logged or exposed:
- Environment variables are loaded at process startup, not read from files at runtime
- All Twilio SDK calls use the credentials from environment, never hardcoded
- Webhook endpoints are rate-limited and validated with Twilio's request-signing mechanism
- Response templates never echo back user phone numbers or message content in logs
Conclusion
This session removed the primary blocker preventing us from implementing a sophisticated SMS relay. By securing credentials appropriately and documenting their locations, we've enabled the next phase: webhook integration and cascading availability logic. The architecture leverages Twilio's maturity in conversational communications while keeping our application layer focused on business logic (availability checking, event binding, crew management) rather than telecom infrastructure.
Next action: Build the webhook handler in GAS that ties Twilio inbound messages to our calendar and crew systems. This unblocks the e2e test for ShipCaptainCrew and the cascading SMS relay for the support line.