Using SendiMessage with Vapi
Vapi runs the AI phone call. SendiMessage handles what happens on text afterward: your backend sends a confirmation, link, or follow-up on a managed line, and the customer's reply returns as a signed webhook your workflow can act on.
There is no native Vapi connector — the integration is a standard API-plus-webhook pattern, wired through your own backend. That keeps the two systems cleanly separated: Vapi owns the voice interaction; SendiMessage owns the messaging transport.
What this integration enables
Architecture
- Vapi call endsVapi fires its end-of-call-report webhook
- Your backendReceives the Vapi event and decides whether to text
- SendiMessage APIPOST /send-message — the follow-up is queued on your line
- Customer receives the messageiMessage where supported, SMS fallback where configured
- Customer repliesThe answer arrives on the same line and thread
- Signed receive webhookSendiMessage posts the reply to your endpoint
- Your workflow continuesConfirm, reschedule, or escalate — the loop stays in your application
Example request
// Your application (not SendiMessage) decides what to say.const res = await fetch("https://api.sendimessage.com/v1/send-message", {method: "POST",headers: {"X-API-Key": process.env.SENDIMESSAGE_API_KEY,"X-API-Secret": process.env.SENDIMESSAGE_API_SECRET,"Content-Type": "application/json",// Idempotency-Key derived from your own record id keeps a// retried automation from double-texting the customer."Idempotency-Key": callId,},body: JSON.stringify({ number: customer.phone, content: agentReply }),});const { message_handle } = await res.json(); // store this on your record
Runs in your backend when the call-ended event fires. Derive Idempotency-Key from the call id so a retry never double-sends.
Limitations and honest notes
- iMessage delivery is available on supported messaging lines and destinations. Recipients without iMessage receive SMS when fallback is configured — never assume universal iMessage availability.
- Messages are accepted asynchronously — the API returns status QUEUED and final status arrives via webhook or the message endpoints.
- No official SDK for this ecosystem yet — the example uses plain HTTP against the REST API. Official SDKs are published for JavaScript/TypeScript (npm: sendimessage), Python (PyPI: sendimessage), PHP (Composer: sendimessage/sdk), and Go (github.com/sendimessage/sendimessage-go). Every SDK is dependency-free and covers the full public API surface.
- SendiMessage does not integrate with Vapi natively; you wire the Vapi call-ended event to your backend, and your backend calls SendiMessage.
- SendiMessage sends and receives messages — it does not run the AI voice call, transcription, or model. Those stay in your stack.
Security considerations
- Do not place SendiMessage API credentials directly in browser code. Send requests through your own server route or backend.
- Keep your API key server-side, in environment variables or a secrets manager — never in client code, CRM front-end scripts, or repositories.
- Verify the signature header on every incoming webhook before trusting the event.
- Scope keys per environment and rotate them if they are ever exposed.
Frequently asked questions
Is this an official Vapi integration?
Where does the AI logic live?
Related integrations
Ready to connect Vapi?
Request a messaging line and a SendiMessage integration specialist will review your Vapi workflow and guide the setup.