database_reflection/reflection/
table.rs1use crate::metadata::consts::{METADATA_CHARSET, METADATA_COLLATION, METADATA_FLAG_PRIMARY};
2use crate::metadata::WithMetadata;
3use crate::reflection::column::Column;
4use crate::reflection::index::Index;
5use indexmap::IndexMap;
6use serde::{Deserialize, Serialize};
7use std::collections::HashMap;
8use std::slice::Iter;
9use std::sync::Arc;
10
11#[derive(Clone, Default, Debug, Serialize, Deserialize)]
12pub struct Table {
13 name: Arc<String>,
14 primary_key: Vec<Arc<String>>,
15 columns: IndexMap<Arc<String>, Arc<Column>>,
16 indexes: IndexMap<Arc<String>, Index>,
17 metadata: HashMap<String, String>,
18}
19
20impl WithMetadata for Table {
21 fn get_metadata(&self) -> &HashMap<String, String> {
23 &self.metadata
24 }
25
26 fn get_metadata_mut(&mut self) -> &mut HashMap<String, String> {
28 &mut self.metadata
29 }
30}
31
32impl Table {
33 pub fn new(name: impl ToString) -> Table {
35 Table {
36 name: Arc::new(name.to_string()),
37 ..Default::default()
38 }
39 }
40
41 pub fn name(&self) -> Arc<String> {
43 self.name.clone()
44 }
45
46 pub fn set_column(&mut self, mut column: Column) -> &mut Table {
48 if column.datatype().is_text()
49 && column.meta(METADATA_CHARSET).is_none()
50 && column.meta(METADATA_COLLATION).is_none()
51 && self.meta(METADATA_CHARSET).is_some()
52 && self.meta(METADATA_COLLATION).is_some()
53 {
54 column
55 .set_meta(
56 METADATA_CHARSET,
57 self.meta(METADATA_CHARSET).unwrap_or_default(),
58 )
59 .set_meta(
60 METADATA_COLLATION,
61 self.meta(METADATA_COLLATION).unwrap_or_default(),
62 );
63 }
64
65 if column.meta_flag(METADATA_FLAG_PRIMARY) && !self.primary_key.contains(&column.name()) {
66 self.primary_key.push(column.name());
67 }
68
69 self.columns.insert(column.name(), Arc::new(column));
70
71 self
72 }
73
74 pub fn column(&self, key: &str) -> Option<Arc<Column>> {
76 self.columns.get(&key.to_string()).cloned()
77 }
78
79 pub fn columns(&self) -> indexmap::map::Iter<'_, Arc<String>, Arc<Column>> {
81 self.columns.iter()
82 }
83
84 pub fn set_index(&mut self, index: Index) -> &mut Table {
86 if index.primary() && !self.primary_key.contains(&index.column().name()) {
87 self.primary_key.push(index.column().name());
88 }
89
90 self.indexes.insert(index.name(), index);
91
92 self
93 }
94
95 pub fn index(&self, key: &str) -> Option<&Index> {
97 self.indexes.get(&key.to_string())
98 }
99
100 pub fn index_by_column_name(&self, column_name: Arc<String>) -> Option<Index> {
102 self.indexes
103 .iter()
104 .find(|(_, c)| c.column().name() == column_name)
105 .map(|(_, c)| c.clone())
106 }
107
108 pub fn index_by_column(&self, column: &Column) -> Option<Index> {
110 self.indexes
111 .iter()
112 .find(|(_, c)| c.column() == column)
113 .map(|(_, c)| c.clone())
114 }
115
116 pub fn indexes(&self) -> indexmap::map::Iter<'_, Arc<String>, Index> {
118 self.indexes.iter()
119 }
120
121 pub fn primary_key_count(&self) -> usize {
123 self.primary_key.len()
124 }
125
126 pub fn primary_key(&self) -> Option<Arc<String>> {
128 self.primary_key.first().cloned()
129 }
130
131 pub fn primary_key_column(&self) -> Option<Arc<Column>> {
133 self.primary_key
134 .first()
135 .map(|k| self.columns.get(k).cloned())
136 .unwrap()
137 }
138
139 pub fn primary_keys(&self) -> Iter<'_, Arc<String>> {
141 self.primary_key.iter()
142 }
143
144 pub fn primary_key_columns(&self) -> Vec<Arc<Column>> {
146 self.columns
147 .iter()
148 .filter(|kv| self.primary_key.contains(kv.0))
149 .map(|kv| kv.1.clone())
150 .collect::<Vec<Arc<Column>>>()
151 }
152}