Skip to main content

icydb_core/model/
field.rs

1///
2/// EntityFieldModel
3///
4/// Runtime field metadata surfaced by macro-generated `EntityModel` values.
5///
6/// This is the smallest unit consumed by predicate validation, planning,
7/// and executor-side plan checks.
8///
9
10#[derive(Debug)]
11pub struct EntityFieldModel {
12    /// Field name as used in predicates and indexing.
13    pub name: &'static str,
14    /// Runtime type shape (no schema-layer graph nodes).
15    pub kind: EntityFieldKind,
16}
17
18///
19/// RelationStrength
20///
21/// Explicit relation intent for save-time referential integrity.
22///
23
24#[derive(Clone, Copy, Debug, Eq, PartialEq)]
25pub enum RelationStrength {
26    Strong,
27    Weak,
28}
29
30///
31/// EntityFieldKind
32///
33/// Minimal runtime type surface needed by planning, validation, and execution.
34///
35/// This is aligned with `Value` variants and intentionally lossy: it encodes
36/// only the shape required for predicate compatibility and index planning.
37///
38
39#[derive(Debug)]
40pub enum EntityFieldKind {
41    // Scalar primitives
42    Account,
43    Blob,
44    Bool,
45    Date,
46    Decimal,
47    Duration,
48    Enum,
49    E8s,
50    E18s,
51    Float32,
52    Float64,
53    Int,
54    Int128,
55    IntBig,
56    Principal,
57    Subaccount,
58    Text,
59    Timestamp,
60    Uint,
61    Uint128,
62    UintBig,
63    Ulid,
64    Unit,
65
66    /// Typed entity reference; `key_kind` reflects the referenced key type.
67    /// `strength` encodes strong vs. weak relation intent.
68    Ref {
69        /// Fully-qualified Rust type path for diagnostics.
70        target_path: &'static str,
71        /// Stable external name used in storage keys.
72        target_entity_name: &'static str,
73        /// Data store path where the target entity is persisted.
74        target_store_path: &'static str,
75        key_kind: &'static Self,
76        strength: RelationStrength,
77    },
78
79    // Collections
80    List(&'static Self),
81    Set(&'static Self),
82    Map {
83        key: &'static Self,
84        value: &'static Self,
85    },
86
87    /// Marker for fields that are not filterable or indexable.
88    Unsupported,
89}
90
91impl EntityFieldKind {
92    /// Returns `true` if this field shape is permitted in
93    /// persisted or query-visible schemas under the current
94    /// determinism policy.
95    ///
96    /// This shape-level check is structural only; query-time policy
97    /// enforcement (for example, map predicate fencing) is applied at
98    /// query construction and validation boundaries.
99    #[must_use]
100    pub const fn is_deterministic_collection_shape(&self) -> bool {
101        match self {
102            Self::Ref { key_kind, .. } => key_kind.is_deterministic_collection_shape(),
103
104            Self::List(inner) | Self::Set(inner) => inner.is_deterministic_collection_shape(),
105
106            Self::Map { key, value } => {
107                key.is_deterministic_collection_shape() && value.is_deterministic_collection_shape()
108            }
109
110            _ => true,
111        }
112    }
113}