Skip to main content

reifydb_store_multi/
lib.rs

1// SPDX-License-Identifier: Apache-2.0
2// Copyright (c) 2025 ReifyDB
3#![cfg_attr(not(debug_assertions), deny(clippy::disallowed_methods))]
4#![cfg_attr(debug_assertions, warn(clippy::disallowed_methods))]
5#![cfg_attr(not(debug_assertions), deny(warnings))]
6#![allow(clippy::tabs_in_doc_comments)]
7
8use reifydb_core::{
9	event::EventBus,
10	interface::version::{ComponentType, HasVersion, SystemVersion},
11};
12use reifydb_type::Result;
13
14pub mod cold;
15pub mod hot;
16pub mod tier;
17pub mod warm;
18
19pub mod config;
20pub mod multi;
21pub mod store;
22
23use config::{HotConfig, MultiStoreConfig};
24use reifydb_core::{
25	common::CommitVersion,
26	delta::Delta,
27	encoded::key::{EncodedKey, EncodedKeyRange},
28	interface::store::{
29		MultiVersionCommit, MultiVersionContains, MultiVersionGet, MultiVersionGetPrevious, MultiVersionRow,
30		MultiVersionStore,
31	},
32};
33use reifydb_type::util::cowvec::CowVec;
34use store::StandardMultiStore;
35
36pub mod memory {}
37pub mod sqlite {}
38
39pub struct MultiStoreVersion;
40
41impl HasVersion for MultiStoreVersion {
42	fn version(&self) -> SystemVersion {
43		SystemVersion {
44			name: env!("CARGO_PKG_NAME")
45				.strip_prefix("reifydb-")
46				.unwrap_or(env!("CARGO_PKG_NAME"))
47				.to_string(),
48			version: env!("CARGO_PKG_VERSION").to_string(),
49			description: "Multi-version storage for OLTP operations with MVCC support".to_string(),
50			r#type: ComponentType::Module,
51		}
52	}
53}
54
55#[repr(u8)]
56#[derive(Clone)]
57pub enum MultiStore {
58	Standard(StandardMultiStore) = 0,
59	// Other(Box<dyn MultiVersionStore>) = 254,
60}
61
62impl MultiStore {
63	pub fn standard(config: MultiStoreConfig) -> Self {
64		Self::Standard(StandardMultiStore::new(config).unwrap())
65	}
66}
67
68impl MultiStore {
69	pub fn testing_memory() -> Self {
70		MultiStore::Standard(StandardMultiStore::testing_memory())
71	}
72
73	pub fn testing_memory_with_eventbus(event_bus: EventBus) -> Self {
74		MultiStore::Standard(StandardMultiStore::testing_memory_with_eventbus(event_bus))
75	}
76
77	/// Get access to the hot storage tier.
78	///
79	/// Returns `None` if the hot tier is not configured.
80	pub fn hot(&self) -> Option<&hot::storage::HotStorage> {
81		match self {
82			MultiStore::Standard(store) => store.hot(),
83		}
84	}
85}
86
87// MultiVersion trait implementations
88
89impl MultiVersionGet for MultiStore {
90	#[inline]
91	fn get(&self, key: &EncodedKey, version: CommitVersion) -> Result<Option<MultiVersionRow>> {
92		match self {
93			MultiStore::Standard(store) => MultiVersionGet::get(store, key, version),
94		}
95	}
96}
97
98impl MultiVersionContains for MultiStore {
99	#[inline]
100	fn contains(&self, key: &EncodedKey, version: CommitVersion) -> Result<bool> {
101		match self {
102			MultiStore::Standard(store) => MultiVersionContains::contains(store, key, version),
103		}
104	}
105}
106
107impl MultiVersionCommit for MultiStore {
108	#[inline]
109	fn commit(&self, deltas: CowVec<Delta>, version: CommitVersion) -> Result<()> {
110		match self {
111			MultiStore::Standard(store) => store.commit(deltas, version),
112		}
113	}
114}
115
116impl MultiVersionGetPrevious for MultiStore {
117	#[inline]
118	fn get_previous_version(
119		&self,
120		key: &EncodedKey,
121		before_version: CommitVersion,
122	) -> Result<Option<MultiVersionRow>> {
123		match self {
124			MultiStore::Standard(store) => store.get_previous_version(key, before_version),
125		}
126	}
127}
128
129/// Iterator type for multi-version range results.
130pub type MultiVersionRangeIterator<'a> = Box<dyn Iterator<Item = Result<MultiVersionRow>> + Send + 'a>;
131
132impl MultiStore {
133	/// Create an iterator for forward range queries.
134	///
135	/// This properly handles high version density by scanning until batch_size
136	/// unique logical keys are collected. The iterator yields individual entries
137	/// and maintains cursor state internally.
138	pub fn range(
139		&self,
140		range: EncodedKeyRange,
141		version: CommitVersion,
142		batch_size: usize,
143	) -> MultiVersionRangeIterator<'_> {
144		match self {
145			MultiStore::Standard(store) => Box::new(store.range(range, version, batch_size)),
146		}
147	}
148
149	/// Create an iterator for reverse range queries.
150	///
151	/// This properly handles high version density by scanning until batch_size
152	/// unique logical keys are collected. The iterator yields individual entries
153	/// in reverse key order and maintains cursor state internally.
154	pub fn range_rev(
155		&self,
156		range: EncodedKeyRange,
157		version: CommitVersion,
158		batch_size: usize,
159	) -> MultiVersionRangeIterator<'_> {
160		match self {
161			MultiStore::Standard(store) => Box::new(store.range_rev(range, version, batch_size)),
162		}
163	}
164}
165
166// High-level trait implementations
167impl MultiVersionStore for MultiStore {}