Skip to main content

alopex_sql/executor/
memory.rs

1use alopex_core::sql::stream::ByteSized;
2
3use crate::executor::ExecutorError;
4use crate::storage::SqlValue;
5
6pub use alopex_core::sql::stream::{
7    DEFAULT_SPILL_THRESHOLD_BYTES, MemoryPolicy, MemoryTracker, SpillMetricsSink, SpillPolicy,
8};
9
10pub(crate) fn map_core_memory_error(err: alopex_core::Error) -> ExecutorError {
11    match err {
12        alopex_core::Error::MemoryLimitExceeded { limit, requested } => {
13            ExecutorError::ResourceExhausted {
14                message: format!("query memory limit exceeded: {requested} bytes (limit {limit})"),
15            }
16        }
17        other => ExecutorError::Core(other),
18    }
19}
20
21impl ByteSized for SqlValue {
22    fn estimated_bytes(&self) -> u64 {
23        match self {
24            SqlValue::Null => 0,
25            SqlValue::Integer(_) => 4,
26            SqlValue::BigInt(_) => 8,
27            SqlValue::Float(_) => 4,
28            SqlValue::Double(_) => 8,
29            SqlValue::Text(text) => text.len() as u64,
30            SqlValue::Blob(blob) => blob.len() as u64,
31            SqlValue::Boolean(_) => 1,
32            SqlValue::Timestamp(_) => 8,
33            SqlValue::Date(_) => 4,
34            SqlValue::Time(_) => 8,
35            SqlValue::Interval { .. } => 16,
36            SqlValue::Decimal(_) => 17,
37            SqlValue::Json(value) => value.as_str().len() as u64,
38            SqlValue::Vector(values) => values.len() as u64 * 4,
39            SqlValue::Array(values) => values.iter().map(ByteSized::estimated_bytes).sum(),
40            SqlValue::Map(values) => values
41                .iter()
42                .map(|(key, value)| key.estimated_bytes() + value.estimated_bytes())
43                .sum(),
44            SqlValue::Struct(values) => values
45                .iter()
46                .map(|(name, value)| name.len() as u64 + value.estimated_bytes())
47                .sum(),
48        }
49    }
50}