Skip to content

Send Test Email

Send one real email through a campaign's sending account.

POST/api/v1/campaigns/{campaign_id}/test-email

Requires an API key with the write scope.

This sends a real email from one of the campaign's sending accounts to the address you give. It is not a dry run: use Preview Campaign Email to see copy without sending.

The email counts against the account's daily limit and the workspace's monthly limit, is logged as a campaign email, and updates the campaign's sent counters. {spin|syntax} and {{merge}} tags are filled in. The same checks run as for a message sent from the app: the address is refused when it belongs to a lead that has bounced, unsubscribed or failed verification, or when it is on the block list. A List-Unsubscribe header is added when the campaign needs one.

A delivery failure at the mail server is not an HTTP error: you get 200 with success: false and the error.

Path Parameters#

campaign_idstringpathrequired
The campaign.

Request Body#

toEmailstringbodyrequired
Recipient. Any address; a real email goes to it.
accountIdstringbodyrequired
A sending account assigned to this campaign. It must be active and connected.
subjectstringbodyrequired
Subject, up to 500 characters.
bodystringbodyrequired
Body, up to 200,000 characters.
isHtmlbooleanbodydefault false
Send as HTML instead of plain text.
preheaderstringbody
Preview text, up to 300 characters. HTML sends only.
leadIdstringbody
Fill merge tags from this lead in the campaign.

Response#

dataobject
Show Result
successboolean
Whether the mail server accepted the email.
messageIdstring | null
The Message-ID when it was sent.
errorstring | null
The mail server error when it was not.

Errors#

StatusDescription
401Missing, invalid, revoked or expired API key
403API key does not have the required scope: write
400The account is not on this campaign, not active or not connected, or the address bounced, unsubscribed, failed verification or is blocked
404Campaign or sending account not found in this workspace
429The account's daily limit or the workspace's monthly send limit is reached, or the expensive rate limit is
503The block list could not be checked; try again

Rate Limit#

  • 100 requests per minute, shared by every expensive call in your workspace. Fixed 60-second window.
  • Every response includes X-RateLimit-Limit, X-RateLimit-Remaining, X-RateLimit-Reset (unix epoch seconds) and X-RateLimit-Bucket (expensive).
  • A 429 response includes a Retry-After header (seconds until the bucket resets).

For client-side patterns (Retry-After, exponential backoff, monitoring X-RateLimit-Remaining), see Rate Limiting.

Was this page helpful?
View as MarkdownLast updated November 4, 2026