canic_core/api/ic/
http.rs1use crate::{PublicError, dto::http as http_dto, ops::ic::http as http_ops};
2use candid::{CandidType, Nat};
3use serde::{Deserialize, Serialize, de::DeserializeOwned};
4
5#[derive(CandidType, Clone, Debug, Deserialize, Serialize)]
17pub struct ApiHttpRequest {
18 pub url: String,
19 pub max_response_bytes: Option<u64>,
20 pub method: ApiHttpMethod,
21 pub headers: Vec<ApiHttpHeader>,
22 pub body: Option<Vec<u8>>,
23 pub is_replicated: Option<bool>,
24}
25
26#[derive(CandidType, Clone, Debug, Deserialize, Serialize)]
31pub struct ApiHttpResponse {
32 pub status: Nat,
33 pub headers: Vec<ApiHttpHeader>,
34 #[serde(with = "serde_bytes")]
35 pub body: Vec<u8>,
36}
37
38#[derive(CandidType, Clone, Copy, Debug, Deserialize, Serialize)]
43pub enum ApiHttpMethod {
44 #[serde(rename = "get")]
45 GET,
46 #[serde(rename = "post")]
47 POST,
48 #[serde(rename = "head")]
49 HEAD,
50}
51
52#[derive(CandidType, Clone, Debug, Deserialize, Serialize)]
57pub struct ApiHttpHeader {
58 pub name: String,
59 pub value: String,
60}
61
62pub async fn get<T: DeserializeOwned>(
65 url: &str,
66 headers: &[(&str, &str)],
67) -> Result<T, PublicError> {
68 http_ops::get(url, headers).await.map_err(PublicError::from)
69}
70
71pub async fn get_with_label<T: DeserializeOwned>(
74 url: &str,
75 headers: &[(&str, &str)],
76 label: &str,
77) -> Result<T, PublicError> {
78 http_ops::get_with_label(url, headers, Some(label))
79 .await
80 .map_err(PublicError::from)
81}
82
83pub async fn get_raw(args: ApiHttpRequest) -> Result<ApiHttpResponse, PublicError> {
85 http_ops::get_raw(args.into())
86 .await
87 .map(ApiHttpResponse::from)
88 .map_err(PublicError::from)
89}
90
91impl From<ApiHttpRequest> for http_dto::HttpRequestArgs {
92 fn from(req: ApiHttpRequest) -> Self {
93 Self {
94 url: req.url,
95 max_response_bytes: req.max_response_bytes,
96 method: req.method.into(),
97 headers: req.headers.into_iter().map(Into::into).collect(),
98 body: req.body,
99 is_replicated: req.is_replicated,
100 }
101 }
102}
103
104impl From<http_dto::HttpRequestResult> for ApiHttpResponse {
105 fn from(res: http_dto::HttpRequestResult) -> Self {
106 Self {
107 status: res.status,
108 headers: res.headers.into_iter().map(Into::into).collect(),
109 body: res.body,
110 }
111 }
112}
113
114impl From<ApiHttpMethod> for http_dto::HttpMethod {
115 fn from(method: ApiHttpMethod) -> Self {
116 match method {
117 ApiHttpMethod::GET => Self::GET,
118 ApiHttpMethod::POST => Self::POST,
119 ApiHttpMethod::HEAD => Self::HEAD,
120 }
121 }
122}
123
124impl From<ApiHttpHeader> for http_dto::HttpHeader {
125 fn from(header: ApiHttpHeader) -> Self {
126 Self {
127 name: header.name,
128 value: header.value,
129 }
130 }
131}
132
133impl From<http_dto::HttpHeader> for ApiHttpHeader {
134 fn from(header: http_dto::HttpHeader) -> Self {
135 Self {
136 name: header.name,
137 value: header.value,
138 }
139 }
140}