HTTP status codes

The codes that actually matter in production — and the ones applications routinely get wrong.

The five classes

RangeMeaning
1xxInformational — keep going
2xxSuccess
3xxRedirection — go elsewhere
4xxClient error — fix the request
5xxServer error — we broke something

The class is the part a client should branch on. Only the first digit is semantic; the other two are a label. That is why a client that switches on the exact code breaks when a server starts sending 422 where it used to send 400 — both are 4xx, and both mean the same thing to the caller: do not retry unchanged.

HTTP/1.1 404 Not Found
Content-Type: application/problem+json
Cache-Control: no-store

{
  "type": "https://example.com/errors/not-found",
  "title": "No such article",
  "status": 404,
  "detail": "Article 8f2c was deleted on 2026-08-01."
}
💡
The status line is the first line a client sees. A JSON body describing the error is useful to a human, but the code is the contract — an API that returns 200 OK with an error object forces every caller to parse the payload to find out whether the call worked.

The ones you will meet daily

CodeUse it for
200 OKStandard success with a body
201 CreatedResource created — send Location
204 No ContentSuccess, nothing to return
301 / 308Permanent redirect (308 preserves the method)
302 / 307Temporary redirect (307 preserves the method)
304 Not ModifiedCache is still valid — for conditional requests
400 Bad RequestMalformed request; failed validation
401 UnauthorizedAuthentication required or invalid
403 ForbiddenAuthenticated but not permitted
404 Not FoundNo such resource
409 ConflictState conflict (duplicate, wrong version)
422Well-formed but semantically invalid
429 Too Many RequestsRate limited — include Retry-After
500Unhandled server fault
502 / 503 / 504Bad gateway / unavailable / gateway timeout

Common mistakes

  • Returning 200 with an error body: clients cannot tell success from failure without parsing.
  • Using 401 where 403 belongs: 401 means 'who are you?', 403 means 'I know who you are, and no'.
  • Returning 404 for resources the user may not know exist — sometimes 403/404 by choice for privacy.
  • Redirecting POST with 302 — many clients convert it to GET. Use 307/308 to preserve the method.
⚠️
Do not return 3xx from an API endpoint expecting JSON unless redirect following is guaranteed. Many clients will not follow, and the redirect body gets ignored.

FAQ

Should validation failures be 400 or 422?
Either is defensible; 400 is the broad 'bad request' and 422 signals syntactically valid but semantically rejected. Pick one and document it.
What should I return for a health check?
200 with a tiny body, or 503 when dependencies are unhealthy so load balancers can pull the instance out.

HTTP methods HTTP headers

Last refreshed 2026-09-17.