SMS delivery & webhooks
A POST /messages request returns immediately with a pending status — delivery happens asynchronously. Track the final outcome by polling the message or by receiving status webhooks, and handle the common errors below.
Check message status
Fetch the current state of a message by its id.
GET/messages/{id}
curl https://api.tryzend.com/messages/6884da240f0e633b7b979bff \
-H "x-api-key: YOUR_API_KEY"
Response
{
"id": "6884da240f0e633b7b979bff",
"status": "delivered",
"channel_used": "sms",
"to": "+233593152134",
"body": "Your verification code is: 123456",
"total_cost": 0.02,
"delivery_attempts": [
{
"channel": "sms",
"status": "delivered",
"attempted_at": "2024-01-15T10:30:00Z",
"cost": 0.02
}
],
"created_at": "2024-01-15T10:29:55Z",
"sent_at": "2024-01-15T10:30:00Z",
"delivered_at": "2024-01-15T10:30:05Z"
}
channel_used is the channel that actually delivered the message, and delivery_attempts lists every channel Zend tried — useful when fallback is enabled.
| Status | Meaning |
|---|---|
pending | Queued, not yet sent |
sent | Handed off to the carrier |
delivered | Confirmed delivered to the recipient |
failed | Could not be delivered on any attempted channel |
Retry a failed message
Re-attempt delivery of a message that ended in failed.
PUT/messages/{id}/retry
curl -X PUT https://api.tryzend.com/messages/6884da240f0e633b7b979bff/retry \
-H "x-api-key: YOUR_API_KEY"
Status webhooks
Instead of polling, pass a webhook_url when sending and Zend posts delivery status updates to it as they happen.
{
"to": "+233593152134",
"body": "Your order has been shipped!",
"preferred_channels": ["sms"],
"webhook_url": "https://yourapp.com/webhooks/message-status"
}
Request fields
webhook_urlstring
https URL that receives a POST for each status change on this message.Note
Your endpoint should respond with a
2xx status code to acknowledge receipt.Common errors
SMS sends fail with a 400 Bad Request and a descriptive message. The most frequent cases:
| Error | Status | Cause | Fix |
|---|---|---|---|
| Insufficient credits | 400 | Account balance is below the message cost | Purchase more credits, then retry |
| Invalid phone number | 400 | to isn't a valid international format | Use +233593152134, 233593152134, or 0593152134 |
| Sender ID not approved | 400 | sender_id isn't approved for your account | Use an approved sender ID or omit it to use your default |
Insufficient credits
{
"statusCode": 400,
"message": "Insufficient credits. Required: 0.020, Available: 0.015. Please purchase more credits.",
"error": "Bad Request"
}
Invalid phone number
{
"statusCode": 400,
"message": "Invalid phone number format. Please use international format (e.g., +233593152134)",
"error": "Bad Request"
}
Sender ID not approved
{
"statusCode": 400,
"message": "Sender ID 'INVALID' is not approved. Please use an approved sender ID.",
"error": "Bad Request"
}
Next steps
- Send SMS — sending, sender IDs, and message limits.
- SMS fallback & priority — fall back to WhatsApp or voice so critical messages still land.