API Shared (all languages) active http-service

Retried mutating operations are idempotent end-to-end

api-004

Intent

Retries after timeouts or lost responses should not duplicate externally visible side effects.

Applicability

Applies when the diff adds or changes a retriable create or mutate operation, or implements the server-side deduplication path for idempotency keys.

What to inspect

Request models, idempotency-key handling, duplicate detection, transaction boundaries, stored request fingerprints, and mismatch error paths.

Pass criteria

Retriable mutations accept an idempotency key or equivalent deduplication handle, store the dedup state atomically with the mutation, and reject key reuse with different parameters.

Fail criteria

A retriable mutation has no deduplication contract, stores dedup state and the side effect separately, or accepts the same key for different request parameters.

Do not flag

Naturally idempotent operations already keyed by a stable client-chosen identifier, or internal one-shot paths with no retry surface.

Confidence guidance

HIGH when the public contract and server implementation are both visible. MEDIUM when some idempotency behavior may exist in shared middleware. LOW when only part of the retry surface is shown.

Remediation

Require an idempotency key, persist it atomically with the mutation, and compare subsequent requests to the original intent.

Pass example

with db.transaction():
    db.insert_idempotency_key(key, request_hash)
    db.insert_order(order_id, customer_id)

Fail example

db.insert_idempotency_key(key, request_hash)
db.insert_order(order_id, customer_id)

Sources

  • Making retries safe with idempotent APIs article