use std::{ops::Bound, sync::Arc};
use crate::{
engine::{Engine, Partition},
error::{Error, Result},
key_composer::{
KeyComposer, SmallKey, encode_catalog_db_key_fixed, encode_catalog_ns_prefix_fixed,
},
wedb::{
Db, DbBatch, Dbs, IntoOptId, WeDb,
core::{WeDbInner, activate_db_impl, namespace_rm_impl, next_db_id_impl},
},
};
pub struct Namespace<E: Engine> {
pub id: u64,
pub(crate) inner: Arc<WeDbInner<E>>,
}
impl<E: Engine> Clone for Namespace<E> {
#[inline(always)]
fn clone(&self) -> Self {
Self {
id: self.id,
inner: self.inner.clone(),
}
}
}
impl<E: Engine> Namespace<E> {
#[inline(always)]
pub const fn id(&self) -> u64 {
self.id
}
#[inline(always)]
pub fn wedb(&self) -> WeDb<E> {
WeDb {
inner: self.inner.clone(),
}
}
#[inline(always)]
pub fn batch(&self) -> DbBatch<E> {
DbBatch::new(
self.inner.data.clone(),
self.inner.meta.clone(),
self.inner.engine.batch(),
)
}
#[inline(always)]
pub fn batch_with_capacity(&self, capacity: usize) -> DbBatch<E> {
DbBatch::new(
self.inner.data.clone(),
self.inner.meta.clone(),
self.inner.engine.batch_with_capacity(capacity),
)
}
#[inline]
pub fn iter(&self, begin: u64) -> Dbs<'_, E> {
let mut cat_prefix_buf = [0u8; 11];
let cat_len = encode_catalog_ns_prefix_fixed(self.id, &mut cat_prefix_buf);
let cat_prefix = &cat_prefix_buf[..cat_len];
let mut db_key_buf = [0u8; 20];
let start_key: &[u8] = if begin == 0 {
cat_prefix
} else {
let db_len = encode_catalog_db_key_fixed(self.id, begin, &mut db_key_buf);
&db_key_buf[..db_len]
};
let iter = self
.inner
.meta
.range((Bound::Included(start_key), Bound::Unbounded));
Dbs {
prefix: SmallKey::from_slice(cat_prefix),
iter,
}
}
}
impl<E: Engine> Namespace<E>
where
Error: From<E::Error>,
{
#[inline]
pub fn db(&self, id: impl IntoOptId) -> Result<Db<E>> {
let db_id = match id.into_opt_id() {
Some(id) => id,
None => next_db_id_impl::<E>(&self.inner.meta, &self.inner.ns_lock, self.id)?,
};
activate_db_impl::<E>(&self.inner.meta, self.id, db_id)?;
Ok(Db {
kc: KeyComposer::new(self.id, db_id),
inner: self.inner.clone(),
})
}
#[inline]
pub fn rm(&self) -> Result<u64> {
let count = namespace_rm_impl::<E>(
&self.inner.data,
&self.inner.meta,
&self.inner.engine,
self.id,
)?;
Ok(count)
}
}