#[cfg(test)]
mod test;
use crate::common::{PreBytes, RawKey, RawValue, engine};
use ruc::*;
use serde::{Deserialize, Serialize};
use std::{borrow::Cow, fs, ops::RangeBounds};
pub type MapxRawIter<'a> = engine::MapxIter<'a>;
pub type MapxRawIterMut<'a> = engine::MapxIterMut<'a>;
pub type ValueMut<'a> = engine::ValueMut<'a>;
pub type ValueIterMut<'a> = engine::ValueIterMut<'a>;
#[derive(Clone, PartialEq, Eq, Debug)]
pub struct MapxRaw {
inner: engine::Mapx,
}
impl Serialize for MapxRaw {
fn serialize<S>(&self, serializer: S) -> std::result::Result<S::Ok, S::Error>
where
S: serde::Serializer,
{
self.inner.serialize(serializer)
}
}
impl<'de> Deserialize<'de> for MapxRaw {
fn deserialize<D>(deserializer: D) -> std::result::Result<Self, D::Error>
where
D: serde::Deserializer<'de>,
{
engine::Mapx::deserialize(deserializer).map(|inner| Self { inner })
}
}
impl MapxRaw {
#[inline(always)]
pub unsafe fn shadow(&self) -> Self {
Self {
inner: unsafe { self.inner.shadow() },
}
}
#[inline(always)]
pub fn new() -> Self {
MapxRaw {
inner: engine::Mapx::new(),
}
}
#[inline(always)]
pub fn get(&self, key: impl AsRef<[u8]>) -> Option<RawValue> {
self.inner.get(key.as_ref())
}
#[inline(always)]
pub fn get_mut(&mut self, key: impl AsRef<[u8]>) -> Option<ValueMut<'_>> {
self.inner.get_mut(key.as_ref())
}
#[inline(always)]
pub fn mock_value_mut(&mut self, key: RawValue, value: RawValue) -> ValueMut<'_> {
self.inner.mock_value_mut(key, value)
}
#[inline(always)]
pub fn contains_key(&self, key: impl AsRef<[u8]>) -> bool {
self.get(key.as_ref()).is_some()
}
#[inline(always)]
pub fn get_le(&self, key: impl AsRef<[u8]>) -> Option<(RawKey, RawValue)> {
self.range(..=Cow::Borrowed(key.as_ref())).next_back()
}
#[inline(always)]
pub fn get_ge(&self, key: impl AsRef<[u8]>) -> Option<(RawKey, RawValue)> {
self.range(Cow::Borrowed(key.as_ref())..).next()
}
#[inline(always)]
pub fn entry<'a>(&'a mut self, key: &'a [u8]) -> Entry<'a> {
Entry { key, hdr: self }
}
#[inline(always)]
pub fn iter(&self) -> MapxRawIter<'_> {
self.inner.iter()
}
#[inline(always)]
pub fn range<'a, R: RangeBounds<Cow<'a, [u8]>>>(
&'a self,
bounds: R,
) -> MapxRawIter<'a> {
self.inner.range(bounds)
}
#[inline(always)]
pub fn range_detached<'a, R: RangeBounds<Cow<'a, [u8]>>>(
&self,
bounds: R,
) -> MapxRawIter<'a> {
self.inner.range_detached(bounds)
}
#[inline(always)]
pub fn iter_mut(&mut self) -> MapxRawIterMut<'_> {
self.inner.iter_mut()
}
#[inline(always)]
pub fn range_mut<'a, R: RangeBounds<Cow<'a, [u8]>>>(
&'a mut self,
bounds: R,
) -> MapxRawIterMut<'a> {
self.inner.range_mut(bounds)
}
#[inline(always)]
pub fn last(&self) -> Option<(RawKey, RawValue)> {
self.iter().next_back()
}
#[inline(always)]
pub fn insert(&mut self, key: impl AsRef<[u8]>, value: impl AsRef<[u8]>) {
self.inner.insert(key.as_ref(), value.as_ref())
}
#[inline(always)]
pub fn remove(&mut self, key: impl AsRef<[u8]>) {
self.inner.remove(key.as_ref())
}
#[doc(hidden)]
#[inline(always)]
pub fn lazy_delete(&self, key: impl AsRef<[u8]>) {
self.inner.lazy_delete(key.as_ref())
}
#[doc(hidden)]
#[inline(always)]
pub fn lazy_delete_batch(&self, keys: impl IntoIterator<Item = impl AsRef<[u8]>>) {
self.inner.lazy_delete_batch(keys)
}
#[inline(always)]
pub fn batch_entry(&mut self) -> Box<dyn crate::common::BatchTrait + '_> {
self.inner.batch_begin()
}
#[inline(always)]
pub fn clear(&mut self) {
self.inner.clear();
}
#[inline(always)]
pub unsafe fn from_bytes(s: impl AsRef<[u8]>) -> Self {
Self {
inner: unsafe { engine::Mapx::from_prefix_slice(s) },
}
}
#[deprecated(since = "13.0.0", note = "use `from_bytes` instead")]
#[inline(always)]
pub unsafe fn from_prefix_slice(s: impl AsRef<[u8]>) -> Self {
unsafe { Self::from_bytes(s) }
}
#[inline(always)]
pub fn as_bytes(&self) -> &PreBytes {
self.inner.as_prefix_slice()
}
#[deprecated(since = "13.0.0", note = "use `as_bytes` instead")]
#[inline(always)]
pub fn as_prefix_slice(&self) -> &PreBytes {
self.inner.as_prefix_slice()
}
pub fn instance_id(&self) -> u64 {
let mut bytes = [0u8; 8];
bytes.copy_from_slice(self.as_bytes());
u64::from_le_bytes(bytes)
}
#[inline(always)]
pub fn is_the_same_instance(&self, other_hdr: &Self) -> bool {
self.inner.is_the_same_instance(&other_hdr.inner)
}
pub fn save_meta(&self) -> Result<u64> {
let id = self.instance_id();
fs::write(
crate::common::vsdb_meta_path(id),
self.inner.encode_prefix_meta(),
)
.c(d!())?;
Ok(id)
}
pub fn from_meta(instance_id: u64) -> Result<Self> {
let bytes = fs::read(crate::common::vsdb_meta_path(instance_id)).c(d!())?;
let prefix = engine::Mapx::decode_trusted_prefix_meta(&bytes).c(d!())?;
Ok(unsafe { Self::from_bytes(prefix) })
}
}
impl Default for MapxRaw {
fn default() -> Self {
Self::new()
}
}
pub struct Entry<'a> {
key: &'a [u8],
hdr: &'a mut MapxRaw,
}
impl<'a> Entry<'a> {
pub fn or_insert(self, default: &'a [u8]) -> ValueMut<'a> {
let hdr = self.hdr as *mut MapxRaw;
match unsafe { &mut *hdr }.get_mut(self.key) {
Some(v) => v,
_ => {
unsafe { &mut *hdr }.mock_value_mut(self.key.to_vec(), default.to_vec())
}
}
}
pub fn or_insert_with<F>(self, f: F) -> ValueMut<'a>
where
F: FnOnce() -> RawValue,
{
let hdr = self.hdr as *mut MapxRaw;
match unsafe { &mut *hdr }.get_mut(self.key) {
Some(v) => v,
_ => unsafe { &mut *hdr }.mock_value_mut(self.key.to_vec(), f()),
}
}
}