Idempotency keys

Prevent duplicate sends on retries with the Idempotency-Key header—deduplicated for 24 hours per API key user.

Network timeouts and client retries can accidentally send the same OTP or receipt twice. Use idempotency keys to make POST /emails safely retryable.

How it works

  1. Your first request includes Idempotency-Key: <unique-string>.
  2. Piisend sends the email and stores (user_id, key) → email_id for 24 hours.
  3. A retry with the same key returns the original email JSON—no second send.

Keys must be 1–256 characters. Choose a stable string per logical operation, e.g. otp:user@example.com:482193.

Step-by-step

1. Generate a deterministic key

Derive the key from data that identifies the operation—not a random UUID on each attempt.

Good: receipt:order-9912, otp:alice@example.com:773120

Bad: new UUID on every HTTP retry

2. Send with the header

Add Idempotency-Key alongside Authorization on POST /emails.

3. Retry safely on failure

If the HTTP client times out, retry with the same key. A 200 response with the same email id confirms deduplication worked.

4. OTP and template sends

Idempotency works with template sends—ideal for one-time codes where duplicate delivery is harmful.

Concurrent requests

If two requests with the same key arrive simultaneously, one wins; the other receives the canonical email record. Duplicate quota is released when possible.

Related

Idempotency key flowRequest 1 + KeySend emailStore key → idRetry with same Idempotency-Key within 24h → return original email (no duplicate send)

Example request

curl -sS -X POST "https://api.piisend.com/api/v1/emails" \
  -H "Authorization: Bearer $PIISEND_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: otp:user@example.com:482193" \
  -d '{
    "to": ["user@example.com"],
    "template_id": "YOUR_OTP_TEMPLATE_ID",
    "template_vars": { "otp_code": "482193" }
  }'

Documentation

Integrate with the REST API

Quickstart, API reference, and webhooks—everything you need to send from your app.