use std::{fmt::Display, net::SocketAddr};
#[cfg_attr(feature = "json", derive(serde::Serialize))]
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
pub enum Method {
GET,
POST,
PUT,
DELETE,
HEAD,
OPTIONS,
CONNECT,
PATCH,
TRACE,
Other,
}
impl Display for Method {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f, "{:?}", self)
}
}
impl From<&[u8]> for Method {
fn from(method: &[u8]) -> Self {
match method {
b"GET" => Method::GET,
b"POST" => Method::POST,
b"PUT" => Method::PUT,
b"DELETE" => Method::DELETE,
b"HEAD" => Method::HEAD,
b"OPTIONS" => Method::OPTIONS,
b"CONNECT" => Method::CONNECT,
b"PATCH" => Method::PATCH,
b"TRACE" => Method::TRACE,
_ => Method::Other,
}
}
}
#[cfg_attr(feature = "json", derive(serde::Serialize))]
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
pub enum HttpVersion {
V1_0,
V1_1,
V2_0,
V3_0,
Other,
}
impl Display for HttpVersion {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(
f,
"HTTP/{}",
match self {
HttpVersion::V1_0 => "1.0",
HttpVersion::V1_1 => "1.1",
HttpVersion::V2_0 => "2.0",
HttpVersion::V3_0 => "3.0",
HttpVersion::Other => "1.1",
}
)
}
}
impl From<&str> for HttpVersion {
fn from(version: &str) -> Self {
match version {
"HTTP/1.0" => HttpVersion::V1_0,
"HTTP/1.1" => HttpVersion::V1_1,
"HTTP/2.0" => HttpVersion::V2_0,
"HTTP/3.0" => HttpVersion::V3_0,
_ => HttpVersion::Other,
}
}
}
pub fn format_addr(addr: SocketAddr) -> String {
match addr {
SocketAddr::V4(v4) => {
if v4.ip().is_loopback() {
format!("localhost:{}", v4.port())
} else {
v4.to_string()
}
}
SocketAddr::V6(v6) => {
if v6.ip().is_loopback() {
format!("localhost:{}", v6.port())
} else {
format!("{}:{}", v6.ip(), v6.port())
}
}
}
}