databend_common_ast/ast/statements/
index.rs1use std::collections::BTreeMap;
16use std::fmt::Display;
17use std::fmt::Formatter;
18
19use derive_visitor::Drive;
20use derive_visitor::DriveMut;
21
22use crate::ast::CreateOption;
23use crate::ast::Identifier;
24use crate::ast::Query;
25use crate::ast::write_comma_separated_list;
26use crate::ast::write_dot_separated_list;
27use crate::ast::write_space_separated_string_map;
28
29#[derive(Debug, Clone, PartialEq, Drive, DriveMut)]
30pub struct CreateIndexStmt {
31 pub index_type: TableIndexType,
32 pub create_option: CreateOption,
33
34 pub index_name: Identifier,
35
36 pub query: Box<Query>,
37 pub sync_creation: bool,
38}
39
40#[derive(Debug, Copy, Clone, PartialEq, Eq, Drive, DriveMut)]
41pub enum TableIndexType {
42 Aggregating,
43 Inverted,
45 Ngram,
46 Vector,
47 Spatial,
48}
49
50impl Display for TableIndexType {
51 fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
52 match self {
53 TableIndexType::Aggregating => {
54 write!(f, "AGGREGATING")
55 }
56 TableIndexType::Inverted => {
57 write!(f, "INVERTED")
58 }
59 TableIndexType::Ngram => {
60 write!(f, "NGRAM")
61 }
62 TableIndexType::Vector => {
63 write!(f, "VECTOR")
64 }
65 TableIndexType::Spatial => {
66 write!(f, "SPATIAL")
67 }
68 }
69 }
70}
71
72impl Display for CreateIndexStmt {
73 fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
74 write!(f, "CREATE ")?;
75 if let CreateOption::CreateOrReplace = self.create_option {
76 write!(f, "OR REPLACE ")?;
77 }
78 if !self.sync_creation {
79 write!(f, "ASYNC ")?;
80 }
81 write!(f, "{} INDEX", self.index_type)?;
82 if let CreateOption::CreateIfNotExists = self.create_option {
83 write!(f, " IF NOT EXISTS")?;
84 }
85
86 write!(f, " {}", self.index_name)?;
87 write!(f, " AS {}", self.query)
88 }
89}
90
91#[derive(Debug, Clone, PartialEq, Drive, DriveMut)]
92pub struct DropIndexStmt {
93 pub if_exists: bool,
94 pub index: Identifier,
95}
96
97impl Display for DropIndexStmt {
98 fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
99 write!(f, "DROP AGGREGATING INDEX")?;
100 if self.if_exists {
101 write!(f, " IF EXISTS")?;
102 }
103
104 write!(f, " {index}", index = self.index)?;
105 Ok(())
106 }
107}
108
109#[derive(Debug, Clone, PartialEq, Drive, DriveMut)]
110pub struct RefreshIndexStmt {
111 pub index: Identifier,
112 pub limit: Option<u64>,
113}
114
115impl Display for RefreshIndexStmt {
116 fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
117 write!(f, "REFRESH AGGREGATING INDEX {index}", index = self.index)?;
118 if let Some(limit) = self.limit {
119 write!(f, " LIMIT {limit}")?;
120 }
121 Ok(())
122 }
123}
124
125#[derive(Debug, Clone, PartialEq, Drive, DriveMut)]
126pub struct CreateTableIndexStmt {
127 pub create_option: CreateOption,
128
129 pub index_name: Identifier,
130 pub index_type: TableIndexType,
131
132 pub catalog: Option<Identifier>,
133 pub database: Option<Identifier>,
134 pub table: Identifier,
135
136 pub columns: Vec<Identifier>,
137 pub sync_creation: bool,
138 pub index_options: BTreeMap<String, String>,
139}
140
141impl Display for CreateTableIndexStmt {
142 fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
143 write!(f, "CREATE ")?;
144 if let CreateOption::CreateOrReplace = self.create_option {
145 write!(f, "OR REPLACE ")?;
146 }
147 if !self.sync_creation {
148 write!(f, "ASYNC ")?;
149 }
150 write!(f, "{} INDEX", self.index_type)?;
151 if let CreateOption::CreateIfNotExists = self.create_option {
152 write!(f, " IF NOT EXISTS")?;
153 }
154
155 write!(f, " {}", self.index_name)?;
156 write!(f, " ON ")?;
157 write_dot_separated_list(
158 f,
159 self.catalog
160 .iter()
161 .chain(&self.database)
162 .chain(Some(&self.table)),
163 )?;
164 write!(f, " (")?;
165 write_comma_separated_list(f, &self.columns)?;
166 write!(f, ")")?;
167
168 if !self.index_options.is_empty() {
169 write!(f, " ")?;
170 write_space_separated_string_map(f, &self.index_options)?;
171 }
172
173 Ok(())
174 }
175}
176
177#[derive(Debug, Clone, PartialEq, Drive, DriveMut)]
178pub struct DropTableIndexStmt {
179 pub if_exists: bool,
180 pub index_name: Identifier,
181 pub index_type: TableIndexType,
182 pub catalog: Option<Identifier>,
183 pub database: Option<Identifier>,
184 pub table: Identifier,
185}
186
187impl Display for DropTableIndexStmt {
188 fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
189 write!(f, "DROP {} INDEX", self.index_type)?;
190 if self.if_exists {
191 write!(f, " IF EXISTS")?;
192 }
193
194 write!(f, " {}", self.index_name)?;
195 write!(f, " ON ")?;
196 write_dot_separated_list(
197 f,
198 self.catalog
199 .iter()
200 .chain(&self.database)
201 .chain(Some(&self.table)),
202 )?;
203 Ok(())
204 }
205}
206
207#[derive(Debug, Clone, PartialEq, Drive, DriveMut)]
208pub struct RefreshTableIndexStmt {
209 pub index_name: Identifier,
210 pub index_type: TableIndexType,
211 pub catalog: Option<Identifier>,
212 pub database: Option<Identifier>,
213 pub table: Identifier,
214 pub limit: Option<u64>,
215}
216
217impl Display for RefreshTableIndexStmt {
218 fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
219 write!(f, "REFRESH {} INDEX", self.index_type)?;
220 write!(f, " {}", self.index_name)?;
221 write!(f, " ON ")?;
222 write_dot_separated_list(
223 f,
224 self.catalog
225 .iter()
226 .chain(&self.database)
227 .chain(Some(&self.table)),
228 )?;
229 if let Some(limit) = self.limit {
230 write!(f, " LIMIT {limit}")?;
231 }
232 Ok(())
233 }
234}