Send with attachments, CC & BCC

Extend the basic send request with additional recipients (cc, bcc), a replyTo address, and file attachments. All fields are part of the same POST /transactional-email payload.

📘

Prerequisite

This builds on Send your first email (HTTP API). You need a Bearer token and a verified authorized sender.

CC, BCC & Reply-To

to, cc, and bcc are each arrays of address objects (address required, name optional). replyTo is a single address applied when a recipient hits Reply.

curl -X POST 'https://connect.routee.net/transactional-email' \
  -H 'Authorization: Bearer YOUR_ACCESS_TOKEN' \
  -H 'Content-Type: application/json' \
  -d '{
    "from":    { "name": "Acme Support", "address": "[email protected]" },
    "replyTo": { "address": "[email protected]" },
    "to":  [{ "address": "[email protected]" }],
    "cc":  [{ "name": "Team", "address": "[email protected]" }],
    "bcc": [{ "address": "[email protected]" }],
    "subject": "Your invoice is attached",
    "content": { "html": "<p>Please find your invoice attached.</p>" }
  }'

Attachments

attachments is an array of objects. Each attachment needs:

FieldDescription
contentBase64-encoded file content
typeMIME type, e.g. application/pdf
filenameDisplay name (max 128 chars)

Base64-encode the file, then include it in the request. A quick way to encode on the CLI:

base64 -i invoice.pdf | tr -d '\n'

Full example — attachment + CC/BCC

import base64, requests

with open("invoice.pdf", "rb") as f:
    encoded = base64.b64encode(f.read()).decode()

payload = {
    "from":    {"name": "Acme Support", "address": "[email protected]"},
    "replyTo": {"address": "[email protected]"},
    "to":  [{"name": "Jane Customer", "address": "[email protected]"}],
    "cc":  [{"address": "[email protected]"}],
    "bcc": [{"address": "[email protected]"}],
    "subject": "Your invoice is attached",
    "content": {
        "html": "<p>Please find your invoice attached.</p>",
        "text": "Please find your invoice attached.",
    },
    "attachments": [
        {
            "content": encoded,
            "type": "application/pdf",
            "filename": "invoice.pdf",
        }
    ],
}

resp = requests.post(
    "https://connect.routee.net/transactional-email",
    headers={"Authorization": "Bearer YOUR_ACCESS_TOKEN", "Content-Type": "application/json"},
    json=payload,
)
print(resp.status_code, resp.json())
import { readFile } from "node:fs/promises";

const encoded = (await readFile("invoice.pdf")).toString("base64");

const res = await fetch("https://connect.routee.net/transactional-email", {
  method: "POST",
  headers: {
    Authorization: "Bearer YOUR_ACCESS_TOKEN",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    from: { name: "Acme Support", address: "[email protected]" },
    replyTo: { address: "[email protected]" },
    to: [{ name: "Jane Customer", address: "[email protected]" }],
    cc: [{ address: "[email protected]" }],
    bcc: [{ address: "[email protected]" }],
    subject: "Your invoice is attached",
    content: {
      html: "<p>Please find your invoice attached.</p>",
      text: "Please find your invoice attached.",
    },
    attachments: [
      { content: encoded, type: "application/pdf", filename: "invoice.pdf" },
    ],
  }),
});
console.log(res.status, await res.json());
⚠️

Keep messages within size limits

Base64 encoding adds ~33% overhead. Oversized messages are rejected with 400 error code 000003 (message size limit exceeded). For large files, link to a hosted download instead of attaching. See Email Error Codes.

Field reference

Next steps