Skip to main content

omega_cache/core/
engine.rs

1use crate::core::entry_ref::Ref;
2use crate::core::key::Key;
3use crate::metrics::MetricsSnapshot;
4use std::borrow::Borrow;
5use std::hash::Hash;
6use std::time::Instant;
7
8/// A thread-safe, fixed-capacity caching interface.
9///
10/// This trait abstracts the underlying storage and eviction mechanics,
11/// allowing callers to interact with different cache implementations
12/// through a consistent API.
13///
14/// # Type Parameters
15/// * `K`: The key type, which must implement [`Eq`] and [`Hash`].
16/// * `V`: The value type stored in the cache.
17pub trait CacheEngine<K, V>
18where
19    K: Eq + Hash,
20{
21    /// Retrieves a protected reference to a cached value.
22    ///
23    /// Returns `Some(Ref<K, V>)` if the key exists and is not expired. Accessing
24    /// a key typically updates internal frequency metadata, which the eviction
25    /// algorithm uses to protect "hot" data from removal.
26    ///
27    /// # Memory Safety
28    /// The returned [`Ref`] pins the entry in memory using an epoch guard.
29    /// The data will remain valid and allocated until the reference is dropped
30    /// and the global epoch advances.
31    fn get<Q>(&self, key: &Q) -> Option<Ref<K, V>>
32    where
33        Key<K>: Borrow<Q>,
34        Q: Eq + Hash + ?Sized;
35
36    /// Inserts a key-value pair into the cache.
37    ///
38    /// This is a convenience wrapper around [`insert_with`] that always
39    /// admits the new entry. If the cache is full, an existing entry
40    /// is evicted based on the engine's internal policy.
41    #[inline]
42    fn insert(&self, key: K, value: V, expired_at: Option<Instant>) {
43        self.insert_with(key, value, expired_at, |_, _| true);
44    }
45
46    /// Inserts a key-value pair with a custom admission policy.
47    ///
48    /// When the cache is full, the `admission` closure is invoked with the
49    /// `(incoming_key, potential_victim_key)`. If the closure returns `false`,
50    /// the insertion is aborted to preserve the current cache state.
51    ///
52    /// # Guarantees
53    /// - **Updates**: If the key already exists, the value is updated and
54    ///   the admission policy is typically bypassed.
55    /// - **Expiration**: Expired entries in a target slot are evicted
56    ///   regardless of the admission policy.
57    fn insert_with<A>(&self, key: K, value: V, expired_at: Option<Instant>, admission: A)
58    where
59        A: Fn(&K, &K) -> bool;
60
61    /// Removes an entry from the cache.
62    ///
63    /// Returns `true` if the entry was found and successfully marked for
64    /// removal.
65    ///
66    /// # Consistency
67    /// This method performs an atomic "unlinking." The entry is immediately
68    /// made unreachable for new `get` requests, while existing readers
69    /// can continue to access the data safely until their [`Ref`] is dropped.
70    fn remove<Q>(&self, key: &Q) -> bool
71    where
72        Key<K>: Borrow<Q>,
73        Q: Eq + Hash + ?Sized;
74
75    /// Returns the total number of slots allocated for the cache.
76    fn capacity(&self) -> usize;
77
78    /// Returns a snapshot of internal cache statistics.
79    fn metrics(&self) -> MetricsSnapshot;
80}