> ## Documentation Index
> Fetch the complete documentation index at: https://docs.sendbaze.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Sending email

> Everything the send request accepts, how recipients, headers, tags and classes work, and what happens after you get an id back.

`POST /v1/emails` validates the request, stores the message, queues it and returns an id. The email leaves through Amazon SES in Cape Town within seconds. Delivery is asynchronous: watch the [webhooks](https://docs.sendbaze.com/learn/webhooks/overview.md) or the **Logs** page.

```json theme={"dark"}
{
  "from": "Yourshop <orders@yourshop.co.za>",
  "to": ["thandi@example.com"],
  "cc": "accounts@yourshop.co.za",
  "replyTo": "help@yourshop.co.za",
  "subject": "Your order #1042 has shipped",
  "html": "<p>Tracking: <b>CG123456789ZA</b></p>",
  "text": "Tracking: CG123456789ZA",
  "headers": { "X-Order-Id": "1042" },
  "tags": ["order-shipped"],
  "class": "transactional"
}
```

## Fields

**from** `string` *required*

A bare address or `Name <address>`. Live keys must use a [verified domain](https://docs.sendbaze.com/get-started/add-domain.md) or a subdomain of one, or the shared test address `onboarding@sendbaze.com`, which [delivers to your own addresses only](https://docs.sendbaze.com/get-started/test-without-a-domain.md).

**to** `string | string[]` *required*

One address or up to 50.

**cc** `string | string[]`

Up to 50. Visible to every recipient.

**bcc** `string | string[]`

Up to 50. Hidden from other recipients.

**replyTo** `string`

Where replies go when it is not the sender.

**subject** `string`

Up to 998 characters. Required unless `templateId` is set, in which case it overrides the template's subject.

**html** `string`

HTML body, up to 2 MB. One of `html`, `text` or `templateId` is required.

**text** `string`

Plain-text body, up to 2 MB. Send both `html` and `text` when you can: some clients and most spam filters read the text part.

**templateId** `string`

Render a [template](https://docs.sendbaze.com/learn/sending/templates.md) instead of passing `html` or `text`.

**variables** `object`

Values for every `{{placeholder}}` in the template. Requires `templateId`.

**attachments** `object[]`

Up to 10 files, 3 MB decoded in total. See [attachments](https://docs.sendbaze.com/learn/sending/attachments.md).

**headers** `object`

Custom headers. Names are letters, digits and dashes. `From`, `To`, `Subject`, `Date`, `Message-ID`, `DKIM-Signature` and the other standard headers cannot be overridden.

**tags** `string[]`

Up to 10 tags of 64 characters. Returned on the message and on webhook events; filter the logs and `GET /v1/emails` by tag.

**class** `'transactional' | 'marketing'` (default: transactional)

See [email types](https://docs.sendbaze.com/get-started/email-types.md). Marketing mail gets unsubscribe headers.

## Response

```json theme={"dark"}
{ "id": "em_01j9x7k2r4m8q3v5n6b7c8d9e0", "status": "queued", "mode": "live" }
```

`mode` is `test` when the request used an `sk_test_` key: the message was validated and stored but never sent.

## Before anything is queued

The API refuses, with nothing stored, when:

* the `from` domain is not verified for your organisation (`403 domain_not_verified`)
* a recipient is on a [suppression list](https://docs.sendbaze.com/learn/deliverability/suppressions.md) (`422 recipient_suppressed`, naming each address)
* your plan's monthly allowance is used up and nothing else covers the send (`402 allowance_exhausted`)
* sending is paused by the complaint monitor (`423 org_paused`)

Test keys skip the first three checks so you can develop before your domain is verified.

## What happens next

1. **queued**: stored and handed to a worker, usually within a second.
2. **sent**: accepted by Amazon SES. The `sent` event carries the SES message id.
3. **delivered**, **bounced** or **complained**: reported by the receiving server, usually within seconds, sometimes hours for greylisting mail servers.
4. **failed**: the worker gave up after retries; `error` says why and, for SMS, credits are refunded.

Fetch any message with `GET /v1/emails/{id}` for its status and full timeline, or list and filter with `GET /v1/emails`.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.