Skip to main content

SMS Delivery Reports

Delivery reports (DLRs) provide real-time feedback on the status of every SMS you send through Exotel. This guide covers how to configure, receive, and interpret delivery reports.

What Are Delivery Reports?

A delivery report is a status notification that tells you whether an SMS was successfully delivered to the recipient's handset, is still in transit, or has failed. Exotel supports two methods for receiving delivery reports:

MethodDescriptionBest For
Webhook CallbacksExotel pushes status updates to your serverReal-time processing, production systems
API PollingYou query the SMS Details API for statusAd-hoc checks, debugging
DashboardView reports in the Exotel web consoleManual review, reporting
tip

Webhook callbacks are the recommended approach for production systems. They provide near-instant status updates without the overhead of polling. See SMS Webhooks for detailed setup instructions.

Delivery Report Flow

Your App → Exotel API → Operator → Handset

Status Callback ← Operator DLR

Your Webhook Endpoint
  1. Message Submitted -- Your app sends an SMS via the Exotel API.
  2. Queued -- Exotel accepts the message and queues it for delivery.
  3. Sent to Operator -- Exotel transmits the message to the telecom operator.
  4. Delivered / Failed -- The operator confirms delivery to the handset or reports a failure.
  5. Callback Sent -- Exotel forwards the delivery status to your configured webhook URL.

Configuring Delivery Report Callbacks

Per-Message Callback

Set the StatusCallback parameter when sending an SMS to receive the delivery report at a specific URL:

curl -X POST "https://<api_key>:<api_token>@api.exotel.com/v1/Accounts/<account_sid>/Sms/send" \
-d "From=EXOTL" \
-d "To=+919876543210" \
-d "Body=Your OTP is 123456" \
-d "DltEntityId=1234567890123" \
-d "DltTemplateId=1107160000000012345" \
-d "StatusCallback=https://your-server.com/sms/status"

Account-Level Callback

Configure a default callback URL for all SMS in your Exotel dashboard:

  1. Log in to the Exotel Dashboard.
  2. Navigate to Settings > SMS Settings.
  3. Enter your default Status Callback URL.
  4. Save the settings.
note

Per-message callbacks override the account-level callback URL. If you set StatusCallback in the API request, it takes precedence.

Delivery Report Payload

When Exotel sends a delivery report to your webhook, the payload includes the following fields:

FieldDescriptionExample
SmsSidUnique identifier for the SMSsms_sid_value
ToRecipient phone number+919876543210
FromSender IDEXOTL
StatusCurrent delivery statusdelivered
DetailedStatusDetailed status descriptionDELIVERED_TO_HANDSET
DetailedStatusCodeNumeric status code20000
SentAtTimestamp when SMS was sent2025-01-15 10:30:00
UpdatedAtTimestamp of the status update2025-01-15 10:30:05

Sample Callback Payload

{
"SmsSid": "a1b2c3d4e5f6",
"AccountSid": "your_account_sid",
"From": "EXOTL",
"To": "+919876543210",
"Body": "Your OTP is 123456",
"Status": "delivered",
"DetailedStatus": "DELIVERED_TO_HANDSET",
"DetailedStatusCode": 20000,
"SentAt": "2025-01-15T10:30:00+05:30",
"UpdatedAt": "2025-01-15T10:30:05+05:30"
}

Delivery Statuses

StatusDetailedStatusDescription
queuedQUEUEDMessage accepted and queued for sending
sendingSENDINGMessage is being transmitted to the operator
submittedSUBMITTED_TO_CARRIERMessage submitted to the telecom operator
sentSENTMessage sent by the operator (awaiting handset confirmation)
deliveredDELIVERED_TO_HANDSETMessage delivered to the recipient's phone
failedVarious (see below)Message delivery failed
expiredEXPIREDOperator could not deliver within the validity period

Failed Status Codes

DetailedStatusCodeCauseResolution
FAILED_DLT_TEMPLATE30001Message does not match DLT templateEnsure message body matches the approved template exactly
FAILED_DLT_ENTITY30002Invalid DLT entity IDVerify your entity ID in your DLT portal account
FAILED_INVALID_SENDER30003Sender ID not registeredRegister and approve your sender ID on the DLT portal
FAILED_DND30004Recipient on DND registryUse transactional SMS for critical messages
FAILED_INVALID_NUMBER30005Invalid or unreachable phone numberVerify the recipient's phone number
FAILED_OPERATOR30010Operator-side delivery failureRetry after some time; contact support for persistent failures
FAILED_EXPIRED30011Message validity period expiredRecipient may have been out of coverage; resend if needed
FAILED_UNKNOWN30099Unknown failureContact Exotel support with the SmsSid

For the complete list of status codes, see SMS Status Codes.

Polling via API

If you prefer to check delivery status on demand, use the SMS Details API:

curl "https://<api_key>:<api_token>@api.exotel.com/v1/Accounts/<account_sid>/Sms/Messages/<sms_sid>"

Response:

{
"SMSMessage": {
"Sid": "a1b2c3d4e5f6",
"Status": "delivered",
"DetailedStatus": "DELIVERED_TO_HANDSET",
"DetailedStatusCode": 20000,
"DateCreated": "2025-01-15T10:30:00+05:30",
"DateUpdated": "2025-01-15T10:30:05+05:30",
"From": "EXOTL",
"To": "+919876543210",
"Body": "Your OTP is 123456",
"Direction": "outbound-api",
"Price": "0.20"
}
}

Delivery Report Timing

Delivery reports are typically received within seconds, but timing depends on the telecom operator:

ScenarioExpected Time
Successful delivery1-15 seconds
Handset off / out of coverageUp to 24-72 hours (then expires)
DLT validation failureImmediate (within seconds)
DND rejectionImmediate (within seconds)
Operator failure1-60 minutes
warning

Do not assume a message has failed if you have not received a delivery report within a few seconds. Some operators may take several minutes to return a DLR, especially during high-traffic periods.

Best Practices

  1. Always configure status callbacks -- Do not rely solely on manual checks. Automate delivery tracking with webhooks.
  2. Handle retries gracefully -- If your webhook endpoint is down, Exotel retries the callback. Ensure your endpoint is idempotent.
  3. Log all delivery reports -- Store delivery reports with the SmsSid for audit trails and debugging.
  4. Monitor failed statuses -- Set up alerts for elevated failure rates, which may indicate DLT configuration issues.
  5. Use detailed status codes -- The DetailedStatus field provides more granular information than the top-level Status field.

Next Steps