use object_rainbow::{
InlineOutput, ListHashes, MaybeHasNiche, Parse, ParseInline, Size, Tagged, ToOutput,
Topological, derive_for_wrapped,
};
use crate::Apply;
#[derive_for_wrapped]
pub trait MapToSet<K: Send, V: Send>: Send + Sync {
type T: Send;
fn map(&self, key: K, value: V)
-> impl Send + Future<Output = object_rainbow::Result<Self::T>>;
}
#[derive(
Debug,
ToOutput,
InlineOutput,
Tagged,
ListHashes,
Topological,
Parse,
ParseInline,
Size,
MaybeHasNiche,
Clone,
Copy,
PartialEq,
Eq,
PartialOrd,
Ord,
Default,
)]
pub struct MappedToSet<M>(M);
impl<K: Send + Clone, V: Send, M: MapToSet<K, V>> Apply<(Option<V>, (Option<V>, K))>
for MappedToSet<M>
{
type Output = Vec<(Option<()>, M::T)>;
async fn apply(
&mut self,
(old, (new, key)): (Option<V>, (Option<V>, K)),
) -> object_rainbow::Result<Self::Output> {
let mut diff = Vec::new();
if let Some(value) = old {
diff.push((None, self.0.map(key.clone(), value).await?));
}
if let Some(value) = new {
diff.push((Some(()), self.0.map(key, value).await?));
}
Ok(diff)
}
}
impl<K: Send, V: Send, M: MapToSet<K, V>> Apply<(Option<(V, K)>, (Option<V>, K))>
for MappedToSet<M>
{
type Output = Vec<(Option<()>, M::T)>;
async fn apply(
&mut self,
(old, (new, key)): (Option<(V, K)>, (Option<V>, K)),
) -> object_rainbow::Result<Self::Output> {
let mut diff = Vec::new();
if let Some((value, key)) = old {
diff.push((None, self.0.map(key, value).await?));
}
if let Some(value) = new {
diff.push((Some(()), self.0.map(key, value).await?));
}
Ok(diff)
}
}
#[derive(
Debug,
ToOutput,
InlineOutput,
Tagged,
ListHashes,
Topological,
Parse,
ParseInline,
Size,
MaybeHasNiche,
Clone,
Copy,
PartialEq,
Eq,
PartialOrd,
Ord,
Default,
)]
pub struct ToSet;
impl<K: Send, V: Send> MapToSet<K, V> for ToSet {
type T = (K, V);
fn map(
&self,
key: K,
value: V,
) -> impl Send + Future<Output = object_rainbow::Result<Self::T>> {
core::future::ready(Ok((key, value)))
}
}