409 Conflict
The request conflicts with the current state of the resource, so it cannot be applied as sent.
Status
HTTP/1.1 409 Conflict
Details
- Category: 4xx
- Status: Standard. Registered with IANA and defined by a current standards-track RFC.
- Specification: RFC 9110 §15.5.10
- Cacheable: Only with explicit cache headers
- Response body: Allowed
- Retry: Retry only after changing the request
409 says the request is well formed but incompatible with reality right now. Classic cases are a duplicate unique key, an edit based on a stale version of a document, and an operation that contradicts the resource's current lifecycle state, such as cancelling something already cancelled.
Unlike most 4xx codes, a 409 can become resolvable without changing the request at all: the conflicting state may clear on its own. The response body should carry enough detail for the client to reconcile.
Common causes
- A unique constraint violation, for example registering an email that already exists.
- Concurrent edits where the second write is based on an outdated version.
- A state machine rejecting a transition, such as shipping an order that was refunded.
- A version control style conflict in a PUT that the server cannot merge.
How to fix it
As the client
- Re-read the current state, merge, and resubmit rather than retrying the identical request.
- Use conditional requests with If-Match and an ETag so conflicts surface as 412 before the write happens.
As the server
- Explain the conflict in the body: which field, which constraint, and what the current value is.
- Use 422 for semantic validation errors and keep 409 for genuine state conflicts, so clients can handle them differently.
Examples
POST /api/accounts HTTP/1.1
Host: api.example.com
Content-Type: application/json
{"email":"user@example.com"}
HTTP/1.1 409 Conflict
Content-Type: application/json; charset=utf-8
{"error":"duplicate","field":"email","detail":"Account already exists"}