HTTP Status Codes — Rust source
Searchable reference of all HTTP status codes with meaning, category, and usage notes.
This is the Rust implementation — the same logic the interactive tool runs, in a shareable, citable form.
//! HTTP Status Codes reference — pure, deterministic data + filter.
//!
//! Language: Rust
//! CosmoDev polyglot showcase port of `http-status-codes`,
//! ported from src/lib/httpStatus.ts.
//! Display source — part of CosmoDev's polyglot tool pages.
//!
//! Pure logic — no I/O, no external crates (std only). Behavior matches the
//! TypeScript lib: same inputs produce identical outputs.
use std::str::FromStr;
/// The five broad families an HTTP status code can belong to.
///
/// Modeled as a fieldless enum rather than a string so the compiler can prove
/// every `StatusCode` carries a valid family. It is `Copy` (no heap) and
/// cheap to compare.
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum StatusCategory {
Informational,
Success,
Redirection,
ClientError,
ServerError,
}
impl StatusCategory {
/// Stable display name, matching the TypeScript union's string values
/// (e.g. `ClientError -> "Client Error"`).
pub fn as_str(&self) -> &'static str {
match self {
Self::Informational => "Informational",
Self::Success => "Success",
Self::Redirection => "Redirection",
Self::ClientError => "Client Error",
Self::ServerError => "Server Error",
}
}
}
/// Parse a category from its display name.
///
/// `FromStr` is the idiomatic Rust bridge from text to a typed value. The
/// filter relies on the `Err` branch to turn an unknown category name into an
/// empty result, exactly as the TypeScript version does.
impl FromStr for StatusCategory {
type Err = ();
fn from_str(s: &str) -> Result<Self, Self::Err> {
match s {
"Informational" => Ok(Self::Informational),
"Success" => Ok(Self::Success),
"Redirection" => Ok(Self::Redirection),
"Client Error" => Ok(Self::ClientError),
"Server Error" => Ok(Self::ServerError),
_ => Err(()),
}
}
}
/// A single HTTP status code entry.
///
/// All fields are `'static` so the whole table can live in read-only memory
/// and entries can be referenced by shared pointer without copying.
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub struct StatusCode {
pub code: u16,
pub reason: &'static str,
pub category: StatusCategory,
pub description: &'static str,
}
/// Standard + widely-implemented HTTP status codes across 1xx–5xx.
///
/// A `static` slice — the table is built once at compile time and never
/// mutated. Order is grouped by category, ascending within each group.
pub static STATUS_CODES: &[StatusCode] = &[
// --- 1xx Informational ---
StatusCode { code: 100, reason: "Continue", category: StatusCategory::Informational, description: "The server has received the request headers and the client should proceed to send the request body." },
StatusCode { code: 101, reason: "Switching Protocols", category: StatusCategory::Informational, description: "The requester has asked the server to switch protocols and the server has agreed to do so." },
StatusCode { code: 103, reason: "Early Hints", category: StatusCategory::Informational, description: "Used to return some response headers before the final HTTP message so the browser can start preloading resources." },
// --- 2xx Success ---
StatusCode { code: 200, reason: "OK", category: StatusCategory::Success, description: "Standard response for a successful HTTP request." },
StatusCode { code: 201, reason: "Created", category: StatusCategory::Success, description: "The request succeeded and a new resource was created." },
StatusCode { code: 202, reason: "Accepted", category: StatusCategory::Success, description: "The request has been accepted for processing but is not yet complete." },
StatusCode { code: 203, reason: "Non-Authoritative Information", category: StatusCategory::Success, description: "The returned metadata originated from a local or third-party copy rather than the origin server." },
StatusCode { code: 204, reason: "No Content", category: StatusCategory::Success, description: "The server processed the request successfully but is not returning any content." },
StatusCode { code: 205, reason: "Reset Content", category: StatusCategory::Success, description: "The server asks the client to reset the document view that sent the request." },
StatusCode { code: 206, reason: "Partial Content", category: StatusCategory::Success, description: "The server is delivering only part of the resource because the client requested a byte range." },
StatusCode { code: 207, reason: "Multi-Status", category: StatusCategory::Success, description: "WebDAV: conveys information about multiple resources in a single XML response." },
StatusCode { code: 208, reason: "Already Reported", category: StatusCategory::Success, description: "WebDAV: the members of a DAV binding have already been enumerated in a previous reply." },
StatusCode { code: 226, reason: "IM Used", category: StatusCategory::Success, description: "The server fulfilled a GET request using an instance-manipulation applied to the current instance." },
// --- 3xx Redirection ---
StatusCode { code: 300, reason: "Multiple Choices", category: StatusCategory::Redirection, description: "The request has more than one possible response; the user agent can choose among them." },
StatusCode { code: 301, reason: "Moved Permanently", category: StatusCategory::Redirection, description: "This and all future requests should be directed to the given URL." },
StatusCode { code: 302, reason: "Found", category: StatusCategory::Redirection, description: "The resource resides temporarily under a different URL; the method may be changed to GET." },
StatusCode { code: 303, reason: "See Other", category: StatusCategory::Redirection, description: "The response to the request can be found under another URI using a GET request." },
StatusCode { code: 304, reason: "Not Modified", category: StatusCategory::Redirection, description: "The resource has not been modified since the version specified by the request headers." },
StatusCode { code: 305, reason: "Use Proxy", category: StatusCategory::Redirection, description: "The requested resource is available only through a proxy (deprecated)." },
StatusCode { code: 306, reason: "Switch Proxy", category: StatusCategory::Redirection, description: "No longer used; originally meant subsequent requests should use a specified proxy." },
StatusCode { code: 307, reason: "Temporary Redirect", category: StatusCategory::Redirection, description: "The request should be repeated with another URL; the request method must not change." },
StatusCode { code: 308, reason: "Permanent Redirect", category: StatusCategory::Redirection, description: "This and all future requests should use another URL; the request method must not change." },
// --- 4xx Client Error ---
StatusCode { code: 400, reason: "Bad Request", category: StatusCategory::ClientError, description: "The server cannot process the request due to a client error such as malformed syntax." },
StatusCode { code: 401, reason: "Unauthorized", category: StatusCategory::ClientError, description: "Authentication is required and has either failed or not been provided." },
StatusCode { code: 402, reason: "Payment Required", category: StatusCategory::ClientError, description: "Reserved for future use; sometimes used for paywalled resources." },
StatusCode { code: 403, reason: "Forbidden", category: StatusCategory::ClientError, description: "The server understood the request but refuses to authorize it." },
StatusCode { code: 404, reason: "Not Found", category: StatusCategory::ClientError, description: "The requested resource could not be found on the server." },
StatusCode { code: 405, reason: "Method Not Allowed", category: StatusCategory::ClientError, description: "The request method is not supported for the requested resource." },
StatusCode { code: 406, reason: "Not Acceptable", category: StatusCategory::ClientError, description: "The requested resource can only generate content not acceptable per the Accept headers." },
StatusCode { code: 407, reason: "Proxy Authentication Required", category: StatusCategory::ClientError, description: "The client must first authenticate itself with the proxy." },
StatusCode { code: 408, reason: "Request Timeout", category: StatusCategory::ClientError, description: "The server timed out waiting for the client to send the request." },
StatusCode { code: 409, reason: "Conflict", category: StatusCategory::ClientError, description: "The request could not be processed because of a conflict with the current state of the resource." },
StatusCode { code: 410, reason: "Gone", category: StatusCategory::ClientError, description: "The resource is no longer available and will not be available again." },
StatusCode { code: 411, reason: "Length Required", category: StatusCategory::ClientError, description: "The request did not specify the length of its content, which is required by the resource." },
StatusCode { code: 412, reason: "Precondition Failed", category: StatusCategory::ClientError, description: "The server does not meet one of the preconditions given in the request headers." },
StatusCode { code: 413, reason: "Content Too Large", category: StatusCategory::ClientError, description: "The request payload is larger than the server is willing or able to process." },
StatusCode { code: 414, reason: "URI Too Long", category: StatusCategory::ClientError, description: "The URI provided was too long for the server to process." },
StatusCode { code: 415, reason: "Unsupported Media Type", category: StatusCategory::ClientError, description: "The request uses a media type the server does not support for the resource." },
StatusCode { code: 416, reason: "Range Not Satisfiable", category: StatusCategory::ClientError, description: "The portion of the resource requested in the Range header cannot be supplied by the server." },
StatusCode { code: 417, reason: "Expectation Failed", category: StatusCategory::ClientError, description: "The server cannot meet the requirements of the Expect request header field." },
StatusCode { code: 418, reason: "I'm a Teapot", category: StatusCategory::ClientError, description: "RFC 2324 joke status: the server refuses to brew coffee because it is, permanently, a teapot." },
StatusCode { code: 421, reason: "Misdirected Request", category: StatusCategory::ClientError, description: "The request was directed at a server that is not able to produce a response." },
StatusCode { code: 422, reason: "Unprocessable Content", category: StatusCategory::ClientError, description: "The server understands the content type and syntax but cannot process the contained instructions (WebDAV)." },
StatusCode { code: 423, reason: "Locked", category: StatusCategory::ClientError, description: "WebDAV: the source or destination resource of the method is locked." },
StatusCode { code: 424, reason: "Failed Dependency", category: StatusCategory::ClientError, description: "WebDAV: the method could not be performed because the requested action depended on another action that failed." },
StatusCode { code: 425, reason: "Too Early", category: StatusCategory::ClientError, description: "The server is unwilling to risk processing a request that might be a replay." },
StatusCode { code: 428, reason: "Precondition Required", category: StatusCategory::ClientError, description: "The origin server requires the request to be conditional." },
StatusCode { code: 429, reason: "Too Many Requests", category: StatusCategory::ClientError, description: "The user has sent too many requests in a given time (rate limiting)." },
StatusCode { code: 431, reason: "Request Header Fields Too Large", category: StatusCategory::ClientError, description: "The server is unwilling to process the request because its header fields are too large." },
StatusCode { code: 451, reason: "Unavailable For Legal Reasons", category: StatusCategory::ClientError, description: "The resource is unavailable due to legal demands such as government censorship or a takedown." },
// --- 5xx Server Error ---
StatusCode { code: 500, reason: "Internal Server Error", category: StatusCategory::ServerError, description: "A generic error message: the server encountered an unexpected condition." },
StatusCode { code: 501, reason: "Not Implemented", category: StatusCategory::ServerError, description: "The server does not support the functionality required to fulfill the request." },
StatusCode { code: 502, reason: "Bad Gateway", category: StatusCategory::ServerError, description: "The server, acting as a gateway, received an invalid response from an upstream server." },
StatusCode { code: 503, reason: "Service Unavailable", category: StatusCategory::ServerError, description: "The server is currently unavailable, typically because it is overloaded or down for maintenance." },
StatusCode { code: 504, reason: "Gateway Timeout", category: StatusCategory::ServerError, description: "The server, acting as a gateway, timed out waiting for an upstream response." },
StatusCode { code: 505, reason: "HTTP Version Not Supported", category: StatusCategory::ServerError, description: "The server does not support the HTTP protocol version used in the request." },
StatusCode { code: 506, reason: "Variant Also Negotiates", category: StatusCategory::ServerError, description: "Transparent content negotiation for the request resulted in a circular reference." },
StatusCode { code: 507, reason: "Insufficient Storage", category: StatusCategory::ServerError, description: "WebDAV: the server is unable to store the representation needed to complete the request." },
StatusCode { code: 508, reason: "Loop Detected", category: StatusCategory::ServerError, description: "WebDAV: the server detected an infinite loop while processing the request." },
StatusCode { code: 510, reason: "Not Extended", category: StatusCategory::ServerError, description: "Further extensions to the request are required for the server to fulfill it." },
StatusCode { code: 511, reason: "Network Authentication Required", category: StatusCategory::ServerError, description: "The client must authenticate to gain network access, as with a captive portal." },
];
/// Filter status codes by a free-text query and an optional category.
///
/// `query` is matched case-insensitively against the numeric code (as a decimal
/// string), the reason phrase, and the description. An empty/whitespace query
/// returns every code in the pool. `category` restricts the pool first:
/// `None` means "no restriction"; `Some("")` is treated as `None`; an unknown
/// name yields an empty result — matching the TypeScript semantics.
///
/// Returns borrowed references into `codes` rather than owned copies, since the
/// data is read-only and copying would be wasted work.
pub fn filter_codes<'a>(
query: &str,
codes: &'a [StatusCode],
category: Option<&str>,
) -> Vec<&'a StatusCode> {
// Resolve the category: None / blank -> no filter; a name that does not
// parse as a known family -> nothing can match, so short-circuit to empty.
let category = match category.map(str::trim).filter(|c| !c.is_empty()) {
None => None,
Some(name) => match StatusCategory::from_str(name) {
Ok(parsed) => Some(parsed),
Err(()) => return Vec::new(),
},
};
// First pass: narrow to the requested family (or keep everything).
let pool: Vec<&StatusCode> = codes
.iter()
.filter(|c| category.map_or(true, |cat| c.category == cat))
.collect();
// Second pass: case-insensitive substring match on code/reason/description.
let needle = query.trim().to_lowercase();
if needle.is_empty() {
return pool;
}
pool.into_iter()
.filter(|c| {
// The code is matched against its decimal form, so "40" hits 404, 405, ...
c.code.to_string().contains(&needle)
|| c.reason.to_lowercase().contains(&needle)
|| c.description.to_lowercase().contains(&needle)
})
.collect()
}
Also available in 13 other languages
Every CosmoDev tool ships its pure logic in TypeScript (web) and Go (CLI), with authored implementations in a dozen-plus languages — the same contract, ported. Compare all languages side by side →