MailLandDocs
ReferenzAPI-Referenz

Sending

Send one email or a batch, schedule a send, read the email log and manage follow-ups.

Gets a paginated list of follow-up rules

GET/v1/transactional/follow-ups

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Query Parameters

isActive?boolean

Optional filter by active status

limit?|
Match^-?(?:0|[1-9]\d*)$
Formatint32
Default20
cursor?string

Response Body

application/json

application/json

application/json

curl -X GET "https://example.com/v1/transactional/follow-ups"
{  "items": [    {      "id": "string",      "name": "string",      "description": null,      "triggerTemplateId": "string",      "triggerTemplateName": "string",      "triggerMessageStream": null,      "followUpTemplateId": "string",      "followUpTemplateName": "string",      "delayValue": 0,      "delayUnit": "string",      "onlyIfNotOpened": true,      "onlyIfNotClicked": true,      "skipWeekends": true,      "allowedFromHour": null,      "allowedToHour": null,      "maxPerRecipientPerDay": null,      "isActive": true,      "priority": 0,      "totalTriggered": 0,      "totalSent": 0,      "totalSkipped": 0,      "createdAt": "2019-08-24T14:15:22Z",      "updatedAt": null    }  ],  "nextCursor": null,  "hasMore": true}

Creates a new follow-up rule

POST/v1/transactional/follow-ups

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Request Body

application/json

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

application/json

application/json

application/json

curl -X POST "https://example.com/v1/transactional/follow-ups" \  -H "Content-Type: application/json" \  -d '{}'
{  "id": "string",  "name": "string",  "description": null,  "triggerTemplateId": "string",  "triggerTemplateName": "string",  "triggerMessageStream": null,  "followUpTemplateId": "string",  "followUpTemplateName": "string",  "delayValue": 0,  "delayUnit": "string",  "onlyIfNotOpened": true,  "onlyIfNotClicked": true,  "skipWeekends": true,  "allowedFromHour": null,  "allowedToHour": null,  "maxPerRecipientPerDay": null,  "isActive": true,  "priority": 0,  "totalTriggered": 0,  "totalSent": 0,  "totalSkipped": 0,  "createdAt": "2019-08-24T14:15:22Z",  "updatedAt": null}

Gets a follow-up rule by its ID

GET/v1/transactional/follow-ups/{id}

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

id*string

Public ID of the rule

Response Body

application/json

application/json

application/json

curl -X GET "https://example.com/v1/transactional/follow-ups/string"
{  "id": "string",  "name": "string",  "description": null,  "triggerTemplateId": "string",  "triggerTemplateName": "string",  "triggerMessageStream": null,  "followUpTemplateId": "string",  "followUpTemplateName": "string",  "delayValue": 0,  "delayUnit": "string",  "onlyIfNotOpened": true,  "onlyIfNotClicked": true,  "skipWeekends": true,  "allowedFromHour": null,  "allowedToHour": null,  "maxPerRecipientPerDay": null,  "isActive": true,  "priority": 0,  "totalTriggered": 0,  "totalSent": 0,  "totalSkipped": 0,  "createdAt": "2019-08-24T14:15:22Z",  "updatedAt": null}

Updates an existing follow-up rule

PUT/v1/transactional/follow-ups/{id}

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

id*string

Public ID of the rule

Request Body

application/json

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

application/json

application/json

application/json

application/json

curl -X PUT "https://example.com/v1/transactional/follow-ups/string" \  -H "Content-Type: application/json" \  -d '{}'
{  "id": "string",  "name": "string",  "description": null,  "triggerTemplateId": "string",  "triggerTemplateName": "string",  "triggerMessageStream": null,  "followUpTemplateId": "string",  "followUpTemplateName": "string",  "delayValue": 0,  "delayUnit": "string",  "onlyIfNotOpened": true,  "onlyIfNotClicked": true,  "skipWeekends": true,  "allowedFromHour": null,  "allowedToHour": null,  "maxPerRecipientPerDay": null,  "isActive": true,  "priority": 0,  "totalTriggered": 0,  "totalSent": 0,  "totalSkipped": 0,  "createdAt": "2019-08-24T14:15:22Z",  "updatedAt": null}

Deletes a follow-up rule

DELETE/v1/transactional/follow-ups/{id}

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

id*string

Public ID of the rule

Response Body

application/json

application/json

curl -X DELETE "https://example.com/v1/transactional/follow-ups/string"
Empty
POST/v1/transactional/follow-ups/{id}/toggle

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

id*string

Public ID of the rule

Request Body

application/json

TypeScript Definitions

Use the request body type in TypeScript.

Request DTO for toggling rule active status

Response Body

application/json

application/json

curl -X POST "https://example.com/v1/transactional/follow-ups/string/toggle" \  -H "Content-Type: application/json" \  -d '{}'
Empty
GET/v1/transactional/follow-ups/scheduled

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Query Parameters

ruleId?string

Optional filter by rule ID

status?string

Optional filter by status (Pending, Sent, Skipped, Cancelled, Failed)

limit?|
Match^-?(?:0|[1-9]\d*)$
Formatint32
Default20
cursor?string

Response Body

application/json

application/json

application/json

curl -X GET "https://example.com/v1/transactional/follow-ups/scheduled"
{  "items": [    {      "publicId": "string",      "ruleId": "string",      "ruleName": "string",      "recipientEmail": "string",      "recipientName": null,      "scheduledAt": "2019-08-24T14:15:22Z",      "status": "string",      "skipReason": null,      "processedAt": null,      "createdAt": "2019-08-24T14:15:22Z"    }  ],  "nextCursor": null,  "hasMore": true}

Cancels a pending scheduled follow-up

POST/v1/transactional/follow-ups/scheduled/{id}/cancel

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

id*string

ID of the scheduled follow-up

Response Body

application/json

application/json

application/json

application/json

curl -X POST "https://example.com/v1/transactional/follow-ups/scheduled/string/cancel"
Empty
GET/v1/transactional/follow-ups/stats

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Response Body

application/json

application/json

curl -X GET "https://example.com/v1/transactional/follow-ups/stats"
{  "totalRules": 0,  "activeRules": 0,  "totalTriggered": 0,  "totalSent": 0,  "totalSkipped": 0,  "pendingFollowUps": 0,  "sendRate": 0}
GET/v1/transactional/logs

PERF: Default 30-day date range prevents full table scan on 1M+ messages. Date filter is always applied for performance. Count is cached for 2 minutes when no search filter is applied.

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Query Parameters

limit?|
Match^-?(?:0|[1-9]\d*)$
Formatint32
Default20
cursor?string
status?string

Filter by status (e.g., "sent", "delivered", "bounced")

search?string

Search term for recipient, subject, or message ID

from?string

Start date filter

Formatdate-time
to?string

End date filter

Formatdate-time
refresh?boolean

When true, bypasses count cache and fetches fresh data

Defaultfalse

Response Body

application/json

application/json

curl -X GET "https://example.com/v1/transactional/logs"
{  "items": [    {      "messageId": "string",      "recipient": "string",      "subject": "string",      "status": "string",      "sentAt": "2019-08-24T14:15:22Z",      "deliveredAt": null,      "openedAt": null,      "clickedAt": null,      "bounceReason": null,      "platformSide": true,      "attemptsExpired": true,      "openCount": 0,      "clickCount": 0,      "deliveryStatus": "string",      "statusVersion": 0,      "previousStatus": null,      "complaintStatus": "string",      "outcomeState": "string"    }  ],  "nextCursor": null,  "hasMore": true}
GET/v1/transactional/logs/stats

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Query Parameters

from?string

Start date for the stats query (default: 7 days ago).

Formatdate-time
to?string

End date for the stats query (default: now).

Formatdate-time
emailType?string

Filter by email type: 0 = Transactional, 1 = Marketing, null = all.

Value in

  • "transactional"
  • "marketing"
refresh?boolean

When true, bypasses cache and queries ClickHouse directly.

Defaultfalse

Response Body

application/json

curl -X GET "https://example.com/v1/transactional/logs/stats"
{  "total": 0,  "accepted": 0,  "sent": 0,  "delivered": 0,  "opened": 0,  "clicked": 0,  "bounced": 0,  "platformRefused": 0,  "attemptsExpired": 0,  "complained": 0,  "failed": 0,  "queued": 0,  "deliveryRate": 0,  "openRate": 0,  "clickRate": 0,  "bounceRate": 0,  "complaintRate": 0,  "source": "string",  "queryTimeMs": 0,  "hasAnyData": true}
GET/v1/transactional/logs/{messageId}

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

messageId*string

Response Body

application/json

curl -X GET "https://example.com/v1/transactional/logs/string"
{  "fromEmail": "string",  "createdAt": "2019-08-24T14:15:22Z",  "bounceCategory": null,  "ipAddress": null,  "retryCount": 0,  "smtpResponse": null,  "htmlContent": null,  "textContent": null,  "events": null,  "messageId": "string",  "recipient": "string",  "subject": "string",  "status": "string",  "sentAt": "2019-08-24T14:15:22Z",  "deliveredAt": null,  "openedAt": null,  "clickedAt": null,  "bounceReason": null,  "platformSide": true,  "attemptsExpired": true,  "openCount": 0,  "clickCount": 0,  "deliveryStatus": "string",  "statusVersion": 0,  "previousStatus": null,  "complaintStatus": "string",  "outcomeState": "string"}

Retry a failed or bounced email

POST/v1/transactional/logs/{messageId}/retry

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

messageId*string

Response Body

application/json

curl -X POST "https://example.com/v1/transactional/logs/string/retry"
{  "message": "string"}

Get all scheduled emails with pagination

GET/v1/transactional/scheduled

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Query Parameters

limit?|
Match^-?(?:0|[1-9]\d*)$
Formatint32
Default20
cursor?string
status?string

Filter by status (pending, processing, sent, failed, cancelled)

Response Body

application/json

application/json

curl -X GET "https://example.com/v1/transactional/scheduled"
{  "items": [    {      "scheduleId": "b7b4f318-018f-4d71-ac1a-f61e4bfaefbe",      "status": "string",      "scheduledAt": "2019-08-24T14:15:22Z",      "timeZone": null,      "to": "string",      "recipientCount": null,      "subject": "string",      "createdAt": "2019-08-24T14:15:22Z",      "processedAt": null,      "messageId": null,      "messageIds": [        "string"      ],      "rejectedRecipients": [        {          "email": "string",          "reason": "string"        }      ],      "reasonCode": null,      "error": null    }  ],  "nextCursor": null,  "hasMore": true}

Schedule an email for future delivery

POST/v1/transactional/scheduled

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Request Body

application/json

The email scheduling request

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

application/json

curl -X POST "https://example.com/v1/transactional/scheduled" \  -H "Content-Type: application/json" \  -d '{    "from": {      "email": "string"    },    "to": {      "email": "string"    },    "subject": "string",    "scheduledAt": "2019-08-24T14:15:22Z"  }'
{  "scheduleId": "b7b4f318-018f-4d71-ac1a-f61e4bfaefbe",  "status": "string",  "scheduledAt": "2019-08-24T14:15:22Z",  "timeZone": null,  "to": "string",  "recipientCount": null,  "subject": "string",  "createdAt": "2019-08-24T14:15:22Z",  "processedAt": null,  "messageId": null,  "messageIds": [    "string"  ],  "rejectedRecipients": [    {      "email": "string",      "reason": "string"    }  ],  "reasonCode": null,  "error": null}

Get a scheduled email by its ID

GET/v1/transactional/scheduled/{scheduleId}

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

scheduleId*string

The schedule ID

Formatuuid

Response Body

application/json

application/json

curl -X GET "https://example.com/v1/transactional/scheduled/497f6eca-6276-4993-bfeb-53cbbbba6f08"
{  "scheduleId": "b7b4f318-018f-4d71-ac1a-f61e4bfaefbe",  "status": "string",  "scheduledAt": "2019-08-24T14:15:22Z",  "timeZone": null,  "to": "string",  "recipientCount": null,  "subject": "string",  "createdAt": "2019-08-24T14:15:22Z",  "processedAt": null,  "messageId": null,  "messageIds": [    "string"  ],  "rejectedRecipients": [    {      "email": "string",      "reason": "string"    }  ],  "reasonCode": null,  "error": null}

Cancel a scheduled email

DELETE/v1/transactional/scheduled/{scheduleId}

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

scheduleId*string

The schedule ID

Formatuuid

Response Body

application/json

application/json

curl -X DELETE "https://example.com/v1/transactional/scheduled/497f6eca-6276-4993-bfeb-53cbbbba6f08"
Empty

Reschedule an email to a new time

PATCH/v1/transactional/scheduled/{scheduleId}

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Path Parameters

scheduleId*string

The schedule ID

Formatuuid

Request Body

application/json

The reschedule request

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

application/json

application/json

curl -X PATCH "https://example.com/v1/transactional/scheduled/497f6eca-6276-4993-bfeb-53cbbbba6f08" \  -H "Content-Type: application/json" \  -d '{    "scheduledAt": "2019-08-24T14:15:22Z"  }'
{  "scheduleId": "b7b4f318-018f-4d71-ac1a-f61e4bfaefbe",  "status": "string",  "scheduledAt": "2019-08-24T14:15:22Z",  "timeZone": null,  "to": "string",  "recipientCount": null,  "subject": "string",  "createdAt": "2019-08-24T14:15:22Z",  "processedAt": null,  "messageId": null,  "messageIds": [    "string"  ],  "rejectedRecipients": [    {      "email": "string",      "reason": "string"    }  ],  "reasonCode": null,  "error": null}
POST/v1/transactional/send

Sends an email to one or more recipients. The email is queued for delivery and a job ID is returned for tracking.

Possible error codes:

  • SEND_FAILED: Email validation failed
  • TEMPLATE_NOT_FOUND: templateId names no active template of this account
  • IP_POOL_NOT_FOUND: ipPoolId names no pool assigned to this account
  • TEMPLATE_VARIABLE_MISSING (422): the content has a {{placeholder}} with no value; nothing is sent (the batch endpoint skips those recipients and lists them in rejectedRecipients)
  • INVALID_REQUEST: scheduledAt is more than 7 days ahead
  • VALIDATION_FAILED: the request body is invalid (including attachments: more than 10, over 10 MiB decoded in total, or content that is not canonical Base64)
  • DOMAIN_NOT_FOUND: Sending domain not registered
  • DOMAIN_NOT_VERIFIED: Sending domain not verified
  • RATE_LIMIT_EXCEEDED: Account rate limit exceeded
  • QUOTA_EXCEEDED: Monthly quota exceeded
  • ACCOUNT_NOT_ACTIVE: Account is suspended/disabled
  • NO_ACTIVE_SUBSCRIPTION: No valid subscription
  • IDEMPOTENCY_KEY_INVALID: The idempotency key is empty, malformed, over 255 characters, or the header was sent more than once
  • IDEMPOTENCY_KEY_CONFLICT: The X-Idempotency-Key header and the idempotencyKey body field were both supplied and differ
  • IDEMPOTENCY_KEY_REUSED (409): The key is already in use for a different endpoint on this account

Idempotency: supply X-Idempotency-Key (recommended) or the idempotencyKey body field. Supplying both is allowed only when the values are identical. A retry with the same key within the retention window replays the original response verbatim instead of sending again. Keys are unique per account, so one key cannot be reused for a different operation.

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Request Body

application/json

Cancellation token

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

application/json

application/json

application/json

application/json

application/json

application/json

application/json

application/json

application/json

curl -X POST "https://example.com/v1/transactional/send" \  -H "Content-Type: application/json" \  -d '{    "from": {},    "to": [      {}    ]  }'
{  "success": true,  "jobId": null,  "messageIds": [    "string"  ],  "acceptedRecipients": [    "string"  ],  "rejectedRecipients": [    {      "email": "string",      "reason": "string",      "suggestion": null    }  ],  "error": null,  "errorCode": null,  "queuedAt": "2019-08-24T14:15:22Z",  "isSandboxed": true,  "sandboxReason": null,  "scheduledAt": null,  "scheduleId": null}

Send batch of emails.

POST/v1/transactional/send-batch

Sends a batch of emails to multiple recipients with the same content. Returns a batch ID for tracking all emails in the batch.

Possible error codes:

  • BATCH_SEND_FAILED: Batch validation failed
  • TEMPLATE_NOT_FOUND: templateId names no active template of this account
  • IP_POOL_NOT_FOUND: ipPoolId names no pool assigned to this account
  • TEMPLATE_VARIABLE_MISSING (422): the content has a {{placeholder}} with no value; nothing is sent (the batch endpoint skips those recipients and lists them in rejectedRecipients)
  • INVALID_REQUEST: scheduledAt is more than 7 days ahead
  • DOMAIN_NOT_FOUND: Sending domain not registered
  • DOMAIN_NOT_VERIFIED: Sending domain not verified
  • RATE_LIMIT_EXCEEDED: Account rate limit exceeded
  • QUOTA_EXCEEDED: Monthly quota exceeded
  • ACCOUNT_NOT_ACTIVE: Account is suspended/disabled
  • NO_ACTIVE_SUBSCRIPTION: No valid subscription
  • IDEMPOTENCY_KEY_INVALID: The idempotency key is empty, malformed, over 255 characters, or the header was sent more than once
  • IDEMPOTENCY_KEY_CONFLICT: The X-Idempotency-Key header and the idempotencyKey body field were both supplied and differ
  • IDEMPOTENCY_KEY_REUSED (409): The key is already in use for a different endpoint on this account

Idempotency: supply X-Idempotency-Key (recommended) or the idempotencyKey body field. Supplying both is allowed only when the values are identical. A retry with the same key within the retention window replays the original response verbatim instead of sending again. Keys are unique per account, so one key cannot be reused for a different operation.

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Request Body

application/json

Cancellation token

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

application/json

application/json

application/json

application/json

application/json

application/json

application/json

application/json

application/json

curl -X POST "https://example.com/v1/transactional/send-batch" \  -H "Content-Type: application/json" \  -d '{    "from": {},    "recipients": [      {}    ]  }'
{  "success": true,  "batchId": "string",  "messageIds": [    "string"  ],  "totalRecipients": 0,  "acceptedCount": 0,  "rejectedCount": 0,  "rejectedRecipients": [    {      "email": "string",      "reason": "string",      "suggestion": null    }  ],  "error": null,  "errorCode": null,  "queuedAt": "2019-08-24T14:15:22Z",  "estimatedCompletion": null,  "isSandboxed": true,  "sandboxReason": null,  "scheduledAt": null,  "scheduleId": null}
GET/v1/transactional/send/check

Pre-flight check to verify if the user can send emails. Checks rate limits and monthly quota.

Authorization

ApiKey
X-API-Key<token>

Your API key, created in the dashboard under API keys. Production sending keys start with ml_pet_ (transactional) or ml_pem_ (marketing); sandbox keys with ml_set_ or ml_sem_.

In: header

Query Parameters

recipientCount?|

Number of recipients to check

Match^-?(?:0|[1-9]\d*)$
Formatint32
Default1

Response Body

application/json

application/json

application/json

curl -X GET "https://example.com/v1/transactional/send/check"
{  "canSend": true,  "reason": null,  "rateLimitStatus": {    "currentSecond": 0,    "limitPerSecond": 0,    "currentHour": 0,    "limitPerHour": 0,    "currentDay": 0,    "limitPerDay": 0  },  "monthlyUsed": 0,  "monthlyLimit": 0}