Emails

Schedule Email

Schedule a transactional email for future delivery. Accepts the same payload as POST /emails with an additional required scheduled_at field. The email must be scheduled at least 5 minutes in the future and within 30 days.

Breaking change. Scheduled emails are no longer parked inside SparkPost with options.start_time — SparkPost retired its per-transmission GET and DELETE endpoints, so Lettr now holds the email in its own store and injects it into SparkPost only when it is due. request_id is therefore Lettr's own id, prefixed sch_ (for example sch_01JQZ3N2K8XW9V6M4TBRC7YHDE), and it is the id you pass to GET and DELETE /emails/scheduled/{transmissionId}. SparkPost's transmission id is now the separate transmission_id field, which is null until the email is actually injected; that is the value that appears as transmission_id on your webhook events, so use it to correlate webhooks. state values are now Lettr's own (scheduled, sending, sent, cancelled, failed) rather than SparkPost's pass-through states.

Idempotency-Key is not honoured here and is ignored if sent — it applies to POST /emails only. A scheduled email is created once and then listed, read or cancelled by the request_id returned here, so use that to check whether a retry is needed.

post/emails/scheduled

Request

  • Base URL: https://app.lettr.com/api
  • URL: https://app.lettr.com/api/emails/scheduled
  • Auth: HTTP bearer

Request body

fromstring email required

Sender email address

from_namestring nullable

Sender display name

subjectstring nullable

Email subject line. Required when not using a template. When using template_slug, defaults to the template's subject (or template name as fallback). If provided alongside a template, overrides the template subject.

tostring[] required

Recipient email addresses

ccstring[]

Carbon copy recipient email addresses

bccstring[]

Blind carbon copy recipient email addresses

reply_tostring email nullable

Reply-To email address

reply_to_namestring nullable

Reply-To display name

htmlstring nullable

HTML content of the email. At least one of html or text is required, but providing both is recommended for best compatibility across email clients.

textstring nullable

Plain text content of the email. At least one of html or text is required, but providing both is recommended for best compatibility across email clients.

amp_htmlstring nullable

AMP HTML content for supported email clients

project_idinteger nullable

Project ID containing the template. If not provided when using template_slug, the team's default project will be used.

template_slugstring nullable

Template slug to use for email content. When provided, the template's HTML will be used instead of the html field.

template_versioninteger nullable

Specific template version to use. If not provided, the active version will be used.

tagstring

Tag for tracking and analytics. Automatically set from template_slug if not provided.

metadataobject

Custom metadata attached to the email for tracking purposes

headersobject

Custom email headers. Up to 10 headers allowed. Standard envelope headers (From, To, Subject, etc.), SparkPost internal headers (X-MSYS-API), and List-Unsubscribe and List-Unsubscribe-Post headers are managed by the system and cannot be set manually.

substitution_dataobject

Variables for template substitution in email content

scheduled_atstring date-time required

The UTC date/time when the email should be sent. Must be at least 5 minutes in the future and within 30 days.

Example request

{
  "from": "sender@example.com",
  "from_name": "Sender Name",
  "subject": "Welcome to Lettr",
  "to": [
    "recipient@example.com"
  ],
  "cc": [
    "cc@example.com"
  ],
  "bcc": [
    "bcc@example.com"
  ],
  "reply_to": "reply@example.com",
  "reply_to_name": "Reply Name",
  "html": "<h1>Hello</h1><p>Welcome!</p>",
  "text": "Hello\n\nWelcome!",
  "project_id": 123,
  "template_slug": "welcome-email",
  "template_version": 1,
  "tag": "welcome-series-2024",
  "metadata": {
    "user_id": "12345",
    "campaign": "onboarding"
  },
  "headers": {
    "X-Mailer": "MyApp/1.0",
    "X-Custom-ID": "abc-123"
  },
  "substitution_data": {
    "first_name": "John",
    "company": "Acme Inc"
  },
  "attachments": [
    {
      "name": "invoice.pdf",
      "type": "application/pdf",
      "data": "JVBERi0xLjQKJeLjz9MKMyAwIG9iago8PC9UeXBlL1BhZ2U="
    }
  ],
  "scheduled_at": "2024-01-16T10:00:00Z"
}

Response

Email scheduled for delivery. Free tier teams receive quota headers indicating their usage and limits.

messagestring required

Example response

{
  "message": "Email scheduled for delivery.",
  "data": {
    "request_id": "sch_01JQZ3N2K8XW9V6M4TBRC7YHDE",
    "transmission_id": "12345678901234567890",
    "state": "scheduled",
    "scheduled_at": "2024-01-16T10:00:00Z",
    "from": "sender@example.com",
    "from_name": "Sender Name",
    "subject": "Scheduled Newsletter",
    "recipients": [
      "recipient@example.com"
    ],
    "num_recipients": 1,
    "accepted": 1,
    "tag": "welcome-series-2024",
    "events": [
      {
        "event_id": "7609871845907017144",
        "timestamp": "2024-01-15T10:31:00.000Z",
        "request_id": "7610639000055488914",
        "rcpt_to": "recipient@example.com",
        "raw_rcpt_to": "recipient@example.com",
        "recipient_domain": "example.com",
        "mailbox_provider": "Gmail",
        "mailbox_provider_region": "Global",
        "message_id": "699715cd9e6961853a97",
        "subject": "Welcome to Lettr",
        "friendly_from": "sender@example.com",
        "sending_domain": "example.com",
        "sending_ip": "168.203.51.91",
        "msg_size": 30823,
        "injection_time": "2024-01-15T10:30:00.000Z",
        "campaign_id": "welcome-series",
        "template_id": "template_7610639000055488914",
        "template_version": "0",
        "ip_pool": "default",
        "msg_from": "msprvs1=abc123=bounces@sparkpostmail1.com",
        "delv_method": "esmtp",
        "recv_method": "rest",
        "routing_domain": "gmail.com"
      }
    ]
  }
}

Changes

No recorded changes to this operation across all 1 revision of this API.