Glossário · Testes de API
Idempotência
Em inglês: Idempotency
Também chamado de: idempotente, requisição idempotente, requisições idempotentes, Idempotency-Key
Definição
A propriedade de que enviar a mesma requisição uma ou várias vezes deixa o servidor no mesmo estado. GET, PUT e DELETE são idempotentes; POST não é.
Uma operação é idempotente se repeti-la tem o mesmo efeito no servidor que executá-la uma vez. Isso importa porque redes falham: um cliente que recebe timeout não sabe se a requisição chegou, e tentar de novo só é seguro quando a requisição é idempotente. Idempotência diz respeito ao estado do servidor, não a receber uma resposta idêntica toda vez.
Quais métodos HTTP são idempotentes
| Método | Idempotente | Seguro (sem efeitos colaterais) |
|---|---|---|
GET, HEAD, OPTIONS |
Sim | Sim |
PUT |
Sim | Não |
DELETE |
Sim | Não |
POST |
Não | Não |
PATCH |
Não garantido | Não |
Um DELETE /orders/42 enviado duas vezes pode retornar 204 e depois 404. As respostas são diferentes, mas o estado é o mesmo: o pedido não existe mais. Isso continua sendo idempotente.
PUT versus PATCH
PUT substitui o recurso inteiro pelo corpo que você envia. Enviar PUT /users/7 com {"name": "Ada", "plan": "pro"} três vezes deixa o mesmo usuário em todas elas, então é idempotente.
PATCH aplica uma alteração, e ser idempotente ou não depende da alteração. {"plan": "pro"} define um valor e, na prática, é idempotente. Uma operação como “incrementar loginCount em 1”, ou um add de JSON Patch em um array, dá um resultado diferente a cada vez; por isso o PATCH, como método, não tem idempotência garantida.
Tornando o POST seguro para retry
APIs de pagamento e de pedidos costumam aceitar uma chave de idempotência: o cliente gera um valor único e o envia em um header como Idempotency-Key. O servidor guarda o resultado da primeira requisição com aquela chave e devolve o mesmo resultado para qualquer repetição, em vez de criar um segundo pedido.
POST /payments HTTP/1.1
Content-Type: application/json
Idempotency-Key: 6f1c2a9e-3b7d-4f0a-9c2e-1d5b8a7e4f60
{"amount": 4999, "currency": "EUR"}
Como testar
- Envie o mesmo
PUTouDELETEduas vezes e faça a asserção do estado do recurso, não só do código de status. - Envie o mesmo
POSTcom a mesma chave de idempotência duas vezes. Espere um único recurso e o mesmo corpo de resposta. - Reutilize uma chave com um corpo diferente. Uma API bem projetada rejeita isso em vez de devolver silenciosamente o resultado antigo.
- Dispare requisições duplicadas em paralelo. Condições de corrida são onde o tratamento de idempotência costuma quebrar.