> ## Documentation Index
> Fetch the complete documentation index at: https://docs.fraudeg.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Idempotencia

> X-Idempotency-Key: obligatorio en scoring, y los dos 409 distintos

`POST /v1/transactions/analyze` y `POST /v1/transactions/analyze/sandbox` exigen el header
`X-Idempotency-Key` en cada petición.

```
X-Idempotency-Key: <clave-que-generas-tu>
```

* Es **obligatorio** — sin una clave estable no puedes reintentar con seguridad.
* Debe tener entre **16 y 128 caracteres**, de alfabeto url-safe (`A-Z a-z 0-9 _ : . -`).
* La clave la genera y controla el cliente: tú decides qué transacciones son “la misma”
  reintentando la misma clave, y cuáles son nuevas usando una clave distinta.

Identidad no usa este header. Ver [POST /verifications](/referencia/verificaciones).

## Los comportamientos

| Caso                                                          | Resultado                                                      |
| ------------------------------------------------------------- | -------------------------------------------------------------- |
| Primera vez que se usa la clave                               | La transacción se scorea y se persiste                         |
| Misma clave, mismo payload                                    | Se reproduce la respuesta ya guardada — no se vuelve a scorear |
| Misma clave, payload distinto                                 | `422`                                                          |
| Misma clave, con una petición todavía en curso                | `409` (en vuelo)                                               |
| Misma clave, pero la respuesta guardada ya no se puede releer | `409` (respuesta ilegible) — reintenta con una **clave nueva** |
| Header ausente o con formato inválido                         | `400`                                                          |

<Tip>
  El caso “mismo payload → replay” es lo que hace seguro reintentar una petición que se cayó
  por timeout de red: reenvíala con la misma clave y recibes la respuesta original, sin
  riesgo de duplicar la transacción.
</Tip>

## Los dos `409`

Comparten HTTP `409` y `error_code` `DATA_CONFLICT`. Se distinguen por **`details`** (no
por `message`, que es la prosa genérica del código).

### 1. Petición en vuelo

`details` contiene `A request with this X-Idempotency-Key is already in progress`.

Reintenta más tarde **con la misma clave**. No es un error de tu payload.

### 2. Respuesta previa ilegible

`details` contiene `The response stored for this X-Idempotency-Key was produced by an earlier version of the API and can no longer be replayed`.

Cuando FraudEG scorea una transacción, guarda la respuesta asociada a tu clave para poder
reproducirla. Si esa respuesta se escribió bajo una versión anterior del contrato y ya no
corresponde a la forma actual, no se puede devolver tal cual.

Lo importante:

* **La transacción sí se scoreó y está guardada.** No se perdió nada.
* **No es un error de tu petición.** Tu payload y tu clave estaban bien.
* **No se vuelve a scorear con esa clave.** Reprocesarla produciría un resultado distinto
  del que ya quedó guardado — exactamente lo que la idempotencia existe para evitar.

La acción correcta es **reintentar con una clave nueva**. Eso produce una respuesta limpia
y coherente con el contrato actual.

<Tip>
  Este caso es raro. Si tu manejo del `409` ya lee `details`, basta con reintentar una vez
  con clave nueva cuando el texto habla de replay, y con la misma clave cuando habla de
  in progress.
</Tip>

Ver [Errores de /analyze](/referencia/analyze#errores) para el envelope completo.

Siguiente paso: [Campos](/integrar/campos).
