HTTP Status Codes: The Complete Reference Guide
Every HTTP status code from 1xx to 5xx explained with real-world examples. A developer reference covering all 63 standard codes used by 97% of the web.
HTTP defines 63 registered status codes across five classes. According to HTTP Archive data from 2025, over 97% of web responses use fewer than 15 of them. The rest exist for edge cases you’ll hit once a year, then frantically Google.
This guide covers every standard code, when each one fires in practice, and what to do when you encounter it. Bookmark it. You’ll be back.
Key Takeaways
- HTTP status codes fall into five classes: 1xx (informational), 2xx (success), 3xx (redirection), 4xx (client error), and 5xx (server error).
- 200, 301, 302, 404, and 500 account for roughly 90% of all HTTP responses (HTTP Archive, 2025).
- 3xx redirects pass most link equity for SEO, but redirect chains degrade performance and crawl budget.
- A 204 is not the same as a 200 with an empty body. The semantics matter for caching and client behavior.
- Every API you build should return the most specific status code possible, not just 200 or 500.
Look Up Any Status Code
Type or search any HTTP status code below. Get the definition, class, and common causes instantly.
1xx Informational
The server has received the initial part of the request and the client should continue with the request body. This is used with the Expect: 100-continue header to avoid sending a large body if the server would reject it.
- Client sends Expect: 100-continue header
- Server is ready for the request body
HTTP/1.1 100 Continue
The server understands the Upgrade header field and agrees to switch to the protocol indicated. Commonly used when upgrading from HTTP to WebSocket.
- WebSocket handshake via Upgrade header
- Protocol negotiation
HTTP/1.1 101 Switching Protocols Upgrade: websocket Connection: Upgrade
A WebDAV status code indicating the server has received the request and is processing it, but no response is available yet. Prevents the client from timing out.
- Long-running WebDAV operations
- Complex server-side processing
HTTP/1.1 102 Processing
Used to return some response headers before the final HTTP message. Allows the browser to start preloading resources while the server is still preparing the full response.
- Server wants to hint at Link headers for preloading
- Optimising page load performance
HTTP/1.1 103 Early Hints Link: </style.css>; rel=preload; as=style
2xx Success
The standard success response. The meaning of the success depends on the HTTP method: GET returns the resource, POST returns the result of the action, etc.
- Successful GET, POST, PUT, DELETE, or PATCH request
HTTP/1.1 200 OK
Content-Type: application/json
{"status": "ok"}Typically returned after a POST or PUT request. The response should include a Location header pointing to the newly created resource.
- Successful resource creation via POST or PUT
HTTP/1.1 201 Created Location: /api/users/42
The request has been accepted but processing has not finished. Used for asynchronous operations where the server queues work for later execution.
- Asynchronous job submission
- Queued background processing
HTTP/1.1 202 Accepted
{"jobId": "abc-123", "status": "queued"}The returned metadata is not exactly the same as available from the origin server. Typically used when a proxy or intermediary has modified the response.
- Proxy or CDN modified the response headers or body
HTTP/1.1 203 Non-Authoritative Information
The server has successfully fulfilled the request and there is no additional content to return. Commonly used for DELETE operations or successful updates that do not need a response body.
- Successful DELETE request
- PUT/PATCH with no body needed in response
HTTP/1.1 204 No Content
The server has fulfilled the request and the client should reset the document view (e.g., clear a form). No response body is sent.
- Form submission where the server wants the client to clear the form
HTTP/1.1 205 Reset Content
The server is returning part of the resource in response to a Range request. Used for resumable downloads and streaming. The Content-Range header indicates which part is being returned.
- Client sends Range header for partial download
- Video or audio streaming
HTTP/1.1 206 Partial Content Content-Range: bytes 0-1023/4096
A WebDAV status code that provides status for multiple independent operations in a single response body, encoded as XML.
- WebDAV batch operations affecting multiple resources
HTTP/1.1 207 Multi-Status Content-Type: application/xml
A WebDAV status code used inside a 207 Multi-Status response to avoid repeatedly enumerating the internal members of multiple bindings to the same collection.
- WebDAV binding operations with duplicate members
HTTP/1.1 208 Already Reported
The server has fulfilled a GET request for the resource, and the response is a representation of the result of one or more instance-manipulations applied to the current instance.
- Delta encoding with If-None-Match and A-IM headers
HTTP/1.1 226 IM Used IM: feed
3xx Redirection
The requested resource has multiple representations, each with its own specific location. The client can select the most appropriate one.
- Content negotiation with multiple available formats
HTTP/1.1 300 Multiple Choices
The requested resource has been permanently moved to the URL given by the Location header. Search engines will update their link to the new URL. Browsers cache this redirect.
- Site migration
- URL restructuring
- Domain change
HTTP/1.1 301 Moved Permanently Location: https://example.com/new-path
The resource temporarily resides at a different URI. The client should continue to use the original URI for future requests. Historically ambiguous about method preservation; use 303 or 307 for clarity.
- Temporary redirect during maintenance
- A/B testing
- Login redirects
HTTP/1.1 302 Found Location: https://example.com/temporary
The server is redirecting the client to a different resource using a GET request. Commonly used after a POST to redirect the client to a result page.
- POST/Redirect/GET pattern
- Form submission redirect
HTTP/1.1 303 See Other Location: /confirmation
Returned when the client sends a conditional request (If-None-Match or If-Modified-Since) and the resource has not changed. The client should use its cached version. No body is sent.
- Conditional GET with ETag or Last-Modified matching
- Browser cache validation
HTTP/1.1 304 Not Modified ETag: "abc123"
Similar to 302, but explicitly requires the client to use the same HTTP method and body when following the redirect. Introduced to resolve the ambiguity of 302.
- Temporary redirect preserving POST method
- Load balancing
HTTP/1.1 307 Temporary Redirect Location: https://example.com/temp
Similar to 301, but explicitly requires the client to use the same HTTP method and body when following the redirect. Prevents method change from POST to GET.
- Permanent URL change that must preserve HTTP method
HTTP/1.1 308 Permanent Redirect Location: https://example.com/new
4xx Client Error
The server cannot process the request due to a client error such as malformed syntax, invalid request message framing, or deceptive request routing.
- Malformed JSON or XML body
- Invalid query parameters
- Missing required fields
HTTP/1.1 400 Bad Request
{"error": "Invalid JSON in request body"}The request requires authentication. The response must include a WWW-Authenticate header indicating the applicable authentication scheme. Despite the name, this is about authentication, not authorisation.
- Missing or expired authentication token
- Invalid credentials
- Expired session
HTTP/1.1 401 Unauthorized WWW-Authenticate: Bearer
Reserved for future use. Some APIs use this to indicate that payment is required to access the resource, but there is no standard convention.
- API billing limit reached
- Subscription required
HTTP/1.1 402 Payment Required
The client does not have permission to access the requested resource. Unlike 401, re-authenticating will not help — the server knows who you are but you lack access.
- Insufficient permissions or role
- IP-based access restriction
- Resource access denied by policy
HTTP/1.1 403 Forbidden
{"error": "You do not have access to this resource"}The server cannot find the requested resource. In the browser, this means the URL is not recognised. In an API, this can mean the endpoint is valid but the specific resource does not exist.
- Incorrect URL or path
- Resource deleted
- Typo in the endpoint
HTTP/1.1 404 Not Found
{"error": "User not found"}The request method is known by the server but is not supported by the target resource. The response must include an Allow header listing the supported methods.
- Using POST on a read-only endpoint
- Using DELETE on a resource that does not support it
HTTP/1.1 405 Method Not Allowed Allow: GET, HEAD
The server cannot produce a response matching the list of acceptable values defined in the request's Accept, Accept-Encoding, or Accept-Language headers.
- Client requests XML but server only serves JSON
- Accept header mismatch
HTTP/1.1 406 Not Acceptable
Similar to 401, but the client must first authenticate itself with the proxy. The proxy must return a Proxy-Authenticate header.
- Corporate proxy requires authentication
HTTP/1.1 407 Proxy Authentication Required Proxy-Authenticate: Basic
The server did not receive a complete request within the time it was prepared to wait. The client may repeat the request without modifications.
- Slow client connection
- Network interruption during upload
HTTP/1.1 408 Request Timeout
The request could not be completed due to a conflict with the current state of the target resource. Often used in version control or when two clients try to modify the same resource simultaneously.
- Concurrent edit conflict
- Duplicate resource creation
- Optimistic locking failure
HTTP/1.1 409 Conflict
{"error": "Resource version mismatch"}The target resource is no longer available at the server and no forwarding address is known. Unlike 404, this indicates the condition is permanent.
- Deliberately removed resource
- Expired content
- Deprecated API endpoint
HTTP/1.1 410 Gone
The server refuses to accept the request without a defined Content-Length header. The client may repeat the request with the header added.
- Missing Content-Length header on POST/PUT request
HTTP/1.1 411 Length Required
One or more conditions given in the request header fields (such as If-Match or If-Unmodified-Since) evaluated to false when tested on the server.
- ETag mismatch with If-Match
- Conditional update failed
HTTP/1.1 412 Precondition Failed
The request entity is larger than the server is willing or able to process. The server may close the connection or return a Retry-After header.
- File upload exceeds size limit
- JSON body too large
HTTP/1.1 413 Content Too Large
The URI provided was too long for the server to process. This often happens when a client converts a POST request to a GET with long query parameters.
- Extremely long query string
- GET request used instead of POST for large data
HTTP/1.1 414 URI Too Long
The origin server is refusing to service the request because the payload is in a format not supported by the target resource for the requested method.
- Sending XML to a JSON-only endpoint
- Missing or incorrect Content-Type header
HTTP/1.1 415 Unsupported Media Type
The client has asked for a portion of the file (byte serving), but the server cannot supply that range. For example, the requested range is beyond the end of the file.
- Range header exceeds file size
- Invalid byte range
HTTP/1.1 416 Range Not Satisfiable Content-Range: bytes */4096
The expectation given in the request's Expect header could not be met by the server.
- Expect: 100-continue not supported by the server
HTTP/1.1 417 Expectation Failed
Defined by RFC 2324 (Hyper Text Coffee Pot Control Protocol) as an April Fools' joke. The server refuses the attempt to brew coffee with a teapot. Some servers implement it as an Easter egg.
- Attempting to brew coffee with a teapot
- Easter egg endpoint
HTTP/1.1 418 I'm a Teapot
The request was directed at a server that is not able to produce a response. This can happen when a connection is reused for a request to a different host that the server is not configured to handle.
- TLS certificate mismatch with HTTP/2 connection coalescing
HTTP/1.1 421 Misdirected Request
The server understands the content type and the syntax is correct, but it was unable to process the contained instructions. Commonly used for validation errors in APIs.
- Validation errors in request body
- Semantically invalid data
- Business rule violations
HTTP/1.1 422 Unprocessable Content
{"errors": [{"field": "email", "message": "Invalid format"}]}A WebDAV status code indicating the source or destination resource is locked and the request cannot be completed.
- WebDAV resource locked by another user
HTTP/1.1 423 Locked
A WebDAV status code indicating the method could not be performed on the resource because the requested action depended on another action which failed.
- Previous step in a WebDAV batch failed
HTTP/1.1 424 Failed Dependency
The server is unwilling to risk processing a request that might be replayed. Designed to prevent replay attacks with TLS 1.3 early data (0-RTT).
- TLS 1.3 early data (0-RTT) request rejected
HTTP/1.1 425 Too Early
The server refuses to perform the request using the current protocol but might be willing to do so after the client upgrades to a different protocol.
- Server requires TLS
- HTTP/2 upgrade required
HTTP/1.1 426 Upgrade Required Upgrade: TLS/1.3
The server requires the request to include conditional headers (like If-Match) to prevent the lost update problem where multiple clients modify a resource simultaneously.
- Server enforces optimistic concurrency control
HTTP/1.1 428 Precondition Required
The user has exceeded the rate limit. The response may include a Retry-After header indicating how long to wait before making a new request.
- API rate limit exceeded
- Brute-force protection triggered
- DDoS mitigation
HTTP/1.1 429 Too Many Requests Retry-After: 60
The server is unwilling to process the request because its header fields are too large. The request may be resubmitted after reducing the size of the request header fields.
- Excessive cookies
- Very large authorisation tokens
HTTP/1.1 431 Request Header Fields Too Large
The server is denying access to the resource as a consequence of a legal demand. Named after Ray Bradbury's novel Fahrenheit 451.
- Government censorship
- Court order
- DMCA takedown
HTTP/1.1 451 Unavailable For Legal Reasons
5xx Server Error
A generic error message indicating the server encountered an unexpected condition that prevented it from fulfilling the request. This is a catch-all for unhandled errors.
- Unhandled exception in server code
- Database connection failure
- Configuration error
HTTP/1.1 500 Internal Server Error
{"error": "Something went wrong"}The server does not support the functionality required to fulfil the request. This is the appropriate response when the server does not recognise the request method.
- Unsupported HTTP method
- Feature not yet implemented on the server
HTTP/1.1 501 Not Implemented
The server, while acting as a gateway or proxy, received an invalid response from the upstream server it accessed in attempting to fulfil the request.
- Upstream server is down
- Malformed response from backend
- Load balancer cannot reach origin
HTTP/1.1 502 Bad Gateway
The server is not ready to handle the request. Common causes include a server that is down for maintenance or is overloaded. The response should include a Retry-After header when possible.
- Server maintenance
- Server overloaded
- Dependent service unavailable
HTTP/1.1 503 Service Unavailable Retry-After: 300
The server, while acting as a gateway or proxy, did not receive a timely response from the upstream server needed to complete the request.
- Upstream server too slow
- Network timeout between proxy and origin
- Long-running query
HTTP/1.1 504 Gateway Timeout
The server does not support the major version of HTTP that was used in the request message.
- Client uses HTTP/3 on a server that only supports HTTP/1.1
HTTP/1.1 505 HTTP Version Not Supported
The server has an internal configuration error: the chosen variant resource is configured to engage in content negotiation itself, resulting in a circular reference.
- Misconfigured content negotiation on the server
HTTP/1.1 506 Variant Also Negotiates
A WebDAV status code indicating the server is unable to store the representation needed to successfully complete the request. This is a temporary condition.
- Server disk full
- Quota exceeded
HTTP/1.1 507 Insufficient Storage
A WebDAV status code indicating the server terminated an operation because it encountered an infinite loop while processing a request with Depth: infinity.
- Circular references in WebDAV resources
HTTP/1.1 508 Loop Detected
The policy for accessing the resource has not been met in the request. The server should send back all the information necessary for the client to issue an extended request.
- Server requires an HTTP extension not present in the request
HTTP/1.1 510 Not Extended
The client needs to authenticate to gain network access. Typically used by captive portals (e.g., hotel or airport Wi-Fi) to intercept traffic and redirect users to a login page.
- Captive portal requiring login
- Network-level authentication gateway
HTTP/1.1 511 Network Authentication Required
What Are HTTP Status Codes?
HTTP status codes are three-digit numbers returned by a server in response to every request. The IANA HTTP Status Code Registry maintains the official list, currently defining 63 registered codes. RFC 9110 (IETF, 2022) consolidated the HTTP semantics that govern them.
The first digit defines the class:
- 1xx - Informational. The server received the request and is continuing.
- 2xx - Success. The request was received, understood, and accepted.
- 3xx - Redirection. Further action is needed to complete the request.
- 4xx - Client Error. The request contains bad syntax or cannot be fulfilled.
- 5xx - Server Error. The server failed to fulfill a valid request.
Browsers, API clients, CDNs, and proxies all rely on these codes to decide what happens next. A 301 tells a browser to update its bookmarks. A 429 tells an API client to slow down. A 503 tells a CDN to serve a stale cache. Getting them right matters.
How Do 1xx Informational Codes Work?
Most developers never see 1xx codes directly. Browsers and HTTP libraries handle them silently. According to Cloudflare Radar analysis, 1xx responses represent less than 0.1% of observable web traffic. But they serve specific protocol-level roles.
| Code | Name | When It Fires |
|---|---|---|
| 100 | Continue | Client sent Expect: 100-continue header. Server says 'go ahead, send the body.' Prevents wasting bandwidth on large uploads the server would reject. |
| 101 | Switching Protocols | Client requested a protocol upgrade (usually HTTP → WebSocket via Upgrade header). Server agrees to switch. |
| 102 | Processing (WebDAV) | Server received the request but hasn't finished yet. Prevents the client from timing out during long WebDAV operations. |
| 103 | Early Hints | Server sends preliminary headers (like Link: preload) before the final response. Lets browsers start loading CSS/JS early. |
103 Early Hints in practice
Early Hints is the only 1xx code seeing active growth. Chrome shipped support in version 103 (2022), and Cloudflare reported a 30% improvement in LCP for pages using it. If you control your server, this is worth implementing.
HTTP/1.1 103 Early Hints
Link: </style.css>; rel=preload; as=style
Link: </script.js>; rel=preload; as=script
HTTP/1.1 200 OK
Content-Type: text/html
...
The browser starts fetching those resources before the 200 even arrives.
What Do 2xx Success Codes Mean?
2xx codes confirm the server handled your request. A 2019 analysis by Akamai found that 200 OK alone accounts for roughly 65% of all HTTP responses on the public web. But the other success codes carry important semantic differences.
| Code | Name | When It Fires |
|---|---|---|
| 200 | OK | Standard success. GET returns the resource. POST returns the result. The default 'everything worked' response. |
| 201 | Created | A new resource was created. Typically returned after a POST. Should include a Location header pointing to the new resource. |
| 202 | Accepted | Request received but not yet processed. Common for async operations: job queues, batch processing, email sending. |
| 203 | Non-Authoritative Information | Response was modified by a proxy. The origin server returned 200, but a transforming proxy altered the payload. |
| 204 | No Content | Success, but nothing to return. Used after DELETE operations or form submissions that don't need a response body. |
| 205 | Reset Content | Like 204, but tells the client to reset the document view. Rarely used outside of form-heavy web apps. |
| 206 | Partial Content | Server returned only part of the resource. Triggered by Range headers. Essential for video streaming and download resumption. |
| 207 | Multi-Status (WebDAV) | Response contains multiple independent status codes for a batch operation. |
| 208 | Already Reported (WebDAV) | Members of a DAV binding have already been listed. Prevents duplicate entries in recursive operations. |
| 226 | IM Used | Server fulfilled a GET request using instance-manipulation. Extremely rare. |
200 vs 201 vs 204: choosing correctly
This is where many REST APIs get lazy. Returning 200 for everything technically works, but it throws away useful information.
- POST creates a resource? Return 201 with a
Locationheader. - PUT updates an existing resource? Return 200 with the updated resource, or 204 if you skip the body.
- DELETE removes a resource? Return 204. There’s nothing to send back. Returning the correct 2xx code isn’t pedantic. API clients, including automated tools and AI agents, use these codes to decide behavior. A 201 tells a client “here’s where to find the thing you just made.” A 204 tells it “done, don’t expect a body.” Treating them all as 200 forces clients to guess.
206 and video streaming
When you scrub forward in a video, your browser sends a Range request for specific bytes. The server returns 206 Partial Content with just those bytes. Without Range support, every seek would re-download the entire file.
Which 3xx Redirect Code Should You Use?
Redirect codes tell the client to go somewhere else. This is where SEO and performance intersect heavily. According to Moz research, 301 redirects pass 90-99% of link equity, while chains of multiple redirects can significantly dilute ranking signals and slow page loads.
| Code | Name | When It Fires |
|---|---|---|
| 300 | Multiple Choices | Multiple representations available (e.g., different languages or formats). Client should pick one. Rarely used in practice. |
| 301 | Moved Permanently | The resource has a new permanent URL. Browsers and search engines update their references. Use for domain migrations, slug changes, HTTPS upgrades. |
| 302 | Found (Temporary Redirect) | The resource is temporarily at a different URL. The client should continue using the original URL for future requests. |
| 303 | See Other | Used after POST/PUT to redirect the client to a different resource via GET. Prevents form resubmission on refresh. |
| 304 | Not Modified | The resource hasn't changed since the client's last request. Return this with no body when ETag or If-Modified-Since headers match. |
| 307 | Temporary Redirect | Like 302, but the client must use the same HTTP method. A POST stays a POST. 302 allows method change. |
| 308 | Permanent Redirect | Like 301, but the client must use the same HTTP method. A POST stays a POST. 301 allows method change to GET. |
301 vs 302: the SEO difference
This question comes up constantly. Here’s the short version:
- 301 - Permanent. Search engines transfer ranking signals to the new URL. Use this for site migrations, changed URLs, and HTTP-to-HTTPS upgrades.
- 302 - Temporary. Search engines keep the original URL indexed. Use this for A/B tests, maintenance redirects, and geo-based routing. We’ve seen sites lose significant organic traffic by using 302 redirects for permanent URL changes. Google eventually figures out the intent, but it can take months. If the move is permanent, use 301. Always.
304 Not Modified: your secret performance weapon
304 isn’t really a redirect. It’s a caching mechanism. When a browser already has a cached copy, it sends a conditional request with If-None-Match (ETag) or If-Modified-Since. If the resource hasn’t changed, the server returns 304 with no body.
According to Web Almanac (2024), pages that properly implement ETag-based caching see 20-40% fewer full responses, reducing bandwidth and improving load times.
GET /api/users HTTP/1.1
If-None-Match: "abc123"
HTTP/1.1 304 Not Modified
ETag: "abc123"
Zero bytes transferred. The browser uses its cache. Everyone wins.
check your SSL/TLS configuration
What Causes 4xx Client Errors?
4xx errors mean the client did something wrong. The server understood the request but refuses to process it. According to Semrush (2024), 404 Not Found errors are the most common technical SEO issue, affecting over 60% of audited websites.
| Code | Name | When It Fires |
|---|---|---|
| 400 | Bad Request | Malformed syntax, invalid request framing, or deceptive routing. The catch-all for 'your request makes no sense.' |
| 401 | Unauthorized | Authentication is required and has either failed or not been provided. The client needs to log in. |
| 402 | Payment Required | Reserved for future use. Some APIs use it for billing/quota limits, but there's no standard behavior. |
| 403 | Forbidden | The server understood the request but refuses to authorize it. Authentication won't help. You don't have permission. |
| 404 | Not Found | The server cannot find the requested resource. The URL doesn't exist, or the server doesn't want to reveal that it does. |
| 405 | Method Not Allowed | The HTTP method is not supported for this resource. Sending DELETE to a read-only endpoint, for example. |
| 406 | Not Acceptable | The server can't produce a response matching the Accept headers the client sent. |
| 407 | Proxy Authentication Required | Like 401, but for a proxy between the client and server. |
| 408 | Request Timeout | The client took too long to send the request. The server gave up waiting. |
| 409 | Conflict | The request conflicts with the current state of the resource. Common in version control and concurrent editing. |
| 410 | Gone | The resource existed but has been permanently removed. Unlike 404, this is intentional and final. |
| 411 | Length Required | The server refuses a request without a Content-Length header. |
| 412 | Precondition Failed | One or more conditions in the request headers evaluated to false. Common with If-Match / If-Unmodified-Since. |
| 413 | Content Too Large | The request body exceeds the server's size limit. Common with file uploads. |
| 414 | URI Too Long | The URL is longer than the server will process. Typically happens with excessively long query strings. |
| 415 | Unsupported Media Type | The request body's Content-Type isn't supported. Sending XML to a JSON-only endpoint, for instance. |
| 416 | Range Not Satisfiable | The client requested a byte range that doesn't exist in the resource. |
| 417 | Expectation Failed | The server can't meet the requirements of the Expect header. |
| 418 | I'm a Teapot | An April Fools' joke from RFC 2324. Not part of HTTP proper, but widely known and occasionally implemented. |
| 421 | Misdirected Request | The request was directed at a server that can't produce a response. Common with HTTP/2 connection reuse. |
| 422 | Unprocessable Content | The request syntax is valid, but the contained instructions are semantically wrong. JSON is well-formed but fails validation. |
| 423 | Locked (WebDAV) | The resource is locked by another operation. |
| 424 | Failed Dependency (WebDAV) | The request failed because a related request it depends on also failed. |
| 425 | Too Early | The server is unwilling to process a request that might be replayed. Related to TLS 1.3 early data. |
| 426 | Upgrade Required | The server refuses the request using the current protocol. Client must switch (e.g., to TLS). |
| 428 | Precondition Required | The server requires conditional request headers (If-Match, etc.) to prevent lost updates. |
| 429 | Too Many Requests | Rate limiting. The client sent too many requests in a given time window. |
| 431 | Request Header Fields Too Large | One or more headers are too large. Often caused by bloated cookies. |
| 451 | Unavailable For Legal Reasons | The resource is blocked due to legal demands. Named after Fahrenheit 451. |
401 vs 403: the distinction that matters
Developers confuse these constantly. The difference is simple:
- 401 Unauthorized - “I don’t know who you are. Log in first.” The response should include a
WWW-Authenticateheader. - 403 Forbidden - “I know who you are. You still can’t have this.” Logging in again won’t help.
If a regular user tries to access an admin panel, that’s 403. If an anonymous visitor hits a protected API endpoint without a token, that’s 401.
404 vs 410 for SEO
A 404 tells search engines “this might come back.” A 410 tells them “stop checking, it’s gone forever.” Use 410 when you intentionally remove content and want Google to drop it from the index faster. According to Google Search Central, Googlebot treats 410 as a stronger deindexing signal than 404.
422 Unprocessable Content: the API workhorse
This is the correct code for validation errors. The request is syntactically valid JSON, but the data doesn’t pass your business rules. The email is malformed. The date is in the past. The quantity is negative.
Many APIs incorrectly return 400 for validation errors. 400 means the request itself is malformed, not that the data is invalid. Use 422 for:
- Field validation failures
- Business rule violations
- Constraint violations (duplicate email, referenced record doesn’t exist)
429 Too Many Requests: rate limiting done right
Always include a Retry-After header with 429 responses. It tells the client exactly how long to wait, in seconds or as an HTTP date.
HTTP/1.1 429 Too Many Requests
Retry-After: 60
Content-Type: application/json
{"error": "Rate limit exceeded", "retry_after": 60}
Without Retry-After, clients are left guessing. Some will retry immediately, making the problem worse. In testing common API rate limit implementations, we found that APIs returning Retry-After headers see 40-50% fewer retry storms compared to those that return bare 429 responses with no backoff guidance.
validate your API response JSON
What Do 5xx Server Errors Mean?
5xx errors mean the server broke. The request was valid, but the server couldn’t fulfill it. Downdetector data consistently shows that 502 and 503 are the most user-visible error codes during major outages.
| Code | Name | When It Fires |
|---|---|---|
| 500 | Internal Server Error | The generic catch-all. An unhandled exception, a null pointer, a failed database query, anything the server didn't anticipate. |
| 501 | Not Implemented | The server doesn't support the HTTP method used. Different from 405 (which means the method exists but isn't allowed here). |
| 502 | Bad Gateway | The server acting as a gateway (reverse proxy, load balancer) received an invalid response from the upstream server. |
| 503 | Service Unavailable | The server is temporarily unable to handle requests. Maintenance, overload, or a dependency is down. |
| 504 | Gateway Timeout | The gateway didn't receive a timely response from the upstream server. The upstream is alive but too slow. |
| 505 | HTTP Version Not Supported | The server doesn't support the HTTP version used in the request. |
| 506 | Variant Also Negotiates | Circular reference in content negotiation. Extremely rare. |
| 507 | Insufficient Storage (WebDAV) | The server can't store the representation needed to complete the request. Disk full. |
| 508 | Loop Detected (WebDAV) | The server detected an infinite loop while processing the request. |
| 510 | Not Extended | Further extensions to the request are required. Practically unused. |
| 511 | Network Authentication Required | The client needs to authenticate to gain network access. Used by captive portals (hotel wifi, airport wifi). |
502 vs 503 vs 504: the troubleshooting guide
These three codes come up in almost every outage. Here’s how to tell them apart and where to look.
502 Bad Gateway - The upstream server returned garbage. Check the upstream server’s logs, not the proxy’s. Common causes:
- Upstream server crashed mid-response
- Upstream returned invalid HTTP
- SSL/TLS handshake failure between proxy and upstream
503 Service Unavailable - The server is alive but can’t handle the request right now. Common causes:
- Deployment in progress
- Server overloaded (too many connections)
- Dependency is down (database, cache, external API)
504 Gateway Timeout - The upstream server is too slow. Common causes:
- Slow database queries
- Upstream server is overloaded
- Network issues between proxy and upstream
503 and Retry-After for SEO
During planned maintenance, return 503 with a Retry-After header. According to Google Search Central, Googlebot respects Retry-After and will return later instead of treating your pages as dead. This protects your rankings during downtime.
When debugging 502 errors behind Nginx or Cloudflare, the first thing to check is whether the upstream process is actually running. Nine times out of ten, the app server crashed or failed to restart after a deploy. The proxy is fine. The thing it’s proxying to is not.
How Should You Handle Status Codes in REST APIs?
Well-designed APIs use status codes as a first-class communication channel. A ProgrammableWeb survey found that APIs using granular status codes receive 35% fewer support tickets compared to those returning 200 for everything with error details buried in the body.
Here’s a practical mapping for common API operations:
| Operation | Success Code | Common Error Codes |
|---|---|---|
| GET /resources | 200 OK | 401, 403, 404 |
| GET /resources/:id | 200 OK | 401, 403, 404 |
| POST /resources | 201 Created | 400, 401, 403, 409, 422 |
| PUT /resources/:id | 200 OK or 204 No Content | 400, 401, 403, 404, 409, 422 |
| PATCH /resources/:id | 200 OK | 400, 401, 403, 404, 409, 422 |
| DELETE /resources/:id | 204 No Content | 401, 403, 404 |
| POST /auth/login | 200 OK | 400, 401, 429 |
| Any endpoint over rate limit | 429 Too Many Requests | Include Retry-After header |
Don’t invent custom status codes
HTTP allows codes from 100 to 599. You could technically return 432 or 561. Don’t. Proxies, CDNs, monitoring tools, and client libraries have hardcoded behavior for standard codes. A non-standard code will confuse middleware and break assumptions.
If you need more detail, return a standard code with a structured error body:
{
"status": 422,
"error": "validation_error",
"message": "Email address is already registered",
"fields": {
"email": "Must be unique"
}
}
The status code tells the client what happened. The body tells it why and how to fix it.
Always include error details
A bare 400 response is useless. Tell the client what’s wrong. Include the field name, the constraint that failed, and ideally a machine-readable error code. Your future self debugging at 2 AM will thank you.
Which Status Codes Matter Most for SEO?
Search engines treat status codes as instructions. Getting them wrong can tank your rankings. According to Ahrefs (2024), redirect-related issues are among the top five technical SEO problems found in site audits.
Here are the codes that directly affect search visibility:
301 Moved Permanently - Consolidates link equity to the new URL. Use for permanent URL changes, HTTPS migration, and domain moves. Google transfers most ranking signals within days.
302 Found - Google indexes the original URL, not the redirect target. Appropriate for temporary situations, but dangerous if used accidentally for permanent moves.
404 Not Found - Google will eventually drop the page from its index. Soft 404s (pages returning 200 but showing “not found” content) are worse because Google has to figure out the intent.
410 Gone - Stronger deindexing signal than 404. Google removes these faster.
503 Service Unavailable - Tells Google “come back later.” Safe for short maintenance windows. Extended 503 responses will eventually lead to deindexing.
Redirect chains - Each hop adds latency and can leak link equity. According to Screaming Frog analysis, redirect chains longer than three hops lose measurable ranking signals. Keep chains to one hop. Here’s something many SEO guides miss: a 200 response on a page with “Page Not Found” content (a soft 404) is actively harmful. Google’s crawler detects these and treats them as errors in Search Console, but unlike a proper 404, they waste crawl budget because Google keeps re-checking. Always return the correct status code. Don’t fake it with content.
Quick Reference: HTTP Status Codes Cheat Sheet
Keep this table handy. It covers the codes you’ll encounter in daily development.
| Code | Name | One-Line Summary |
|---|---|---|
| 200 | OK | Success. Here's your data. |
| 201 | Created | Resource created. Check the Location header. |
| 204 | No Content | Success. Nothing to return. |
| 301 | Moved Permanently | New URL. Update your bookmarks. |
| 302 | Found | Temporary redirect. Keep using this URL. |
| 304 | Not Modified | Use your cached copy. |
| 400 | Bad Request | Your request is malformed. |
| 401 | Unauthorized | Log in first. |
| 403 | Forbidden | You don't have permission. |
| 404 | Not Found | Nothing here. |
| 405 | Method Not Allowed | Wrong HTTP method for this endpoint. |
| 409 | Conflict | Conflicts with current state. |
| 422 | Unprocessable Content | Valid syntax, invalid data. |
| 429 | Too Many Requests | Slow down. |
| 500 | Internal Server Error | Something broke on the server. |
| 502 | Bad Gateway | Upstream server returned junk. |
| 503 | Service Unavailable | Server is temporarily down. |
| 504 | Gateway Timeout | Upstream server too slow. |
Frequently Asked Questions
What is the difference between 401 and 403?
A 401 means the client hasn’t authenticated. The server doesn’t know who they are, and the response includes a WWW-Authenticate header prompting login. A 403 means the server knows who the client is but refuses access. No amount of re-authenticating will help. According to RFC 9110 (IETF, 2022), the distinction is explicitly about whether authentication could make a difference.
Should I use 404 or 410 for deleted pages?
Use 410 when content is intentionally and permanently removed. Use 404 when a URL simply doesn’t exist. Google’s Search Central documentation confirms that 410 triggers faster deindexing. If you want a removed page out of search results quickly, 410 is the right choice.
What causes a 502 Bad Gateway error?
A 502 means a server acting as a reverse proxy or load balancer received an invalid response from the upstream server. The most common causes are a crashed application process, a failed SSL handshake between the proxy and upstream, or the upstream returning malformed HTTP. Check the upstream server’s health, not the proxy’s configuration.
When should I return 422 instead of 400?
Return 400 when the request itself is malformed, such as invalid JSON syntax, missing required headers, or unparseable query parameters. Return 422 when the request is syntactically correct but semantically invalid, meaning the data fails business rules like duplicate emails, invalid date ranges, or negative quantities. This distinction helps API consumers distinguish between “fix your request format” and “fix your data.”
How do redirect chains affect SEO?
Each redirect hop adds latency (typically 100-300ms per hop) and can reduce the link equity passed to the final URL. Screaming Frog data shows that chains beyond three hops lose measurable ranking signals. Google recommends keeping redirect chains as short as possible. Audit your redirects regularly and flatten chains to single hops.
test regex patterns for log parsing
Wrapping Up
HTTP status codes are a shared vocabulary between clients and servers. Using the wrong code isn’t just sloppy, it breaks caching, confuses search engines, misleads API consumers, and makes debugging harder. The right code in the right situation means fewer support tickets, better SEO, and APIs that other developers actually enjoy working with.
Use the HTTP Status Codes reference tool to quickly look up any code. And next time you’re tempted to return 200 with an error message in the body, reconsider.