1use async_trait::async_trait;
2use hyper::client::HttpConnector;
3use hyper::Client;
4use hyper_tls::HttpsConnector;
5
6mod error;
7pub use error::Error;
8pub use http;
9
10pub mod content;
11pub use content::{RequestContent, ResponseContent};
12
13#[cfg(feature = "sse")]
14pub mod sse;
15
16#[cfg(feature = "sse")]
17pub use sse::Sse;
18
19#[async_trait]
20pub trait HttpClient
21where
22 Self: Send + Sync + Sized,
23{
24 async fn perform(
25 &self,
26 r: hyper::Request<hyper::Body>,
27 ) -> Result<hyper::Response<hyper::Body>, hyper::Error>;
28
29 async fn send<Req, Res>(
30 &self,
31 r: http::Request<Req>,
32 ) -> Result<http::Response<Res::Data>, Error>
33 where
34 Req: RequestContent + Send,
35 Res: ResponseContent,
36 {
37 let (mut parts, body) = r.into_parts();
38
39 body.apply_headers(&mut parts.headers);
40
41 let hyper_body: hyper::Body = body.into_body()?;
42 let request = hyper::Request::from_parts(parts, hyper_body);
43
44 let res = self.perform(request).await?;
45
46 Res::convert_response(res).await
47 }
48
49 fn https() -> HttpsClient {
50 HttpsClient::default()
51 }
52}
53
54pub struct HttpsClient {
55 http_client: Client<HttpsConnector<HttpConnector>>,
56}
57
58impl Default for HttpsClient {
59 fn default() -> Self {
60 let http_client = Client::builder().build::<_, hyper::Body>(HttpsConnector::new());
61 Self { http_client }
62 }
63}
64
65#[async_trait]
66impl HttpClient for HttpsClient {
67 async fn perform(
68 &self,
69 r: hyper::Request<hyper::Body>,
70 ) -> Result<hyper::Response<hyper::Body>, hyper::Error> {
71 self.http_client.request(r).await
72 }
73}