Skip to content
couryo

Developer guideGetting started

Test mode

ck_test_ keys capture emails without delivering them and simulate delivery, bounces, complaints and deferrals by recipient address, with real events and webhooks.

View as Markdown

With a ck_test_ key, Couryo does everything it would do for real (validates the request, applies idempotency, creates events and calls your webhooks), except deliver. No email leaves for the internet.

How to use it#

  1. Create a test key under Keys (mode test).
  2. Use it instead of the ck_live_ key, with no other code change.
  3. The response has status: "captured":
Response 202
{ "id": "msg_t3st0k9a1b2c3d4e", "status": "captured" }

The email's status stays captured; what happened to each recipient shows up in the events.

Simulated addresses#

The part before the recipient's @ decides what the test simulates, on any domain:

Recipient What happens Events
bounced@... or bounce@... hard bounce sent and bounced with 550 5.1.1 (unknown user)
complained@... or complaint@... delivered, then marked as spam sent, delivered and complained
deferred@... deferred, then delivered sent, deferred with 421 4.7.0 and delivered
anything else delivered sent and delivered with 250 2.0.0

Events arrive right after the send, with times (at) that mimic the real pace: the complaint 5 seconds after delivery, and the deferred email's delivery 1 minute after the deferral.

cURL
curl https://api.couryo.com/v1/emails \
  -H "Authorization: Bearer $COURYO_TEST_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "from": "Shop <orders@example.com>",
    "to": ["bounced@example.com", "ana@example.com"],
    "subject": "Bounce test",
    "text": "Hello"
  }'

Simulated events go through the same path as real ones: they show up in the timeline (GET /v1/emails/{id}), in GET /v1/events and in your webhooks, with an SMTP response marked as simulated and a plain-language explanation. It is how you test bounce and complaint handling without hurting anyone's reputation.

What is different from a live key#

  • No verified domain needed in from, and no level 0 (sandbox) restriction.
  • Does not count toward the level's daily and monthly limits or the plan quota. The per-second request limit applies as usual.
  • Never touches suppression or the account's bounce and complaint rates: a simulated bounced@ is not added to your suppression list.
  • The content check (shortened links and the like) only runs live. To check an email first, use POST /v1/emails/check.

In the dashboard#

The email shows up under Emails with the captured status and the simulated timeline, and webhook calls appear in the delivery history, so you can check your integration. Viewing the rendered content and sharing a review link with your team: coming soon.

Good for#

  • Automated tests and CI: no email ever reaches real customers.
  • Staging environments with data copied from production.
  • Testing how you handle bounce, complaint and deferral webhooks.
  • Using the MCP server with your agent at no risk.