Enforce format on new details

This commit is contained in:
asonix 2023-08-16 12:36:18 -05:00
parent f3c6239979
commit 521cdd5b9d
6 changed files with 67 additions and 59 deletions

View file

@ -22,8 +22,7 @@ pub(crate) struct Details {
frames: Option<u32>,
content_type: Serde<mime::Mime>,
created_at: MaybeHumanDate,
#[serde(skip_serializing_if = "Option::is_none")]
format: Option<InternalFormat>,
format: InternalFormat,
}
impl Details {
@ -57,12 +56,8 @@ impl Details {
Ok(Details::from_parts(format, width, height, frames))
}
pub(crate) fn internal_format(&self) -> Option<InternalFormat> {
if let Some(format) = self.format {
return Some(format);
}
InternalFormat::maybe_from_media_type(&self.content_type, self.frames.is_some())
pub(crate) fn internal_format(&self) -> InternalFormat {
self.format
}
pub(crate) fn media_type(&self) -> mime::Mime {
@ -74,15 +69,27 @@ impl Details {
}
pub(crate) fn video_format(&self) -> Option<InternalVideoFormat> {
if *self.content_type == crate::formats::mimes::video_mp4() {
return Some(InternalVideoFormat::Mp4);
match self.format {
InternalFormat::Video(format) => Some(format),
_ => None,
}
}
if *self.content_type == crate::formats::mimes::video_webm() {
return Some(InternalVideoFormat::Webm);
pub(crate) fn from_parts_full(
format: InternalFormat,
width: u16,
height: u16,
frames: Option<u32>,
created_at: MaybeHumanDate,
) -> Self {
Self {
width,
height,
frames,
content_type: Serde::new(format.media_type()),
created_at,
format,
}
None
}
pub(crate) fn from_parts(
@ -97,7 +104,7 @@ impl Details {
frames,
content_type: Serde::new(format.media_type()),
created_at: MaybeHumanDate::HumanDate(OffsetDateTime::now_utc()),
format: Some(format),
format,
}
}
}

View file

@ -130,8 +130,8 @@ async fn process<S: Store + 'static>(
let input_format = input_details
.internal_format()
.and_then(|format| format.processable_format())
.expect("Valid details should always have internal format");
.processable_format()
.expect("Already verified format is processable");
let Some(format) = input_format.process_to(output_format) else {
return Err(UploadError::InvalidProcessExtension.into());

View file

@ -102,13 +102,7 @@ async fn ensure_details<S: Store + 'static>(
return Err(UploadError::MissingAlias.into());
};
let details = repo.details(&identifier).await?.and_then(|details| {
if details.internal_format().is_some() {
Some(details)
} else {
None
}
});
let details = repo.details(&identifier).await?;
if let Some(details) = details {
tracing::debug!("details exist");
@ -784,13 +778,7 @@ async fn process<S: Store + 'static>(
.transpose()?;
if let Some(identifier) = identifier_opt {
let details = repo.details(&identifier).await?.and_then(|details| {
if details.internal_format().is_some() {
Some(details)
} else {
None
}
});
let details = repo.details(&identifier).await?;
let details = if let Some(details) = details {
tracing::debug!("details exist");
@ -916,13 +904,7 @@ async fn process_head<S: Store + 'static>(
.transpose()?;
if let Some(identifier) = identifier_opt {
let details = repo.details(&identifier).await?.and_then(|details| {
if details.internal_format().is_some() {
Some(details)
} else {
None
}
});
let details = repo.details(&identifier).await?;
let details = if let Some(details) = details {
tracing::debug!("details exist");

View file

@ -398,14 +398,7 @@ where
.details(identifier)
.await
.map_err(Error::from)
.map_err(MigrateError::Details)?
.and_then(|details| {
if details.internal_format().is_some() {
Some(details)
} else {
None
}
});
.map_err(MigrateError::Details)?;
let details = if let Some(details) = details_opt {
details

View file

@ -151,11 +151,7 @@ async fn do_migrate_hash_04<S: Store>(
let hash = old_hash[..].try_into().expect("Invalid hash size");
let hash = Hash::new(
hash,
size,
hash_details.internal_format().expect("format exists"),
);
let hash = Hash::new(hash, size, hash_details.internal_format());
let _ = HashRepo::create(new_repo.as_ref(), hash.clone(), &identifier).await?;
@ -212,13 +208,7 @@ async fn fetch_or_generate_details<S: Store>(
config: &Configuration,
identifier: &S::Identifier,
) -> Result<Details, Error> {
let details_opt = old_repo.details(identifier).await?.and_then(|details| {
if details.internal_format().is_some() {
Some(details)
} else {
None
}
});
let details_opt = old_repo.details(identifier).await?;
if let Some(details) = details_opt {
Ok(details)

View file

@ -57,6 +57,41 @@ pub(crate) struct SledRepo {
_db: Db,
}
#[derive(Clone, Debug, serde::Deserialize, serde::Serialize)]
pub(crate) struct OldDetails {
width: u16,
height: u16,
frames: Option<u32>,
content_type: crate::serde_str::Serde<mime::Mime>,
created_at: crate::details::MaybeHumanDate,
#[serde(skip_serializing_if = "Option::is_none")]
format: Option<crate::formats::InternalFormat>,
}
impl OldDetails {
fn into_details(self) -> Option<Details> {
let OldDetails {
width,
height,
frames,
content_type,
created_at,
format,
} = self;
let format = format.or_else(|| {
crate::formats::InternalFormat::maybe_from_media_type(
&content_type,
self.frames.is_some(),
)
})?;
Some(Details::from_parts_full(
format, width, height, frames, created_at,
))
}
}
impl SledRepo {
#[tracing::instrument]
pub(crate) fn build(path: PathBuf, cache_capacity: u64) -> color_eyre::Result<Option<Self>> {
@ -135,11 +170,12 @@ impl IdentifierRepo for SledRepo {
let opt = b!(self.identifier_details, identifier_details.get(key));
opt.map(|ivec| serde_json::from_slice(&ivec))
opt.map(|ivec| serde_json::from_slice::<OldDetails>(&ivec))
.transpose()
.map_err(SledError::from)
.map_err(RepoError::from)
.map_err(StoreError::from)
.map(|opt| opt.and_then(OldDetails::into_details))
}
}