Skip to main content

icydb_core/model/
index.rs

1//! Module: model::index
2//! Responsibility: module-local ownership and contracts for model::index.
3//! Does not own: cross-module orchestration outside this module.
4//! Boundary: exposes this module API while keeping implementation details internal.
5
6use std::fmt::{self, Display};
7
8///
9/// IndexModel
10///
11/// Runtime-only descriptor for an index used by the executor and stores.
12/// Keeps core decoupled from the schema `Index` shape.
13/// Indexing is hash-based over `Value` equality for all variants.
14/// Unique indexes enforce value equality; hash collisions surface as corruption.
15///
16
17#[derive(Clone, Copy, Debug, Eq, PartialEq)]
18pub struct IndexModel {
19    /// Stable index name used for diagnostics and planner identity.
20    name: &'static str,
21    store: &'static str,
22    fields: &'static [&'static str],
23    unique: bool,
24}
25
26impl IndexModel {
27    #[must_use]
28    pub const fn new(
29        name: &'static str,
30        store: &'static str,
31        fields: &'static [&'static str],
32        unique: bool,
33    ) -> Self {
34        Self {
35            name,
36            store,
37            fields,
38            unique,
39        }
40    }
41
42    /// Return the stable index name.
43    #[must_use]
44    pub const fn name(&self) -> &'static str {
45        self.name
46    }
47
48    /// Return the backing index store path.
49    #[must_use]
50    pub const fn store(&self) -> &'static str {
51        self.store
52    }
53
54    /// Return the canonical index field list.
55    #[must_use]
56    pub const fn fields(&self) -> &'static [&'static str] {
57        self.fields
58    }
59
60    /// Return whether the index enforces value uniqueness.
61    #[must_use]
62    pub const fn is_unique(&self) -> bool {
63        self.unique
64    }
65
66    /// Whether this index's field prefix matches the start of another index.
67    #[must_use]
68    pub fn is_prefix_of(&self, other: &Self) -> bool {
69        self.fields().len() < other.fields().len() && other.fields().starts_with(self.fields())
70    }
71}
72
73impl Display for IndexModel {
74    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
75        let fields = self.fields().join(", ");
76
77        if self.is_unique() {
78            write!(f, "{}: UNIQUE {}({})", self.name(), self.store(), fields)
79        } else {
80            write!(f, "{}: {}({})", self.name(), self.store(), fields)
81        }
82    }
83}