redact_crypto/storage/
selfstore.rs

1use crate::{CryptoError, Entry, NonIndexedTypeStorer, StorableType, Storer, TypeStorer};
2use async_trait::async_trait;
3use once_cell::sync::Lazy;
4use serde::{Deserialize, Serialize};
5use std::{
6    error::Error,
7    fmt::Display,
8    sync::{Arc, RwLock},
9};
10
11static SELF_STORER: Lazy<RwLock<Arc<SelfStorer>>> = Lazy::new(|| RwLock::new(Default::default()));
12
13#[derive(Debug)]
14pub enum SelfStorerError {
15    /// No self storer was defined for use, self store operations are not supported
16    NoSelfStorerProvided,
17}
18
19impl Error for SelfStorerError {
20    fn source(&self) -> Option<&(dyn Error + 'static)> {
21        match *self {
22            SelfStorerError::NoSelfStorerProvided => None,
23        }
24    }
25}
26
27impl Display for SelfStorerError {
28    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
29        match *self {
30            SelfStorerError::NoSelfStorerProvided => write!(f, "No self storer was defined"),
31        }
32    }
33}
34
35impl From<SelfStorerError> for CryptoError {
36    fn from(sse: SelfStorerError) -> Self {
37        match sse {
38            SelfStorerError::NoSelfStorerProvided => CryptoError::InternalError {
39                source: Box::new(sse),
40            },
41        }
42    }
43}
44
45#[derive(Serialize, Deserialize, Debug, Clone, Default)]
46pub struct SelfStorer {
47    #[serde(skip)]
48    internal_storer: Option<Box<TypeStorer>>,
49}
50
51impl From<SelfStorer> for NonIndexedTypeStorer {
52    fn from(ss: SelfStorer) -> Self {
53        NonIndexedTypeStorer::SelfStore(ss)
54    }
55}
56
57impl From<SelfStorer> for TypeStorer {
58    fn from(ss: SelfStorer) -> Self {
59        TypeStorer::NonIndexed(NonIndexedTypeStorer::SelfStore(ss))
60    }
61}
62
63impl SelfStorer {
64    pub fn current() -> Arc<SelfStorer> {
65        SELF_STORER.read().unwrap().clone()
66    }
67
68    pub fn make_current(self) {
69        *SELF_STORER.write().unwrap() = Arc::new(self)
70    }
71}
72
73#[async_trait]
74impl Storer for SelfStorer {
75    async fn get<T: StorableType>(&self, path: &str) -> Result<Entry<T>, CryptoError> {
76        match SelfStorer::current().internal_storer {
77            Some(ref storer) => storer.get(path).await,
78            None => Err(SelfStorerError::NoSelfStorerProvided.into()),
79        }
80    }
81
82    async fn create<T: StorableType>(&self, value: Entry<T>) -> Result<Entry<T>, CryptoError> {
83        match SelfStorer::current().internal_storer {
84            Some(ref storer) => storer.create(value).await,
85            None => Err(SelfStorerError::NoSelfStorerProvided.into()),
86        }
87    }
88}