fix: playlist deserialization error, add VecSkipErrorWrap

This commit is contained in:
ThetaDev 2023-05-05 17:13:03 +02:00
parent bb396968dc
commit 963ff14dc1
10 changed files with 129 additions and 55 deletions

View file

@ -6,7 +6,7 @@ mod vec_log_err;
pub use date::DateYmd;
pub use range::Range;
pub use vec_log_err::VecLogError;
pub use vec_log_err::{VecLogError, VecSkipErrorWrap};
use std::fmt::Debug;

View file

@ -1,7 +1,7 @@
use std::{fmt, marker::PhantomData};
use serde::{
de::{SeqAccess, Visitor},
de::{IgnoredAny, SeqAccess, Visitor},
Deserialize,
};
use serde_with::{de::DeserializeAsWrap, DeserializeAs};
@ -89,6 +89,59 @@ where
}
}
/// Reimplementation of VecSkipError using a type wrapper
/// to allow use with generics
pub struct VecSkipErrorWrap<T>(pub Vec<T>);
impl<'de, T> Deserialize<'de> for VecSkipErrorWrap<T>
where
T: Deserialize<'de>,
{
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: serde::Deserializer<'de>,
{
#[derive(serde::Deserialize)]
#[serde(untagged)]
enum GoodOrError<T> {
Good(T),
Error(IgnoredAny),
}
struct SeqVisitor<T>(PhantomData<T>);
impl<'de, T> Visitor<'de> for SeqVisitor<T>
where
T: Deserialize<'de>,
{
type Value = VecSkipErrorWrap<T>;
fn expecting(&self, formatter: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
formatter.write_str("a sequence")
}
fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
where
A: SeqAccess<'de>,
{
let mut values = Vec::with_capacity(seq.size_hint().unwrap_or_default());
while let Some(value) = seq.next_element()? {
match value {
GoodOrError::<T>::Good(value) => {
values.push(value);
}
GoodOrError::<T>::Error(_) => {}
}
}
Ok(VecSkipErrorWrap(values))
}
}
deserializer.deserialize_seq(SeqVisitor(PhantomData::<T>))
}
}
#[cfg(test)]
mod tests {
use serde::Deserialize;