trueno_db/kv/memory.rs
1//! In-memory KV store implementation using `DashMap`.
2//!
3//! This is the default backend - data is lost on process restart.
4//! For persistence, use `ParquetKvStore` (future).
5
6use super::KvStore;
7use crate::Result;
8use dashmap::DashMap;
9
10/// In-memory key-value store using lock-free concurrent hashmap.
11///
12/// Thread-safe and optimized for high-concurrency read/write workloads.
13/// Uses `DashMap` internally for O(1) average-case operations.
14///
15/// # Example
16///
17/// ```rust
18/// use trueno_db::kv::{KvStore, MemoryKvStore};
19///
20/// # async fn example() -> trueno_db::Result<()> {
21/// let store = MemoryKvStore::new();
22/// store.set("hello", b"world".to_vec()).await?;
23/// assert_eq!(store.get("hello").await?, Some(b"world".to_vec()));
24/// # Ok(())
25/// # }
26/// ```
27pub struct MemoryKvStore {
28 store: DashMap<String, Vec<u8>>,
29}
30
31impl MemoryKvStore {
32 /// Create a new in-memory KV store.
33 #[must_use]
34 pub fn new() -> Self {
35 Self { store: DashMap::new() }
36 }
37
38 /// Create with pre-allocated capacity.
39 #[must_use]
40 pub fn with_capacity(capacity: usize) -> Self {
41 Self { store: DashMap::with_capacity(capacity) }
42 }
43
44 /// Get the number of entries in the store.
45 #[must_use]
46 pub fn len(&self) -> usize {
47 self.store.len()
48 }
49
50 /// Check if the store is empty.
51 #[must_use]
52 pub fn is_empty(&self) -> bool {
53 self.store.is_empty()
54 }
55
56 /// Clear all entries.
57 pub fn clear(&self) {
58 self.store.clear();
59 }
60}
61
62impl Default for MemoryKvStore {
63 fn default() -> Self {
64 Self::new()
65 }
66}
67
68impl KvStore for MemoryKvStore {
69 async fn get(&self, key: &str) -> Result<Option<Vec<u8>>> {
70 Ok(self.store.get(key).map(|v| v.value().clone()))
71 }
72
73 async fn set(&self, key: &str, value: Vec<u8>) -> Result<()> {
74 self.store.insert(key.to_string(), value);
75 Ok(())
76 }
77
78 async fn delete(&self, key: &str) -> Result<()> {
79 self.store.remove(key);
80 Ok(())
81 }
82
83 async fn exists(&self, key: &str) -> Result<bool> {
84 Ok(self.store.contains_key(key))
85 }
86}