1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184
//! Key, value and selector types used to access FoundationDB
use bytes::Bytes;
/// [`Key`] represents a FDB key, a lexicographically-ordered sequence
/// of bytes.
///
/// [`Key`] can be converted from and into [`Bytes`].
#[derive(Clone, Debug, PartialEq, PartialOrd, Ord, Eq)]
pub struct Key(Bytes);
impl From<Bytes> for Key {
fn from(b: Bytes) -> Key {
Key(b)
}
}
impl From<Key> for Bytes {
fn from(k: Key) -> Bytes {
k.0
}
}
/// [`Value`] represents a value of an FDB [`Key`] and is a sequence
/// of bytes.
///
/// [`Value`] can be converted from and into [`Bytes`].
#[derive(Clone, Debug, PartialEq)]
pub struct Value(Bytes);
impl From<Bytes> for Value {
fn from(b: Bytes) -> Value {
Value(b)
}
}
impl From<Value> for Bytes {
fn from(v: Value) -> Bytes {
v.0
}
}
/// A key/value pair.
///
/// Range read operations on FDB return [`KeyValue`]s.
#[derive(Clone, Debug)]
pub struct KeyValue {
key: Key,
value: Value,
}
impl KeyValue {
/// Construct a new [`KeyValue`].
pub fn new(key: impl Into<Key>, value: impl Into<Value>) -> KeyValue {
KeyValue {
key: key.into(),
value: value.into(),
}
}
/// Gets a reference to [`Key`] from [`KeyValue`].
pub fn get_key_ref(&self) -> &Key {
&self.key
}
/// Gets a reference to [`Value`] from [`KeyValue`].
pub fn get_value_ref(&self) -> &Value {
&self.value
}
/// Extract [`Key`] from [`KeyValue`].
pub fn into_key(self) -> Key {
self.key
}
/// Extract [`Value`] from [`KeyValue`].
pub fn into_value(self) -> Value {
self.value
}
/// Extract [`Key`] and [`Value`] from [`KeyValue`].
pub fn into_parts(self) -> (Key, Value) {
(self.key, self.value)
}
}
/// [`KeySelector`] identifies a particular key in the database.
///
/// FDB's lexicographically ordered data model permits finding keys
/// based on their order (for example, finding the first key in the
/// database greater than a given key). Key selectors represent a
/// description of a key in the database that could be resolved to an
/// actual key by transaction's [`get_key`] or used directly as the
/// beginning or end of a range in transaction's [`get_range`].
///
/// For more about how key selectors work in practice, see the [`key
/// selector`] documentation. Note that the way key selectors are
/// resolved is somewhat non-intuitive, so users who wish to use a key
/// selector other than the default ones described below should
/// probably consult that documentation before proceeding.
///
/// Generally one of the following methods should be used to construct
/// a [`KeySelector`].
/// - [`last_less_than`]
/// - [`last_less_or_equal`]
/// - [`first_greater_than`]
/// - [`first_greater_or_equal`]
///
/// This is an *immutable* type. The `add(i32)` call does not modify
/// internal state, but returns a new value.
///
/// [`get_key`]: crate::transaction::ReadTransaction::get_key
/// [`get_range`]: crate::transaction::ReadTransaction::get_range
/// [`key selector`]: https://apple.github.io/foundationdb/developer-guide.html#key-selectors
/// [`last_less_than`]: KeySelector::last_less_than
/// [`last_less_or_equal`]: KeySelector::last_less_or_equal
/// [`first_greater_than`]: KeySelector::first_greater_than
/// [`first_greater_or_equal`]: KeySelector::first_greater_or_equal
#[derive(Clone, Debug)]
pub struct KeySelector {
key: Key,
or_equal: bool,
offset: i32,
}
impl KeySelector {
/// Create a new [`KeySelector`] from the given parameters.
pub fn new(key: impl Into<Key>, or_equal: bool, offset: i32) -> KeySelector {
KeySelector {
key: key.into(),
or_equal,
offset,
}
}
/// Returns a new [`KeySelector`] offset by a given number of keys
/// from this one.
#[allow(clippy::should_implement_trait)]
pub fn add(self, offset: i32) -> KeySelector {
KeySelector::new(self.key, self.or_equal, self.offset + offset)
}
/// Creates a [`KeySelector`] that picks the first key greater
/// than or equal to the parameter.
pub fn first_greater_or_equal(key: impl Into<Key>) -> KeySelector {
KeySelector::new(key, false, 1)
}
/// Creates a [`KeySelector`] that picks the first key greater
/// than or equal to the parameter.
pub fn first_greater_than(key: impl Into<Key>) -> KeySelector {
KeySelector::new(key, true, 1)
}
/// Returns a reference to the key that serves as the anchor for
/// this [`KeySelector`].
pub fn get_key(&self) -> &Key {
&self.key
}
/// Returns the key offset parameter for this [`KeySelector`].
pub fn get_offset(&self) -> i32 {
self.offset
}
/// Creates a [`KeySelector`] that picks the last key less than or
/// equal to the parameter.
pub fn last_less_or_equal(key: impl Into<Key>) -> KeySelector {
KeySelector::new(key, true, 0)
}
/// Creates a [`KeySelector`] that picks the last key less than the parameter.
pub fn last_less_than(key: impl Into<Key>) -> KeySelector {
KeySelector::new(key, false, 0)
}
pub(crate) fn deconstruct(self) -> (Key, bool, i32) {
let KeySelector {
key,
or_equal,
offset,
} = self;
(key, or_equal, offset)
}
}