foundationdb/
mapped_key_values.rs1use crate::from_raw_fdb_slice;
18use crate::future::{FdbFutureHandle, FdbKeyValue};
19use crate::{error, KeySelector};
20use crate::{FdbError, FdbResult};
21use foundationdb_sys as fdb_sys;
22use std::borrow::Cow;
23use std::fmt;
24
25use std::ops::Deref;
26use std::sync::Arc;
27
28pub struct MappedKeyValues {
30 _f: FdbFutureHandle,
31 mapped_keyvalues: *const FdbMappedKeyValue,
32 len: i32,
33 more: bool,
34}
35unsafe impl Sync for MappedKeyValues {}
36unsafe impl Send for MappedKeyValues {}
37
38impl MappedKeyValues {
39 pub fn more(&self) -> bool {
41 self.more
42 }
43}
44
45impl TryFrom<FdbFutureHandle> for MappedKeyValues {
46 type Error = FdbError;
47 fn try_from(f: FdbFutureHandle) -> FdbResult<Self> {
48 let mut mapped_keyvalues = std::ptr::null();
49 let mut len = 0;
50 let mut more = 0;
51
52 unsafe {
53 error::eval(fdb_sys::fdb_future_get_mappedkeyvalue_array(
54 f.as_ptr(),
55 &mut mapped_keyvalues,
56 &mut len,
57 &mut more,
58 ))?
59 }
60
61 Ok(MappedKeyValues {
62 _f: f,
63 mapped_keyvalues: mapped_keyvalues as *const FdbMappedKeyValue,
64 len,
65 more: more != 0,
66 })
67 }
68}
69
70#[repr(packed)]
71pub struct FdbMappedKeyValue(fdb_sys::FDBMappedKeyValue);
73
74impl PartialEq for FdbMappedKeyValue {
75 fn eq(&self, other: &Self) -> bool {
76 (self.parent_key(), self.parent_value()) == (other.parent_key(), other.parent_value())
77 }
78}
79impl Eq for FdbMappedKeyValue {}
80impl fmt::Debug for FdbMappedKeyValue {
81 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
82 write!(
83 f,
84 "({:?}, {:?})",
85 crate::tuple::Bytes::from(self.parent_key()),
86 crate::tuple::Bytes::from(self.parent_value())
87 )
88 }
89}
90
91impl FdbMappedKeyValue {
92 pub fn parent_key(&self) -> &[u8] {
94 from_raw_fdb_slice(self.0.key.key, self.0.key.key_length as usize)
95 }
96
97 pub fn parent_value(&self) -> &[u8] {
99 from_raw_fdb_slice(self.0.value.key, self.0.value.key_length as usize)
100 }
101
102 pub fn begin_range(&self) -> &[u8] {
104 from_raw_fdb_slice(
105 self.0.getRange.begin.key.key,
106 self.0.getRange.begin.key.key_length as usize,
107 )
108 }
109
110 pub fn end_range(&self) -> &[u8] {
112 from_raw_fdb_slice(
113 self.0.getRange.end.key.key,
114 self.0.getRange.end.key.key_length as usize,
115 )
116 }
117
118 pub fn begin_selector(&self) -> KeySelector {
120 KeySelector::new(Cow::from(self.begin_range()), false, 0)
121 }
122
123 pub fn end_selector(&self) -> KeySelector {
125 KeySelector::new(Cow::from(self.end_range()), false, 0)
126 }
127
128 pub fn key_values(&self) -> &[FdbKeyValue] {
130 from_raw_fdb_slice(
131 self.0.getRange.data as *const FdbKeyValue,
132 self.0.getRange.m_size as usize,
133 )
134 }
135}
136
137impl Deref for MappedKeyValues {
138 type Target = [FdbMappedKeyValue];
139
140 fn deref(&self) -> &Self::Target {
141 assert_eq_size!(FdbMappedKeyValue, fdb_sys::FDBMappedKeyValue);
142 assert_eq_align!(FdbMappedKeyValue, u8);
143 from_raw_fdb_slice(self.mapped_keyvalues, self.len as usize)
144 }
145}
146
147impl AsRef<[FdbMappedKeyValue]> for MappedKeyValues {
148 fn as_ref(&self) -> &[FdbMappedKeyValue] {
149 self.deref()
150 }
151}
152
153impl<'a> IntoIterator for &'a MappedKeyValues {
154 type Item = &'a FdbMappedKeyValue;
155 type IntoIter = std::slice::Iter<'a, FdbMappedKeyValue>;
156
157 fn into_iter(self) -> Self::IntoIter {
158 self.deref().iter()
159 }
160}
161
162pub struct FdbMappedValue {
164 _f: Arc<FdbFutureHandle>,
165 mapped_keyvalue: *const FdbMappedKeyValue,
166}
167
168impl IntoIterator for MappedKeyValues {
169 type Item = FdbMappedValue;
170 type IntoIter = FdbMappedValuesIter;
171
172 fn into_iter(self) -> Self::IntoIter {
173 FdbMappedValuesIter {
174 f: Arc::new(self._f),
175 mapped_keyvalues: self.mapped_keyvalues,
176 len: self.len,
177 pos: 0,
178 }
179 }
180}
181
182unsafe impl Send for FdbMappedValue {}
183
184impl Deref for FdbMappedValue {
185 type Target = FdbMappedKeyValue;
186 fn deref(&self) -> &Self::Target {
187 assert_eq_size!(FdbMappedKeyValue, fdb_sys::FDBMappedKeyValue);
188 assert_eq_align!(FdbMappedKeyValue, u8);
189 unsafe { &*self.mapped_keyvalue }
190 }
191}
192impl AsRef<FdbMappedKeyValue> for FdbMappedValue {
193 fn as_ref(&self) -> &FdbMappedKeyValue {
194 self.deref()
195 }
196}
197impl PartialEq for FdbMappedValue {
198 fn eq(&self, other: &Self) -> bool {
199 self.deref() == other.deref()
200 }
201}
202impl Eq for FdbMappedValue {}
203
204pub struct FdbMappedValuesIter {
206 f: Arc<FdbFutureHandle>,
207 mapped_keyvalues: *const FdbMappedKeyValue,
208 len: i32,
209 pos: i32,
210}
211
212unsafe impl Send for FdbMappedValuesIter {}
213
214impl Iterator for FdbMappedValuesIter {
215 type Item = FdbMappedValue;
216 fn next(&mut self) -> Option<Self::Item> {
217 #[allow(clippy::iter_nth_zero)]
218 self.nth(0)
219 }
220
221 fn nth(&mut self, n: usize) -> Option<Self::Item> {
222 let pos = (self.pos as usize).checked_add(n);
223 match pos {
224 Some(pos) if pos < self.len as usize => {
225 let mapped_keyvalue = unsafe { self.mapped_keyvalues.add(pos) };
227 self.pos = pos as i32 + 1;
228
229 Some(FdbMappedValue {
230 _f: self.f.clone(),
231 mapped_keyvalue,
232 })
233 }
234 _ => {
235 self.pos = self.len;
236 None
237 }
238 }
239 }
240
241 fn size_hint(&self) -> (usize, Option<usize>) {
242 let rem = (self.len - self.pos) as usize;
243 (rem, Some(rem))
244 }
245}
246impl ExactSizeIterator for FdbMappedValuesIter {
247 #[inline]
248 fn len(&self) -> usize {
249 (self.len - self.pos) as usize
250 }
251}
252impl DoubleEndedIterator for FdbMappedValuesIter {
253 fn next_back(&mut self) -> Option<Self::Item> {
254 self.nth_back(0)
255 }
256
257 fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
258 if n < self.len() {
259 self.len -= 1 + n as i32;
260 let keyvalue = unsafe { self.mapped_keyvalues.add(self.len as usize) };
262 Some(FdbMappedValue {
263 _f: self.f.clone(),
264 mapped_keyvalue: keyvalue,
265 })
266 } else {
267 self.pos = self.len;
268 None
269 }
270 }
271}