velesdb_core/collection/core/
index_management.rs1use crate::collection::types::Collection;
4use crate::error::Result;
5use crate::index::{JsonValue, SecondaryIndex};
6use parking_lot::RwLock;
7use std::collections::BTreeMap;
8
9#[derive(Debug, Clone)]
11pub struct IndexInfo {
12 pub label: String,
14 pub property: String,
16 pub index_type: String,
18 pub cardinality: usize,
20 pub memory_bytes: usize,
22}
23
24impl Collection {
25 pub fn create_index(&self, field_name: &str) -> Result<()> {
31 let mut indexes = self.secondary_indexes.write();
32 indexes
33 .entry(field_name.to_string())
34 .or_insert_with(|| SecondaryIndex::BTree(RwLock::new(BTreeMap::new())));
35 Ok(())
36 }
37
38 #[must_use]
40 pub fn has_secondary_index(&self, field_name: &str) -> bool {
41 self.secondary_indexes.read().contains_key(field_name)
42 }
43
44 #[must_use]
46 pub fn secondary_index_lookup(&self, field_name: &str, value: &JsonValue) -> Option<Vec<u64>> {
47 let indexes = self.secondary_indexes.read();
48 let index = indexes.get(field_name)?;
49 match index {
50 SecondaryIndex::BTree(tree) => tree.read().get(value).cloned(),
51 }
52 }
53
54 pub fn create_property_index(&self, label: &str, property: &str) -> Result<()> {
65 let mut index = self.property_index.write();
66 index.create_index(label, property);
67 Ok(())
68 }
69
70 pub fn create_range_index(&self, label: &str, property: &str) -> Result<()> {
81 let mut index = self.range_index.write();
82 index.create_index(label, property);
83 Ok(())
84 }
85
86 #[must_use]
88 pub fn has_property_index(&self, label: &str, property: &str) -> bool {
89 self.property_index.read().has_index(label, property)
90 }
91
92 #[must_use]
94 pub fn has_range_index(&self, label: &str, property: &str) -> bool {
95 self.range_index.read().has_index(label, property)
96 }
97
98 #[must_use]
100 pub fn list_indexes(&self) -> Vec<IndexInfo> {
101 let mut indexes = Vec::new();
102
103 let prop_index = self.property_index.read();
106 for (label, property) in prop_index.indexed_properties() {
107 let cardinality = prop_index.cardinality(&label, &property).unwrap_or(0);
108 indexes.push(IndexInfo {
109 label,
110 property,
111 index_type: "hash".to_string(),
112 cardinality,
113 memory_bytes: 0, });
115 }
116
117 let range_idx = self.range_index.read();
119 for (label, property) in range_idx.indexed_properties() {
120 indexes.push(IndexInfo {
121 label,
122 property,
123 index_type: "range".to_string(),
124 cardinality: 0, memory_bytes: 0,
126 });
127 }
128
129 indexes
130 }
131
132 pub fn drop_index(&self, label: &str, property: &str) -> Result<bool> {
147 let dropped_prop = self.property_index.write().drop_index(label, property);
149 if dropped_prop {
150 return Ok(true);
151 }
152
153 let dropped_range = self.range_index.write().drop_index(label, property);
155 Ok(dropped_range)
156 }
157
158 #[must_use]
160 pub fn indexes_memory_usage(&self) -> usize {
161 let prop_mem = self.property_index.read().memory_usage();
164 let range_mem = self.range_index.read().memory_usage();
165 prop_mem + range_mem
166 }
167}