# A2P Messaging API errors

The A2P Messaging HTTP API uses standard HTTP status codes. This page lists the ones you will encounter, what they mean and whether a retry is safe.

**Language:** en
**Audience:** developer
**TLDR:** Branch on the HTTP status, not on the message text: most error bodies are JSON with error.message and error.code, but the 429 body is plain text. 400, 401, 402 (out of balance), 403, 404 and 413 mean the request or the account needs fixing and retrying won't help; retry only 429 and 5xx, with exponential backoff starting at 1 second.
**Docs index (every page):** https://staging-instasent-docs-nextjs.oscar-284.workers.dev/llms.txt
**This zone's index:** https://staging-instasent-docs-nextjs.oscar-284.workers.dev/a2p-messaging-api/llms-full.txt
**This page:** https://staging-instasent-docs-nextjs.oscar-284.workers.dev/a2p-messaging-api/http/errors/ (HTML) · https://staging-instasent-docs-nextjs.oscar-284.workers.dev/a2p-messaging-api/http/errors.md (Markdown)

Every response carries a meaningful HTTP status code. A `2xx` means the request was accepted; anything else signals a problem your code should handle explicitly. Most error bodies are JSON with an `error` object that carries a human-readable `message` and the numeric `code`; the exception is `429`, whose body is plain text. Branch your code on the HTTP status, not on the `message` text, which is written for people and can change.

## Status codes

### `400 Bad Request`

The request body is malformed or has the wrong shape. Not retryable — fix the payload first.

```http
HTTP/1.1 400 Bad Request
```

When the body is not valid JSON:

```json
{ "error": { "message": "Invalid JSON", "code": 400 } }
```

When the body of `POST /sms/bulk` is not a JSON array of objects (for example, a single object):

```json
{ "error": { "message": "Body should be a JSON array of objects", "code": 400 } }
```

### `401 Unauthorized`

The token is missing or does not exist (mistyped, rotated or deleted), or the request comes from an IP address outside the token's accepted IPs. Not retryable as is: check the token and the network you call from, and see the [Authentication](/a2p-messaging-api/http/authentication) guide.

```http
HTTP/1.1 401 Unauthorized
```

```json
{ "error": { "message": "No token could be found.", "code": 401 } }
```

### `402 Payment Required`

The account has run out of balance. Not retryable until funds are topped up in the dashboard.

```http
HTTP/1.1 402 Payment Required
```

### `403 Forbidden`

The token exists but cannot be used for this request: it is disabled, the user or account is not enabled or is pending verification, or it is not an A2P Messaging API token (`api_sms`) with HTTP access. `GET /sms/{id}` also returns `403` when the message belongs to another account. Not retryable until the cause is fixed. The `message` differs from one cause to another, so branch on the `403` status rather than parsing the text.

```http
HTTP/1.1 403 Forbidden
```

### `404 Not Found`

The resource (message id, token id, project) does not exist or is not visible to the current token.

```http
HTTP/1.1 404 Not Found
```

### `413 Request Too Large`

The request body exceeds the maximum accepted size. Not retryable — trim the payload.

```http
HTTP/1.1 413 Request Too Large
```

### `429 Too Many Requests`

You hit the per-endpoint rate limit. The body is the plain text `You exceeded the rate limit`, not JSON, so do not try to parse it. The `X-RateLimit-Reset` header says when to retry. See [Rate limits](/a2p-messaging-api/http/rate-limits).

```http
HTTP/1.1 429 Too Many Requests

You exceeded the rate limit
```

### `500 Internal Server Error`

Something broke on our side. Retry with exponential backoff; if the failure persists, contact support with the request id.

```http
HTTP/1.1 500 Internal Server Error
```

## Retry policy

> **Tip**: Retry `429` and `5xx` with exponential backoff, starting at 1 s and capping at a minute or so. Everything in the `4xx` range other than `429` means the request itself is wrong — retrying will not help.

## What's next

- **[Receiving DLRs](/a2p-messaging-api/http/dlrs)** — delivery reporting for messages that did leave the API successfully.
- **[API Reference](/a2p-messaging-api/http/reference)** — per-endpoint responses.

---

This is one page of the Instasent documentation. For the complete machine-readable index of every guide and API reference, fetch https://staging-instasent-docs-nextjs.oscar-284.workers.dev/llms.txt — start there for full context.
