use core::pin::Pin;
use std::error::Error as StdError;
use std::fmt;
use std::time::Duration;
use futures_io::AsyncRead;
const OEM_PREFIX: &str = "Oem";
pub trait UploadReader: AsyncRead + Send + 'static {}
impl<T> UploadReader for T where T: AsyncRead + Send + 'static {}
pub struct DataStream<R> {
pub name: String,
pub reader: R,
pub content_length: Option<u64>,
}
impl<R> DataStream<R> {
#[must_use]
pub fn new(name: impl Into<String>, reader: R) -> Self {
Self {
name: name.into(),
reader,
content_length: None,
}
}
#[must_use]
pub const fn with_content_length(mut self, content_length: u64) -> Self {
self.content_length = Some(content_length);
self
}
}
#[derive(Debug, Clone, PartialEq, Eq)]
pub struct OemMultipartPartNameError {
pub name: String,
}
impl fmt::Display for OemMultipartPartNameError {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(
f,
"OEM multipart part name must start with Oem: {}",
self.name
)
}
}
impl StdError for OemMultipartPartNameError {}
pub type OemMultipartPartReader = Pin<Box<dyn AsyncRead + Send + 'static>>;
pub struct OemMultipartPart {
pub name: String,
pub reader: OemMultipartPartReader,
pub content_type: Option<String>,
pub content_length: Option<u64>,
}
impl OemMultipartPart {
#[must_use]
pub fn is_name_valid(&self) -> bool {
self.name.starts_with(OEM_PREFIX)
}
}
impl OemMultipartPart {
pub fn new(
name: impl Into<String>,
reader: impl UploadReader,
) -> Result<Self, OemMultipartPartNameError> {
let name = name.into();
if !name.starts_with(OEM_PREFIX) {
return Err(OemMultipartPartNameError { name });
}
Ok(Self {
name,
reader: Box::pin(reader),
content_type: None,
content_length: None,
})
}
#[must_use]
pub fn with_content_type(mut self, content_type: impl Into<String>) -> Self {
self.content_type = Some(content_type.into());
self
}
#[must_use]
pub const fn with_content_length(mut self, content_length: u64) -> Self {
self.content_length = Some(content_length);
self
}
}
pub struct MultipartUpdateRequest<'a, U, V> {
pub update_parameters: &'a V,
pub update_stream: DataStream<U>,
pub oem_parts: Vec<OemMultipartPart>,
pub upload_timeout: Duration,
}