Skip to content

Idempotency and retries

The network fails halfway through a POST. Did the job get created? Without a way to ask — and this API has no way to read a job back — a retry is a coin toss between a missing job and two of them.

The Idempotency-Key header removes the guess.

Every create request carries one:

Idempotency-Key: crm-order-2026-000123
  • Required on POST only. GET requests need none.
  • Up to 255 characters, from A-Z a-z 0-9 . _ : -.
  • A UUID v4 is the recommended shape.
  • Generate it once per intended action, and reuse that same value for every retry of it.

The last point is the whole mechanism. A key generated fresh on each attempt protects nothing.

You sendYou get
The same key, the same bodyThe original response, replayed. No second record is created.
The same key, a different body422, IDEMPOTENCY_CONFLICT. The key is already spoken for by a different request.
The same key while the first is still running409, IDEMPOTENCY_CONFLICT. Wait, then retry.
A new key, but an external_id already used409, DUPLICATE_EXTERNAL_ID.

The last row is a second line of defence. Your own external_idCRM-JOB-10001 — is checked for duplicates independently of the idempotency key, so even a genuinely new request cannot create a second EyeOnTask job for one CRM record.

Retry on 429, and only after the Retry-After period. Use the same idempotency key. See rate limits.

Do not retry automatically on 422 or 409. Both mean the server understood you and is refusing on purpose — a field is wrong, or the record already exists. Retrying changes nothing and hides the problem; these belong in front of a person, or in a queue that a person reads.

Use a new key for a different request. Two jobs for the same customer on the same day are two actions and want two keys, however similar their bodies look.