cratefield_runtime_native/ports/
http.rs1use async_trait::async_trait;
7use bytes::Bytes;
8use cratefield_core::{HttpClient, HttpError};
9
10pub struct ReqwestClient(reqwest::Client);
18
19impl Default for ReqwestClient {
20 fn default() -> Self {
21 Self::new()
22 }
23}
24
25impl ReqwestClient {
26 pub fn new() -> Self {
32 Self(
33 reqwest::Client::builder()
34 .build()
35 .expect("reqwest initializes: rustls with webpki roots is static"),
36 )
37 }
38}
39
40#[async_trait]
41impl HttpClient for ReqwestClient {
42 async fn send(
43 &self,
44 request: http::Request<Bytes>,
45 ) -> Result<http::Response<Bytes>, HttpError> {
46 let (parts, body) = request.into_parts();
49 let url = parts
50 .uri
51 .to_string()
52 .parse::<reqwest::Url>()
53 .map_err(|err| HttpError::Transport(format!("invalid request uri: {err}")))?;
54 let mut builder = self.0.request(parts.method, url);
55 for (name, value) in &parts.headers {
56 builder = builder.header(name, value);
57 }
58 let response = builder
59 .body(body)
60 .send()
61 .await
62 .map_err(|err| HttpError::Transport(err.to_string()))?;
63
64 let status = response.status();
65 let headers = response.headers().clone();
66 let bytes = response
67 .bytes()
68 .await
69 .map_err(|err| HttpError::Transport(err.to_string()))?;
70 let mut rebuilt = http::Response::builder().status(status);
71 if let Some(target) = rebuilt.headers_mut() {
72 *target = headers;
73 }
74 rebuilt
75 .body(bytes)
76 .map_err(|err| HttpError::Transport(err.to_string()))
77 }
78}