HTTP Status Codes: The Complete Reference

Every HTTP response carries a three-digit status code, and most developers know maybe eight of them by heart. The rest get looked up — usually at the worst possible moment, while something is broken. This is the full list, organised so you can find what you need, with real attention to the handful of codes people consistently use incorrectly.

The one-line version

The first digit is the whole story: 1xx wait, 2xx it worked, 3xx look elsewhere, 4xx you made a mistake, 5xx the server made a mistake. If you remember nothing else, remember that 4xx blames the client and 5xx blames the server — that single distinction resolves most debugging arguments.

How the five classes work

Status codes are deliberately designed so a client that has never seen a particular code can still handle it sensibly. A client encountering an unknown 418 is required to treat it as a generic 400; an unknown 503 is treated as a generic 500. This is why the classes matter more than the individual numbers — the class carries the actionable meaning, and the specific code carries the detail.

Class Name Meaning Whose fault
1xx Informational Request received, still processing Nobody
2xx Success Received, understood, accepted Nobody
3xx Redirection Further action needed to complete Nobody
4xx Client Error The request was wrong The caller
5xx Server Error The request was fine; the server failed The server

⚠️ The most common status code mistake

Returning 200 OK with an error message in the body. Every monitoring tool, every retry policy, every cache and every search engine reads the status code, not your JSON. An API that answers 200 {"error": "not found"} is invisible to your own alerting. If something went wrong, say so in the status line.

1xx — Informational

CodeNameWhat it means
100ContinueHeaders received; the client may send the body. Used with Expect: 100-continue so a large upload is not wasted on a request the server would reject.
101Switching ProtocolsThe server is changing protocol as requested — this is how a WebSocket handshake completes.
102ProcessingWebDAV. The request is underway but no response is ready. Largely deprecated.
103Early HintsSends Link headers before the real response so the browser can start preloading critical assets. A genuine performance win, increasingly supported by CDNs.

2xx — Success

CodeNameWhat it means
200OKThe general-purpose success. A GET returns the resource; a POST returns the result.
201CreatedA new resource now exists. Should include a Location header pointing at it. The correct answer to a successful POST that creates something.
202AcceptedQueued, not done. For asynchronous work — the response says "I took this", not "I finished this".
203Non-Authoritative InformationA proxy modified the response. Rare.
204No ContentSuccess with an intentionally empty body. The right answer to a DELETE, or a PUT where you have nothing to return.
205Reset ContentTells the client to clear the form it just submitted. Almost never used.
206Partial ContentThe response to a Range request. Powers video seeking and resumable downloads.
207Multi-StatusWebDAV. An XML body carrying several independent statuses.
226IM UsedDelta encoding applied. Effectively unused in practice.

201 vs 202 vs 204

These three are all "it worked" but promise different things, and picking the wrong one misleads clients. 201 guarantees the resource exists now and tells you where. 202 guarantees nothing except that the work is queued — the operation may still fail later, so the client must poll or subscribe to find out. 204 says the operation completed and there is deliberately nothing to send back, which is different from sending an empty body with 200 (that implies there was something to send and it happened to be empty).

3xx — Redirection

CodeNameWhat it means
301Moved PermanentlyThe resource has a new permanent URL. Cached indefinitely by browsers. Passes SEO signals.
302FoundTemporary. The original URL remains canonical. Historically clients turned POST into GET here.
303See Other"Go GET this other thing." The classic post-then-redirect pattern that stops form resubmission on refresh.
304Not ModifiedYour cached copy is still fresh. Sent in reply to a conditional request. No body — that is the entire point.
307Temporary RedirectLike 302, but the method and body are guaranteed to be preserved.
308Permanent RedirectLike 301, but the method and body are guaranteed to be preserved.

💡 The 301/302/307/308 grid

There are only two questions: is the move permanent, and must the HTTP method survive? That gives a two-by-two grid.

  • Permanent, method may change: 301
  • Permanent, method preserved: 308
  • Temporary, method may change: 302
  • Temporary, method preserved: 307

The "method may change" wording is historical baggage: the specification for 301 and 302 said the method should be preserved, but browsers converted POST to GET anyway, and the behaviour became too entrenched to fix. 307 and 308 were introduced purely to have codes whose behaviour is unambiguous.

Why 304 matters more than you think

A 304 is the cheapest possible successful response. The client sends If-None-Match with the ETag it already has, or If-Modified-Since with a timestamp; if nothing changed, the server replies 304 with headers only and no body. For a site serving large images or bundles, correct 304 handling can cut bandwidth dramatically while keeping content instantly fresh when it does change.

# Request — the client already has version "a3f9c1" GET /logo.png HTTP/1.1 Host: example.com If-None-Match: "a3f9c1" # Response — nothing changed, so no body is sent at all HTTP/1.1 304 Not Modified ETag: "a3f9c1" Cache-Control: max-age=3600

4xx — Client Error

CodeNameWhat it means
400Bad RequestMalformed syntax. The server could not parse what you sent.
401UnauthorizedAuthentication required or failed. Must include a WWW-Authenticate header. Misnamed — it means unauthenticated.
402Payment RequiredReserved since 1997. Some APIs now use it for billing failures.
403ForbiddenAuthenticated but not permitted. Re-authenticating will not help.
404Not FoundNo resource at this URL. The server will not say whether it ever existed.
405Method Not AllowedThe URL exists but not for this verb. Must include an Allow header listing what is permitted.
406Not AcceptableCannot produce a response matching the client's Accept headers.
407Proxy Authentication RequiredLike 401, but for the proxy rather than the origin.
408Request TimeoutThe client took too long to send its request.
409ConflictThe request clashes with current state — an edit conflict, or a duplicate unique key.
410GoneDeliberately deleted and not coming back. Stronger than 404; search engines de-index faster.
411Length RequiredA Content-Length header is mandatory here.
412Precondition FailedAn If-Match style condition was not met. The basis of optimistic locking.
413Content Too LargeThe upload exceeds the server limit. Formerly "Payload Too Large".
414URI Too LongUsually a GET that should have been a POST.
415Unsupported Media TypeThe Content-Type is one the endpoint will not accept.
416Range Not SatisfiableThe requested byte range lies outside the file.
417Expectation FailedThe Expect header cannot be met.
418I'm a TeapotAn April Fools' joke from 1998 that was never removed. Genuinely reserved.
421Misdirected RequestThis server cannot produce a response for the requested authority.
422Unprocessable ContentSyntax is valid; semantics are not. The standard validation-failure code.
423LockedWebDAV. The resource is locked.
424Failed DependencyWebDAV. A previous request in the chain failed.
425Too EarlyRefusing to risk replay of an early-data request.
426Upgrade RequiredSwitch protocol — usually to TLS.
428Precondition RequiredForces conditional requests to prevent lost updates.
429Too Many RequestsRate limited. Should include Retry-After.
431Request Header Fields Too LargeUsually an oversized cookie.
451Unavailable For Legal ReasonsBlocked by law. The number references Fahrenheit 451.

404 vs 410, and why it matters for search

Both say the resource is not here. 404 is agnostic — it might return, it might never have existed. 410 Gone is a definite statement: this existed, we removed it deliberately, stop asking. Search engines act on that difference: a 410 typically drops out of the index faster than a 404, which they may re-crawl for weeks in case it was a mistake. If you have permanently retired a section of a site, 410 is the honest and faster signal.

The soft 404 problem

A soft 404 is a page that looks like an error to a human but returns 200 OK to a machine. It happens most often with single-page applications, where the server returns the app shell for every path and the router decides afterwards that the route does not exist. By then the status code has already been sent. Search engines index these as real pages, filling your index with hundreds of identical "page not found" entries. The fix is server-side: the server must know which routes exist and return a genuine 404 status for the rest.

5xx — Server Error

CodeNameWhat it means
500Internal Server ErrorThe catch-all. Something threw an exception and nobody handled it.
501Not ImplementedThe server does not support this method at all, for any resource.
502Bad GatewayA proxy got an invalid response from upstream. Classic sign that your application server is down behind nginx.
503Service UnavailableTemporarily overloaded or in maintenance. Should include Retry-After. The correct code for planned downtime.
504Gateway TimeoutThe upstream server did not answer in time. The app is up but too slow.
505HTTP Version Not SupportedRare.
507Insufficient StorageWebDAV. Out of disk.
508Loop DetectedWebDAV. Infinite recursion while processing.
511Network Authentication RequiredA captive portal — the hotel wifi login page.

502 vs 503 vs 504 tells you where to look

These three are the everyday operational codes and they point at genuinely different failures:

  • 502 Bad Gateway — the proxy reached your app and got garbage back, or could not connect at all. Check whether the application process is running and listening on the expected port.
  • 503 Service Unavailable — the server is deliberately refusing work. Check for maintenance mode, a full connection pool, or a load shedder doing its job.
  • 504 Gateway Timeout — the app accepted the connection and never finished. Check for slow database queries, deadlocks, or an external API you depend on hanging.

The distinction is worth wiring into your alerting. A spike in 504s and a spike in 502s call for completely different first moves, and treating them as one "5xx rate" metric throws away the most useful signal you have.

✅ Always send Retry-After with 503 and 429

Both codes mean "try again later", and without Retry-After the client has to guess. Guessing usually means retrying immediately, which is exactly what you do not want from a service that is already overloaded. The header accepts either a number of seconds or an HTTP date.

Choosing the right code: a decision path

When you are writing an endpoint and are unsure, walk this in order:

  1. Did the server fail through no fault of the caller? → 5xx. Pick 503 if it is temporary and expected, 500 if it is an unhandled bug.
  2. Could the client not be identified? → 401.
  3. Is the client identified but not permitted? → 403.
  4. Does the resource not exist? → 404, or 410 if it was deliberately removed.
  5. Does the URL exist but not for this method? → 405, with an Allow header.
  6. Could the body not be parsed? → 400.
  7. Did it parse but fail validation? → 422.
  8. Does it clash with current state? → 409.
  9. Did you create something? → 201 with a Location header.
  10. Did it work with nothing to return? → 204.
  11. Otherwise → 200.

Checking status codes yourself

The fastest way to see what a server is really sending — bypassing any friendly error page your browser might substitute:

# Show headers only curl -I https://example.com/some-page # Follow redirects and print the chain of codes curl -sIL -o /dev/null -w "%{http_code} %{url_effective}\n" https://example.com # Full request and response, including TLS negotiation curl -v https://example.com/api/thing

In the browser, the Network tab of developer tools shows the status for every request. Two things to watch for: a chain of several redirects where one would do (each hop costs a full round trip), and any request returning 200 that should have failed.

Reading a messy API response?

Paste the JSON body and get it formatted, validated and readable in a second — entirely in your browser, nothing uploaded.

Open the JSON Formatter →

The short list worth memorising

You will never need most of the codes above. In day-to-day work these twelve cover almost everything: 200, 201, 204, 301, 302, 304, 400, 401, 403, 404, 429, 500. Learn those properly, understand the 401/403 and 400/422 distinctions, and bookmark this page for the rest.

The underlying principle is worth more than the list: a status code is a machine-readable contract about what happened and what the client should do next. Every time you reach for 200 because it is easier, you are breaking that contract for every cache, proxy, monitor and crawler between you and your user.

Frequently Asked Questions

What is the difference between 401 and 403?

401 Unauthorized means the server does not know who you are — you sent no credentials, or the ones you sent were invalid. Retrying with valid credentials could succeed. 403 Forbidden means the server knows exactly who you are and you are still not allowed. Retrying with the same identity will never succeed. In short: 401 is 'who are you?', 403 is 'not you'.

Should I use 301 or 308 for a permanent redirect?

Use 301 for ordinary page moves. It is universally supported and is what search engines expect. Use 308 only when you must guarantee that a POST request stays a POST after redirecting — 301 historically allowed clients to convert POST to GET, and many still do. For SEO purposes both pass ranking signals, but 301 has decades of proven behaviour behind it.

Is a 404 bad for SEO?

No. A 404 for a page that genuinely does not exist is correct and healthy. What harms you is returning 200 OK for a missing page — a soft 404 — because search engines then index an error page as real content. Also avoid redirecting every 404 to your homepage; Google treats that as a soft 404 too. Return a real 404 with a helpful page.

What does 429 Too Many Requests mean?

You have exceeded a rate limit. The response should include a Retry-After header telling you how many seconds to wait, or a date after which to retry. Well-behaved clients read that header and back off; clients that immediately retry usually make the situation worse and get blocked for longer.

When should an API return 422 instead of 400?

Return 400 Bad Request when the request itself is malformed — broken JSON, a missing required header, a payload the parser cannot read. Return 422 Unprocessable Content when the syntax is perfectly valid but the meaning is wrong, such as a well-formed JSON body with an email field that is not an email address. The distinction tells the client whether to fix its serialisation or its data.

P

Written by Paras

We build free, browser-based file tools and write the reference material we wish existed when we were looking things up. Spotted an error? Tell us and we will fix it.