fire_http/util/
header.rs

1use crate::header::{HeaderValues, RequestHeader, Uri, HOST};
2
3use std::net::SocketAddr;
4
5use hyper::http::uri::{Authority, Scheme};
6
7#[derive(Debug, Clone, PartialEq, Eq, thiserror::Error)]
8pub enum HeaderError {
9	#[error("No host header found")]
10	NoHost,
11
12	#[error("Host header is invalid")]
13	HostInvalid,
14
15	#[error("Invalid uri")]
16	Uri,
17}
18
19type Result<T> = std::result::Result<T, HeaderError>;
20
21pub fn convert_hyper_parts_to_fire_header(
22	parts: hyper::http::request::Parts,
23	address: SocketAddr,
24) -> Result<RequestHeader> {
25	let values = HeaderValues::from_inner(parts.headers);
26	let uri = fill_uri(parts.uri, &values)?;
27
28	Ok(RequestHeader {
29		address,
30		method: parts.method,
31		uri,
32		values,
33	})
34}
35
36pub fn convert_hyper_req_to_fire_header<B>(
37	req: &hyper::Request<B>,
38	address: SocketAddr,
39) -> Result<RequestHeader> {
40	let values = HeaderValues::from_inner(req.headers().clone());
41	let uri = fill_uri(req.uri().clone(), &values)?;
42
43	Ok(RequestHeader {
44		address,
45		method: req.method().clone(),
46		uri,
47		values,
48	})
49}
50
51fn fill_uri(uri: Uri, headers: &HeaderValues) -> Result<Uri> {
52	let mut parts = uri.into_parts();
53	// Try to detect it
54	// todo how would it be possible to detect http or https
55	parts.scheme = Some(Scheme::HTTP);
56
57	// get host infos
58	let host = headers.get(HOST).ok_or(HeaderError::NoHost)?;
59
60	parts.authority = Some(
61		Authority::try_from(host.as_bytes())
62			.map_err(|_| HeaderError::HostInvalid)?,
63	);
64
65	Uri::from_parts(parts).map_err(|_| HeaderError::Uri)
66}