db_rs/
lookup.rs

1use crate::errors::DbResult;
2use crate::logger::Logger;
3use crate::table::Table;
4use crate::TableId;
5use serde::de::DeserializeOwned;
6use serde::{Deserialize, Serialize};
7use std::collections::HashMap;
8use std::hash::Hash;
9
10/// A table backed by a [HashMap] of type `K`, `V`
11#[derive(Debug)]
12#[cfg_attr(feature = "clone", derive(Clone))]
13pub struct LookupTable<K, V>
14where
15    K: Hash + Eq + Serialize,
16    V: Serialize,
17{
18    table_id: TableId,
19    inner: HashMap<K, V>,
20    pub logger: Logger,
21}
22
23#[derive(Serialize, Deserialize)]
24pub enum LogEntry<K, V> {
25    Insert(K, V),
26    Remove(K),
27    Clear,
28}
29
30impl<K, V> Table for LookupTable<K, V>
31where
32    K: Hash + Eq + Serialize + DeserializeOwned,
33    V: Serialize + DeserializeOwned,
34{
35    fn init(table_id: TableId, logger: Logger) -> Self {
36        Self { table_id, inner: HashMap::default(), logger }
37    }
38
39    fn handle_event(&mut self, bytes: &[u8]) -> DbResult<()> {
40        match bincode::deserialize(bytes)? {
41            LogEntry::Insert(k, v) => {
42                self.inner.insert(k, v);
43            }
44            LogEntry::Remove(k) => {
45                self.inner.remove(&k);
46            }
47            LogEntry::Clear => {
48                self.inner.clear();
49            }
50        };
51
52        Ok(())
53    }
54
55    fn compact_repr(&self) -> DbResult<Vec<u8>> {
56        let mut repr = vec![];
57        for (k, v) in &self.inner {
58            let data = bincode::serialize(&LogEntry::Insert(k, v))?;
59            let mut data = Logger::log_entry(self.table_id, data);
60            repr.append(&mut data);
61        }
62
63        Ok(repr)
64    }
65}
66
67impl<K, V> LookupTable<K, V>
68where
69    K: Hash + Eq + Serialize,
70    V: Serialize,
71{
72    pub fn insert(&mut self, key: K, value: V) -> DbResult<Option<V>> {
73        let log_entry = LogEntry::Insert(&key, &value);
74        let data = bincode::serialize(&log_entry)?;
75
76        let ret = self.inner.insert(key, value);
77
78        self.logger.write(self.table_id, data)?;
79        Ok(ret)
80    }
81
82    pub fn remove(&mut self, key: &K) -> DbResult<Option<V>> {
83        let log_entry = LogEntry::Remove::<&K, &V>(key);
84        let data = bincode::serialize(&log_entry)?;
85        let ret = self.inner.remove(key);
86        self.logger.write(self.table_id, data)?;
87        Ok(ret)
88    }
89
90    pub fn get(&self) -> &HashMap<K, V> {
91        &self.inner
92    }
93
94    pub fn clear(&mut self) -> DbResult<()> {
95        self.inner.clear();
96        let log_entry = LogEntry::<K, V>::Clear;
97        let data = bincode::serialize(&log_entry)?;
98        self.logger.write(self.table_id, data)?;
99
100        Ok(())
101    }
102}