#![warn(missing_docs)]
use std::fmt::Display;
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum StatusCode {
Ok,
Created,
Accepted,
NoContent,
PermanentRedirect,
Redirect,
BadRequest,
Unauthorized,
Forbidden,
NotFound,
MethodNotAllowed,
Conflict,
PayloadTooLarge,
TooManyRequests,
InternalServerError,
NotImplemented,
BadGateway,
ServiceUnavailable,
Custom(u16),
}
impl Display for StatusCode {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
let code = self.as_u16();
write!(
f,
"{} {}",
code,
match self {
StatusCode::Ok => "OK",
StatusCode::Created => "Created",
StatusCode::Accepted => "Accepted",
StatusCode::NoContent => "No Content",
StatusCode::Redirect => "Found",
StatusCode::PermanentRedirect => "Moved Permanently",
StatusCode::BadRequest => "Bad Request",
StatusCode::Unauthorized => "Unauthorized",
StatusCode::Forbidden => "Forbidden",
StatusCode::NotFound => "Not Found",
StatusCode::MethodNotAllowed => "Method Not Allowed",
StatusCode::Conflict => "Conflict",
StatusCode::PayloadTooLarge => "Payload Too Large",
StatusCode::TooManyRequests => "Too Many Requests",
StatusCode::InternalServerError => "Internal Server Error",
StatusCode::NotImplemented => "Not Implemented",
StatusCode::BadGateway => "Bad Gateway",
StatusCode::ServiceUnavailable => "Service Unavailable",
StatusCode::Custom(_code) => "Custom",
}
)
}
}
impl StatusCode {
pub fn as_u16(&self) -> u16 {
match self {
StatusCode::Ok => 200,
StatusCode::Created => 201,
StatusCode::Accepted => 202,
StatusCode::NoContent => 204,
StatusCode::Redirect => 302,
StatusCode::PermanentRedirect => 301,
StatusCode::BadRequest => 400,
StatusCode::Unauthorized => 401,
StatusCode::Forbidden => 403,
StatusCode::NotFound => 404,
StatusCode::MethodNotAllowed => 405,
StatusCode::Conflict => 409,
StatusCode::PayloadTooLarge => 413,
StatusCode::TooManyRequests => 429,
StatusCode::InternalServerError => 500,
StatusCode::NotImplemented => 501,
StatusCode::BadGateway => 502,
StatusCode::ServiceUnavailable => 503,
StatusCode::Custom(code) => *code,
}
}
pub fn from_u16(code: u16) -> StatusCode {
match code {
200 => StatusCode::Ok,
201 => StatusCode::Created,
202 => StatusCode::Accepted,
204 => StatusCode::NoContent,
302 => StatusCode::Redirect,
301 => StatusCode::PermanentRedirect,
400 => StatusCode::BadRequest,
401 => StatusCode::Unauthorized,
403 => StatusCode::Forbidden,
404 => StatusCode::NotFound,
405 => StatusCode::MethodNotAllowed,
409 => StatusCode::Conflict,
413 => StatusCode::PayloadTooLarge,
429 => StatusCode::TooManyRequests,
500 => StatusCode::InternalServerError,
501 => StatusCode::NotImplemented,
502 => StatusCode::BadGateway,
503 => StatusCode::ServiceUnavailable,
other => StatusCode::Custom(other),
}
}
pub fn is_success(&self) -> bool {
matches!(self.as_u16(), 200..=299)
}
pub fn is_redirection(&self) -> bool {
matches!(self.as_u16(), 300..=399)
}
pub fn is_client_error(&self) -> bool {
matches!(self.as_u16(), 400..=499)
}
pub fn is_server_error(&self) -> bool {
matches!(self.as_u16(), 500..=599)
}
pub fn is_informational(&self) -> bool {
matches!(self.as_u16(), 100..=199)
}
pub fn canonical_reason(&self) -> &'static str {
match self {
StatusCode::Ok => "OK",
StatusCode::Created => "Created",
StatusCode::Accepted => "Accepted",
StatusCode::NoContent => "No Content",
StatusCode::Redirect => "Found",
StatusCode::PermanentRedirect => "Moved Permanently",
StatusCode::BadRequest => "Bad Request",
StatusCode::Unauthorized => "Unauthorized",
StatusCode::Forbidden => "Forbidden",
StatusCode::NotFound => "Not Found",
StatusCode::MethodNotAllowed => "Method Not Allowed",
StatusCode::Conflict => "Conflict",
StatusCode::PayloadTooLarge => "Payload Too Large",
StatusCode::TooManyRequests => "Too Many Requests",
StatusCode::InternalServerError => "Internal Server Error",
StatusCode::NotImplemented => "Not Implemented",
StatusCode::BadGateway => "Bad Gateway",
StatusCode::ServiceUnavailable => "Service Unavailable",
StatusCode::Custom(_) => "Custom",
}
}
}