pub mod mem;
use std::borrow::Borrow;
use std::cmp::Ord;
use std::error::Error;
use std::fmt;
use std::ops::{Bound, Range, RangeFrom, RangeFull, RangeInclusive, RangeTo, RangeToInclusive};
pub trait DurableSet: Send + Sync {
type Item: Send;
fn add(&mut self, item: Self::Item) -> Result<(), DurableSetError>;
fn remove(&mut self, item: &Self::Item) -> Result<Option<Self::Item>, DurableSetError>;
fn contains(&self, item: &Self::Item) -> Result<bool, DurableSetError>;
fn iter<'a>(&'a self) -> Result<Box<(dyn Iterator<Item = Self::Item> + 'a)>, DurableSetError>;
fn len(&self) -> Result<u64, DurableSetError>;
fn is_empty(&self) -> Result<bool, DurableSetError> {
Ok(self.len()? == 0)
}
}
pub trait DurableOrderedSet<V, Index>: DurableSet<Item = V>
where
Index: Ord + Send,
V: Send + Ord + Borrow<Index>,
{
fn get_by_index(&self, index_value: &Index) -> Result<Option<Self::Item>, DurableSetError>;
fn contains_by_index(&self, index_value: &Index) -> Result<bool, DurableSetError>;
fn range_iter<'a>(
&'a self,
range: DurableRange<&Index>,
) -> Result<Box<(dyn Iterator<Item = Self::Item> + 'a)>, DurableSetError>;
fn first(&self) -> Result<Option<Self::Item>, DurableSetError>;
fn last(&self) -> Result<Option<Self::Item>, DurableSetError>;
fn clone_boxed_ordered_set(&self) -> Box<dyn DurableOrderedSet<V, Index>>;
}
impl<V, Index> Clone for Box<dyn DurableOrderedSet<V, Index>>
where
Index: Ord + Send,
V: Send + Ord + Borrow<Index>,
{
fn clone(&self) -> Self {
self.clone_boxed_ordered_set()
}
}
pub struct DurableRange<T> {
pub start: Bound<T>,
pub end: Bound<T>,
}
impl<T> From<Range<T>> for DurableRange<T> {
fn from(range: Range<T>) -> Self {
Self {
start: Bound::Included(range.start),
end: Bound::Excluded(range.end),
}
}
}
impl<T> From<RangeInclusive<T>> for DurableRange<T> {
fn from(range: RangeInclusive<T>) -> Self {
let (start, end) = range.into_inner();
Self {
start: Bound::Included(start),
end: Bound::Included(end),
}
}
}
impl<T> From<RangeFull> for DurableRange<T> {
fn from(_: RangeFull) -> Self {
Self {
start: Bound::Unbounded,
end: Bound::Unbounded,
}
}
}
impl<T> From<RangeFrom<T>> for DurableRange<T> {
fn from(range: RangeFrom<T>) -> Self {
Self {
start: Bound::Included(range.start),
end: Bound::Unbounded,
}
}
}
impl<T> From<RangeTo<T>> for DurableRange<T> {
fn from(range: RangeTo<T>) -> Self {
Self {
start: Bound::Unbounded,
end: Bound::Excluded(range.end),
}
}
}
impl<T> From<RangeToInclusive<T>> for DurableRange<T> {
fn from(range: RangeToInclusive<T>) -> Self {
Self {
start: Bound::Unbounded,
end: Bound::Included(range.end),
}
}
}
impl<T> From<(Bound<T>, Bound<T>)> for DurableRange<T> {
fn from((start, end): (Bound<T>, Bound<T>)) -> Self {
Self { start, end }
}
}
#[derive(Debug)]
pub struct DurableSetError {
pub context: String,
pub source: Option<Box<dyn Error + Send>>,
}
impl DurableSetError {
pub fn new(context: &str) -> Self {
Self {
context: context.into(),
source: None,
}
}
pub fn with_source(context: &str, source: Box<dyn Error + Send>) -> Self {
Self {
context: context.into(),
source: Some(source),
}
}
}
impl Error for DurableSetError {
fn source(&self) -> Option<&(dyn Error + 'static)> {
self.source
.as_ref()
.map(|err| &**err as &(dyn Error + 'static))
}
}
impl fmt::Display for DurableSetError {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
if let Some(ref err) = self.source {
write!(f, "{}: {}", self.context, err)
} else {
f.write_str(&self.context)
}
}
}