Pular para o conteúdo principal

Idempotência

A API suporta idempotência para repetir mutações com segurança, sem executar a mesma operação duas vezes. O caso clássico: um POST /api/v1/charges cai por erro de rede e você não sabe se a cobrança foi criada — reenvie com a mesma chave e a resposta original volta, sem criar uma segunda cobrança.

Como usar

Envie o header em qualquer POST, PUT ou PATCH:

X-Idempotency-Key: <chave>

A chave é gerada pelo seu lado — recomendamos UUID v4. Máximo de 255 caracteres.

curl -i \
-H "Authorization: Bearer $DUNNING_TOKEN" \
-H 'Content-Type: application/json' \
-H 'X-Idempotency-Key: 8c0f5d6e-3f8b-4cb5-9a47-d8f5b15e9b21' \
-d '{ "personId": "cmd8k1x2y0009cd4e", "amount": 1500.00, "dueDate": "2026-08-10" }' \
-X POST 'https://api.dunning.kobana.com.br/api/v1/charges'

Como funciona

  1. A chave é reservada atomicamente, escopada à sua organização (organizações diferentes podem usar a mesma chave sem conflito).
  2. O servidor calcula a impressão digital da requisição: hash de método + caminho + body cru.
  3. O handler executa e a resposta (status, body, headers) é gravada vinculada à chave — inclusive quando é erro.
  4. Nova requisição com a mesma chave dentro de 24 horas recebe a resposta original verbatim, com o header extra:
X-Idempotent-Replay: true

Após 24 horas a chave expira e a mesma chave gera uma execução nova.

Conflitos

CenárioStatuscode
Mesma chave com método/caminho/body diferente409IDEMPOTENCY_KEY_REUSED
Outra requisição com a mesma chave em andamento409IDEMPOTENCY_REQUEST_IN_PROGRESS
Chave vazia ou com mais de 255 caracteres400VALIDATION_ERROR

Exemplo de resposta de conflito:

{
"message": "X-Idempotency-Key já foi usado com parâmetros diferentes. Reenvie os parâmetros originais ou gere uma nova chave",
"code": "IDEMPOTENCY_KEY_REUSED"
}

Em IDEMPOTENCY_REQUEST_IN_PROGRESS, aguarde um instante e reenvie a mesma requisição: ou a primeira execução termina e você recebe o replay, ou a reserva foi liberada e a sua tentativa executa.

Quando o resultado não é gravado

É seguro reenviar quando o handler nem chegou a rodar:

  • Requisição rejeitada antes do handler (JSON inválido, autenticação ausente).
  • O handler lançou uma exceção — a reserva é liberada para o próximo retry rodar limpo.

Métodos aceitos

MétodoAceita X-Idempotency-Key?
POST / PUT / PATCH✅ Sim
GET / DELETE❌ Não — já são idempotentes por definição; o header é ignorado

Boas práticas

  • Uma chave por operação de negócio; repita-a apenas em retries da mesma operação.
  • Persista a chave junto com o estado da operação no seu lado — retry pós-crash usa a mesma chave.
  • Combine com backoff exponencial em 5xx/timeout: a chave garante que o retry não duplica nada.
  • Como erros também são gravados, um replay de erro é sinal para corrigir a requisição e gerar chave nova — não insistir na mesma.
  • Descarte chaves com mais de 24 horas no seu lado; o servidor já as expirou.