1#[derive(Debug, Clone, PartialEq, Eq, Hash)]
10pub enum QuoteStyle {
11 None,
13 DoubleQuotes,
15 Brackets,
17}
18
19#[derive(Debug, Clone, PartialEq, Eq, Hash)]
21pub struct ColumnRef {
22 pub name: String,
23 pub quote_style: QuoteStyle,
24}
25
26impl ColumnRef {
27 pub fn unquoted(name: String) -> Self {
29 Self {
30 name,
31 quote_style: QuoteStyle::None,
32 }
33 }
34
35 pub fn quoted(name: String) -> Self {
37 Self {
38 name,
39 quote_style: QuoteStyle::DoubleQuotes,
40 }
41 }
42
43 pub fn bracketed(name: String) -> Self {
45 Self {
46 name,
47 quote_style: QuoteStyle::Brackets,
48 }
49 }
50
51 pub fn to_sql(&self) -> String {
53 match self.quote_style {
54 QuoteStyle::None => self.name.clone(),
55 QuoteStyle::DoubleQuotes => format!("\"{}\"", self.name),
56 QuoteStyle::Brackets => format!("[{}]", self.name),
57 }
58 }
59}
60
61impl PartialEq<str> for ColumnRef {
62 fn eq(&self, other: &str) -> bool {
63 self.name == other
64 }
65}
66
67impl PartialEq<&str> for ColumnRef {
68 fn eq(&self, other: &&str) -> bool {
69 self.name == *other
70 }
71}
72
73impl std::fmt::Display for ColumnRef {
74 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
75 write!(f, "{}", self.to_sql())
76 }
77}
78
79#[derive(Debug, Clone)]
80pub enum SqlExpression {
81 Column(ColumnRef),
82 StringLiteral(String),
83 NumberLiteral(String),
84 BooleanLiteral(bool),
85 Null, DateTimeConstructor {
87 year: i32,
88 month: u32,
89 day: u32,
90 hour: Option<u32>,
91 minute: Option<u32>,
92 second: Option<u32>,
93 },
94 DateTimeToday {
95 hour: Option<u32>,
96 minute: Option<u32>,
97 second: Option<u32>,
98 },
99 MethodCall {
100 object: String,
101 method: String,
102 args: Vec<SqlExpression>,
103 },
104 ChainedMethodCall {
105 base: Box<SqlExpression>,
106 method: String,
107 args: Vec<SqlExpression>,
108 },
109 FunctionCall {
110 name: String,
111 args: Vec<SqlExpression>,
112 distinct: bool, },
114 WindowFunction {
115 name: String,
116 args: Vec<SqlExpression>,
117 window_spec: WindowSpec,
118 },
119 BinaryOp {
120 left: Box<SqlExpression>,
121 op: String,
122 right: Box<SqlExpression>,
123 },
124 InList {
125 expr: Box<SqlExpression>,
126 values: Vec<SqlExpression>,
127 },
128 NotInList {
129 expr: Box<SqlExpression>,
130 values: Vec<SqlExpression>,
131 },
132 Between {
133 expr: Box<SqlExpression>,
134 lower: Box<SqlExpression>,
135 upper: Box<SqlExpression>,
136 },
137 Not {
138 expr: Box<SqlExpression>,
139 },
140 CaseExpression {
141 when_branches: Vec<WhenBranch>,
142 else_branch: Option<Box<SqlExpression>>,
143 },
144 SimpleCaseExpression {
145 expr: Box<SqlExpression>,
146 when_branches: Vec<SimpleWhenBranch>,
147 else_branch: Option<Box<SqlExpression>>,
148 },
149 ScalarSubquery {
152 query: Box<SelectStatement>,
153 },
154 InSubquery {
157 expr: Box<SqlExpression>,
158 subquery: Box<SelectStatement>,
159 },
160 NotInSubquery {
163 expr: Box<SqlExpression>,
164 subquery: Box<SelectStatement>,
165 },
166}
167
168#[derive(Debug, Clone)]
169pub struct WhenBranch {
170 pub condition: Box<SqlExpression>,
171 pub result: Box<SqlExpression>,
172}
173
174#[derive(Debug, Clone)]
175pub struct SimpleWhenBranch {
176 pub value: Box<SqlExpression>,
177 pub result: Box<SqlExpression>,
178}
179
180#[derive(Debug, Clone)]
183pub struct WhereClause {
184 pub conditions: Vec<Condition>,
185}
186
187#[derive(Debug, Clone)]
188pub struct Condition {
189 pub expr: SqlExpression,
190 pub connector: Option<LogicalOp>, }
192
193#[derive(Debug, Clone)]
194pub enum LogicalOp {
195 And,
196 Or,
197}
198
199#[derive(Debug, Clone, PartialEq)]
202pub enum SortDirection {
203 Asc,
204 Desc,
205}
206
207#[derive(Debug, Clone)]
208pub struct OrderByColumn {
209 pub column: String,
210 pub direction: SortDirection,
211}
212
213#[derive(Debug, Clone, PartialEq)]
217pub enum FrameBound {
218 UnboundedPreceding,
219 CurrentRow,
220 Preceding(i64),
221 Following(i64),
222 UnboundedFollowing,
223}
224
225#[derive(Debug, Clone, PartialEq)]
227pub enum FrameUnit {
228 Rows,
229 Range,
230}
231
232#[derive(Debug, Clone)]
234pub struct WindowFrame {
235 pub unit: FrameUnit,
236 pub start: FrameBound,
237 pub end: Option<FrameBound>, }
239
240#[derive(Debug, Clone)]
241pub struct WindowSpec {
242 pub partition_by: Vec<String>,
243 pub order_by: Vec<OrderByColumn>,
244 pub frame: Option<WindowFrame>, }
246
247#[derive(Debug, Clone)]
251pub enum SelectItem {
252 Column(ColumnRef),
254 Expression { expr: SqlExpression, alias: String },
256 Star,
258}
259
260#[derive(Debug, Clone)]
261pub struct SelectStatement {
262 pub distinct: bool, pub columns: Vec<String>, pub select_items: Vec<SelectItem>, pub from_table: Option<String>,
266 pub from_subquery: Option<Box<SelectStatement>>, pub from_function: Option<TableFunction>, pub from_alias: Option<String>, pub joins: Vec<JoinClause>, pub where_clause: Option<WhereClause>,
271 pub order_by: Option<Vec<OrderByColumn>>,
272 pub group_by: Option<Vec<SqlExpression>>, pub having: Option<SqlExpression>, pub limit: Option<usize>,
275 pub offset: Option<usize>,
276 pub ctes: Vec<CTE>, }
278
279#[derive(Debug, Clone)]
283pub enum TableFunction {
284 Range {
285 start: SqlExpression,
286 end: SqlExpression,
287 step: Option<SqlExpression>,
288 },
289 Split {
290 text: SqlExpression,
291 delimiter: Option<SqlExpression>,
292 },
293 Generator {
294 name: String,
295 args: Vec<SqlExpression>,
296 },
297}
298
299#[derive(Debug, Clone)]
301pub struct CTE {
302 pub name: String,
303 pub column_list: Option<Vec<String>>, pub cte_type: CTEType,
305}
306
307#[derive(Debug, Clone)]
309pub enum CTEType {
310 Standard(SelectStatement),
311 Web(WebCTESpec),
312}
313
314#[derive(Debug, Clone)]
316pub struct WebCTESpec {
317 pub url: String,
318 pub format: Option<DataFormat>, pub headers: Vec<(String, String)>, pub cache_seconds: Option<u64>, }
322
323#[derive(Debug, Clone)]
325pub enum DataFormat {
326 CSV,
327 JSON,
328 Auto, }
330
331#[derive(Debug, Clone)]
333pub enum TableSource {
334 Table(String), DerivedTable {
336 query: Box<SelectStatement>,
338 alias: String, },
340}
341
342#[derive(Debug, Clone, PartialEq)]
344pub enum JoinType {
345 Inner,
346 Left,
347 Right,
348 Full,
349 Cross,
350}
351
352#[derive(Debug, Clone, PartialEq)]
354pub enum JoinOperator {
355 Equal,
356 NotEqual,
357 LessThan,
358 GreaterThan,
359 LessThanOrEqual,
360 GreaterThanOrEqual,
361}
362
363#[derive(Debug, Clone)]
365pub struct JoinCondition {
366 pub left_column: String, pub operator: JoinOperator, pub right_column: String, }
370
371#[derive(Debug, Clone)]
373pub struct JoinClause {
374 pub join_type: JoinType,
375 pub table: TableSource, pub alias: Option<String>, pub condition: JoinCondition, }