use candid::{define_function, CandidType, Deserialize};
use ic_http_certification::{HeaderField, HttpRequest, HttpResponse, StatusCode};
use serde_bytes::ByteBuf;
pub type Args = HttpRequest<'static>;
pub type Response = HttpStreamingResponse;
#[derive(CandidType, Deserialize, Clone, Debug, PartialEq, Eq)]
pub struct StreamingCallbackToken {
pub path: String,
pub index: u64,
pub content_type: String,
pub total_length: u64,
}
define_function!(pub CallbackFunc : (StreamingCallbackToken) -> (StreamingCallbackHttpResponse) query);
#[derive(CandidType, Deserialize, Clone, Debug)]
pub enum StreamingStrategy {
Callback {
callback: CallbackFunc,
token: StreamingCallbackToken,
},
}
#[derive(CandidType, Deserialize, Clone, Debug)]
pub struct StreamingCallbackHttpResponse {
pub body: ByteBuf,
pub token: Option<StreamingCallbackToken>,
}
#[derive(CandidType, Deserialize, Clone, Debug)]
pub struct HttpStreamingResponse {
pub status_code: u16,
pub headers: Vec<HeaderField>,
pub body: ByteBuf,
pub upgrade: Option<bool>,
pub streaming_strategy: Option<StreamingStrategy>,
}
impl HttpStreamingResponse {
pub fn status_code(&self) -> StatusCode {
StatusCode::from_u16(self.status_code).unwrap_or(StatusCode::INTERNAL_SERVER_ERROR)
}
pub fn body(&self) -> &[u8] {
&self.body
}
pub fn headers(&self) -> &[HeaderField] {
&self.headers
}
}
impl From<HttpResponse<'_>> for HttpStreamingResponse {
fn from(response: HttpResponse<'_>) -> Self {
Self {
status_code: response.status_code().as_u16(),
headers: response.headers().to_vec(),
body: ByteBuf::from(response.body().to_vec()),
upgrade: response.upgrade(),
streaming_strategy: None,
}
}
}