pub mod bitwise;
#[doc(hidden)]
pub mod cdt;
pub mod cdt_context;
pub mod exp;
pub mod hll;
pub mod lists;
pub mod maps;
pub mod scalar;
use self::cdt::CdtOperation;
pub use self::maps::{MapOrder, MapPolicy, MapReturnType, MapWriteMode};
pub use self::scalar::*;
use crate::commands::buffer::Buffer;
use crate::commands::ParticleType;
use crate::errors::Result;
use crate::operations::cdt_context::CdtContext;
use crate::operations::exp::ExpOperation;
use crate::Value;
#[derive(Clone, Copy)]
#[doc(hidden)]
pub enum OperationType {
Read = 1,
Write = 2,
CdtRead = 3,
CdtWrite = 4,
Incr = 5,
ExpRead = 7,
ExpWrite = 8,
Append = 9,
Prepend = 10,
Touch = 11,
BitRead = 12,
BitWrite = 13,
Delete = 14,
HllRead = 15,
HllWrite = 16,
}
#[doc(hidden)]
pub enum OperationData<'a> {
None,
Value(&'a Value),
CdtListOp(CdtOperation<'a>),
CdtMapOp(CdtOperation<'a>),
CdtBitOp(CdtOperation<'a>),
HLLOp(CdtOperation<'a>),
EXPOp(ExpOperation<'a>),
}
#[doc(hidden)]
pub enum OperationBin<'a> {
None,
All,
Name(&'a str),
}
pub struct Operation<'a> {
#[doc(hidden)]
pub op: OperationType,
#[doc(hidden)]
pub ctx: &'a [CdtContext],
#[doc(hidden)]
pub bin: OperationBin<'a>,
#[doc(hidden)]
pub data: OperationData<'a>,
}
impl<'a> Operation<'a> {
#[doc(hidden)]
pub fn estimate_size(&self) -> Result<usize> {
let mut size: usize = 0;
size += match self.bin {
OperationBin::Name(bin) => bin.len(),
OperationBin::None | OperationBin::All => 0,
};
size += match self.data {
OperationData::None => 0,
OperationData::Value(value) => value.estimate_size()?,
OperationData::EXPOp(ref exp_op) => exp_op.estimate_size()?,
OperationData::CdtListOp(ref cdt_op)
| OperationData::CdtMapOp(ref cdt_op)
| OperationData::CdtBitOp(ref cdt_op)
| OperationData::HLLOp(ref cdt_op) => cdt_op.estimate_size(self.ctx)?,
};
Ok(size)
}
#[doc(hidden)]
pub fn write_to(&self, buffer: &mut Buffer) -> Result<usize> {
let mut size: usize = 0;
let op_size = self.estimate_size()?;
size += buffer.write_u32(op_size as u32 + 4)?;
size += buffer.write_u8(self.op as u8)?;
match self.data {
OperationData::None => {
size += self.write_op_header_to(buffer, ParticleType::NULL as u8)?;
}
OperationData::Value(value) => {
size += self.write_op_header_to(buffer, value.particle_type() as u8)?;
size += value.write_to(buffer)?;
}
OperationData::CdtListOp(ref cdt_op)
| OperationData::CdtMapOp(ref cdt_op)
| OperationData::CdtBitOp(ref cdt_op)
| OperationData::HLLOp(ref cdt_op) => {
size += self.write_op_header_to(buffer, cdt_op.particle_type() as u8)?;
size += cdt_op.write_to(buffer, self.ctx)?;
}
OperationData::EXPOp(ref exp) => {
size += self.write_op_header_to(buffer, ParticleType::BLOB as u8)?;
size += exp.write_to(buffer)?;
}
};
Ok(size)
}
#[doc(hidden)]
fn write_op_header_to(&self, buffer: &mut Buffer, particle_type: u8) -> Result<usize> {
let mut size = buffer.write_u8(particle_type as u8)?;
size += buffer.write_u8(0)?;
match self.bin {
OperationBin::Name(bin) => {
size += buffer.write_u8(bin.len() as u8)?;
size += buffer.write_str(bin)?;
}
OperationBin::None | OperationBin::All => {
size += buffer.write_u8(0)?;
}
}
Ok(size)
}
pub const fn set_context(mut self, ctx: &'a [CdtContext]) -> Operation<'a> {
self.ctx = ctx;
self
}
}