Idempotency

Send an Idempotency-Key header so a retried request never sends twice.

A network error can leave you unsure whether a send went through. Send an Idempotency-Key header, and a retry returns the first result instead of sending again.

How it works

Add the header to the request. The key can be up to 256 characters.

  • The same key and the same body return the original result without sending again. The response carries the header Idempotent-Replayed: true.
  • The same key with a different body answers 409 NOT_UNIQUE, so you can spot the mismatch.
  • The same key while the first request is still running answers 409. Retry after a short delay.
  • If a request stopped part way, a retry with the same key answers 409 PARTIAL_COMPLETION. The body lists the email ids already sent, and nothing is sent again.

Keys expire after 24 hours. Keys belong to the API key that sent them, so two integrations never share one.

curl -X POST https://app.usenotix.dev/api/v1/emails \
  -H "Authorization: Bearer $NOTIX_API_KEY" \
  -H "Idempotency-Key: order-4471-receipt" \
  -H "Content-Type: application/json" \
  -d '{
    "from": "Acme <receipts@acme.com>",
    "to": "maria@example.com",
    "subject": "Your receipt for order 4471",
    "html": "<p>Thanks for your order.</p>"
  }'

Endpoints that accept it

EndpointWhat a retry protects
`POST /v1/emails`One email
`POST /v1/emails/batch`A batch of emails
`POST /v1/sms`One SMS
`POST /v1/verify/send`One one-time code
`POST /v1/campaigns/{campaignId}/schedule`Scheduling a broadcast
`POST /v1/journeys/{id}/enroll`Enrolling one contact
`POST /v1/journeys/{id}/enroll/batch`Enrolling a batch of contacts
`POST /v1/contactBooks/{contactBookId}/contacts/import`A CSV import
`POST /v1/inbound/conversations/{id}/reply`A reply in the shared inbox

Other endpoints ignore the header.

Choosing a key

  • Use one key per business event, such as an order id: order-4471-receipt, not retry-3.
  • Build the key from your own record, not from a clock.
  • Retry transport errors, 429 and 5xx with backoff, and send the same key each time.
Open in ClaudeOpen in ChatGPT