use {
crate::{default, generic::never, ToPng, Zip},
std::{cmp::Ordering, fmt::Debug},
};
#[non_exhaustive]
pub struct ZipEntry<'name, 'body> {
pub name: &'name [u8],
pub body: &'body [u8],
}
pub type ZipEntryPredicate = fn(&ZipEntry) -> bool;
pub type ZipEntryComparison = fn(&ZipEntry, &ZipEntry) -> Ordering;
pub static SORT_BY_NAME: ZipEntryComparison = |a, b| {
(
a.name.iter().filter(|&&c| c == b'/').collect::<Vec<_>>(),
a.name,
)
.cmp(&(
b.name.iter().filter(|&&c| c == b'/').collect::<Vec<_>>(),
b.name,
))
};
pub static SORT_BY_BODY: ZipEntryComparison = |a, b| {
(a.body, a.name)
.cmp(&(b.body, b.name))
.then_with(|| SORT_BY_NAME(a, b))
};
pub static PIN_MIMETYPE: ZipEntryPredicate =
|file| file.name == b"mimetype" && file.body.is_ascii() && file.body.len() <= 0xFF;
#[derive(Clone)]
#[non_exhaustive]
pub struct ZipConfiguration {
pub body_contiguous: bool,
pub body_alignment: usize,
pub sort_body_by: Option<ZipEntryComparison>,
pub sort_meta_by: Option<ZipEntryComparison>,
pub pin_header_with: Option<ZipEntryPredicate>,
}
impl ZipConfiguration {
pub fn new(f: fn(&mut Self)) -> Self {
let mut zip_configuration = default();
f(&mut zip_configuration);
zip_configuration
}
}
impl Debug for ZipConfiguration {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
f.debug_struct("ZipConfiguration")
.field("body_contiguous", &self.body_contiguous)
.field("body_alignment", &self.body_alignment)
.field(
"sort_body_by",
self.sort_body_by.map(|_| &Some(())).unwrap_or(&None),
)
.field(
"sort_meta_by",
self.sort_meta_by.map(|_| &Some(())).unwrap_or(&None),
)
.finish()
}
}
impl Default for ZipConfiguration {
fn default() -> Self {
Self {
body_contiguous: true,
body_alignment: 1024,
sort_body_by: SORT_BY_BODY.into(),
sort_meta_by: SORT_BY_NAME.into(),
pin_header_with: PIN_MIMETYPE.into(),
}
}
}
impl Zip {
pub fn minimal(&mut self) {
todo!()
}
pub fn blocks(&mut self) {
todo!()
}
pub fn covered(&mut self) {
todo!()
}
pub fn uncovered(&mut self) {
todo!()
}
}