simple_request/
request.rs1use hyper::body::Bytes;
2#[cfg(feature = "basic-auth")]
3use hyper::header::HeaderValue;
4pub use http_body_util::Full;
5
6#[cfg(feature = "basic-auth")]
7use crate::Error;
8
9#[derive(Debug)]
10pub struct Request {
11 pub(crate) request: hyper::Request<Full<Bytes>>,
12 pub(crate) response_size_limit: Option<usize>,
13}
14
15impl Request {
16 #[cfg(feature = "basic-auth")]
17 fn username_password_from_uri(&self) -> Result<(String, String), Error> {
18 if let Some(authority) = self.request.uri().authority() {
19 let authority = authority.as_str();
20 if authority.contains('@') {
21 let mut userpass = authority.split('@').next().unwrap().to_string();
23
24 let mut userpass_iter = userpass.split(':');
25 let username = userpass_iter.next().unwrap().to_string();
26 let password = userpass_iter.next().map_or_else(String::new, str::to_string);
27 zeroize::Zeroize::zeroize(&mut userpass);
28
29 return Ok((username, password));
30 }
31 }
32 Err(Error::InvalidUri)
33 }
34
35 #[cfg(feature = "basic-auth")]
36 pub fn basic_auth(&mut self, username: &str, password: &str) {
37 use zeroize::Zeroize;
38 use base64ct::{Encoding, Base64};
39
40 let mut formatted = format!("{username}:{password}");
41 let mut encoded = Base64::encode_string(formatted.as_bytes());
42 formatted.zeroize();
43 self.request.headers_mut().insert(
44 hyper::header::AUTHORIZATION,
45 HeaderValue::from_str(&format!("Basic {encoded}")).unwrap(),
46 );
47 encoded.zeroize();
48 }
49
50 #[cfg(feature = "basic-auth")]
51 pub fn basic_auth_from_uri(&mut self) -> Result<(), Error> {
52 let (mut username, mut password) = self.username_password_from_uri()?;
53 self.basic_auth(&username, &password);
54
55 use zeroize::Zeroize;
56 username.zeroize();
57 password.zeroize();
58
59 Ok(())
60 }
61
62 #[cfg(feature = "basic-auth")]
63 pub fn with_basic_auth(&mut self) {
64 let _ = self.basic_auth_from_uri();
65 }
66
67 pub fn set_response_size_limit(&mut self, response_size_limit: Option<usize>) {
71 self.response_size_limit = response_size_limit;
72 }
73}
74
75impl From<hyper::Request<Full<Bytes>>> for Request {
76 fn from(request: hyper::Request<Full<Bytes>>) -> Request {
77 Request { request, response_size_limit: None }
78 }
79}