Skip to main content

qail_core/ast/
operators.rs

1use serde::{Deserialize, Serialize};
2
3/// The action type (SQL operation).
4#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
5pub enum Action {
6    Get,
7    Cnt,
8    Set,
9    Del,
10    Add,
11    Gen,
12    Make,
13    Drop,
14    Mod,
15    Over,
16    With,
17    Index,
18    DropIndex,
19    Alter,
20    AlterDrop,
21    AlterType,
22    TxnStart,
23    TxnCommit,
24    TxnRollback,
25    Put,
26    DropCol,
27    RenameCol,
28    JsonTable,
29    Export,
30    Truncate,
31    Explain,
32    ExplainAnalyze,
33    Lock,
34    CreateMaterializedView,
35    RefreshMaterializedView,
36    DropMaterializedView,
37    Listen,
38    Notify,
39    Unlisten,
40    Savepoint,
41    ReleaseSavepoint,
42    RollbackToSavepoint,
43    CreateView,
44    DropView,
45    Search,
46    Upsert,
47    Scroll,
48    CreateCollection,
49    DeleteCollection,
50    CreateFunction,
51    DropFunction,
52    CreateTrigger,
53    DropTrigger,
54    RedisGet,
55    RedisSet,
56    RedisDel,
57    RedisIncr,
58    RedisDecr,
59    RedisTtl,
60    RedisExpire,
61    RedisExists,
62    RedisMGet,
63    RedisMSet,
64    RedisPing,
65    CreateExtension,
66    DropExtension,
67    CommentOn,
68    CreateSequence,
69    DropSequence,
70    CreateEnum,
71    DropEnum,
72    AlterEnumAddValue,
73    AlterSetNotNull,
74    AlterDropNotNull,
75    AlterSetDefault,
76    AlterDropDefault,
77    AlterEnableRls,
78    AlterDisableRls,
79    AlterForceRls,
80    AlterNoForceRls,
81}
82
83impl std::fmt::Display for Action {
84    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
85        match self {
86            Action::Get => write!(f, "GET"),
87            Action::Cnt => write!(f, "CNT"),
88            Action::Set => write!(f, "SET"),
89            Action::Del => write!(f, "DEL"),
90            Action::Add => write!(f, "ADD"),
91            Action::Gen => write!(f, "GEN"),
92            Action::Make => write!(f, "MAKE"),
93            Action::Drop => write!(f, "DROP"),
94            Action::Mod => write!(f, "MOD"),
95            Action::Over => write!(f, "OVER"),
96            Action::With => write!(f, "WITH"),
97            Action::Index => write!(f, "INDEX"),
98            Action::DropIndex => write!(f, "DROP_INDEX"),
99            Action::Alter => write!(f, "ALTER"),
100            Action::AlterDrop => write!(f, "ALTER_DROP"),
101            Action::AlterType => write!(f, "ALTER_TYPE"),
102            Action::TxnStart => write!(f, "TXN_START"),
103            Action::TxnCommit => write!(f, "TXN_COMMIT"),
104            Action::TxnRollback => write!(f, "TXN_ROLLBACK"),
105            Action::Put => write!(f, "PUT"),
106            Action::DropCol => write!(f, "DROP_COL"),
107            Action::RenameCol => write!(f, "RENAME_COL"),
108            Action::JsonTable => write!(f, "JSON_TABLE"),
109            Action::Export => write!(f, "EXPORT"),
110            Action::Truncate => write!(f, "TRUNCATE"),
111            Action::Explain => write!(f, "EXPLAIN"),
112            Action::ExplainAnalyze => write!(f, "EXPLAIN_ANALYZE"),
113            Action::Lock => write!(f, "LOCK"),
114            Action::CreateMaterializedView => write!(f, "CREATE_MATERIALIZED_VIEW"),
115            Action::RefreshMaterializedView => write!(f, "REFRESH_MATERIALIZED_VIEW"),
116            Action::DropMaterializedView => write!(f, "DROP_MATERIALIZED_VIEW"),
117            Action::Listen => write!(f, "LISTEN"),
118            Action::Notify => write!(f, "NOTIFY"),
119            Action::Unlisten => write!(f, "UNLISTEN"),
120            Action::Savepoint => write!(f, "SAVEPOINT"),
121            Action::ReleaseSavepoint => write!(f, "RELEASE_SAVEPOINT"),
122            Action::RollbackToSavepoint => write!(f, "ROLLBACK_TO_SAVEPOINT"),
123            Action::CreateView => write!(f, "CREATE_VIEW"),
124            Action::DropView => write!(f, "DROP_VIEW"),
125            Action::Search => write!(f, "SEARCH"),
126            Action::Upsert => write!(f, "UPSERT"),
127            Action::Scroll => write!(f, "SCROLL"),
128            Action::CreateCollection => write!(f, "CREATE_COLLECTION"),
129            Action::DeleteCollection => write!(f, "DELETE_COLLECTION"),
130            Action::CreateFunction => write!(f, "CREATE_FUNCTION"),
131            Action::DropFunction => write!(f, "DROP_FUNCTION"),
132            Action::CreateTrigger => write!(f, "CREATE_TRIGGER"),
133            Action::DropTrigger => write!(f, "DROP_TRIGGER"),
134            Action::RedisGet => write!(f, "REDIS_GET"),
135            Action::RedisSet => write!(f, "REDIS_SET"),
136            Action::RedisDel => write!(f, "REDIS_DEL"),
137            Action::RedisIncr => write!(f, "REDIS_INCR"),
138            Action::RedisDecr => write!(f, "REDIS_DECR"),
139            Action::RedisTtl => write!(f, "REDIS_TTL"),
140            Action::RedisExpire => write!(f, "REDIS_EXPIRE"),
141            Action::RedisExists => write!(f, "REDIS_EXISTS"),
142            Action::RedisMGet => write!(f, "REDIS_MGET"),
143            Action::RedisMSet => write!(f, "REDIS_MSET"),
144            Action::RedisPing => write!(f, "REDIS_PING"),
145            Action::CreateExtension => write!(f, "CREATE_EXTENSION"),
146            Action::DropExtension => write!(f, "DROP_EXTENSION"),
147            Action::CommentOn => write!(f, "COMMENT_ON"),
148            Action::CreateSequence => write!(f, "CREATE_SEQUENCE"),
149            Action::DropSequence => write!(f, "DROP_SEQUENCE"),
150            Action::CreateEnum => write!(f, "CREATE_ENUM"),
151            Action::DropEnum => write!(f, "DROP_ENUM"),
152            Action::AlterEnumAddValue => write!(f, "ALTER_ENUM_ADD_VALUE"),
153            Action::AlterSetNotNull => write!(f, "ALTER_SET_NOT_NULL"),
154            Action::AlterDropNotNull => write!(f, "ALTER_DROP_NOT_NULL"),
155            Action::AlterSetDefault => write!(f, "ALTER_SET_DEFAULT"),
156            Action::AlterDropDefault => write!(f, "ALTER_DROP_DEFAULT"),
157            Action::AlterEnableRls => write!(f, "ALTER_ENABLE_RLS"),
158            Action::AlterDisableRls => write!(f, "ALTER_DISABLE_RLS"),
159            Action::AlterForceRls => write!(f, "ALTER_FORCE_RLS"),
160            Action::AlterNoForceRls => write!(f, "ALTER_NO_FORCE_RLS"),
161        }
162    }
163}
164
165/// Logical operator between conditions.
166#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize, Default)]
167pub enum LogicalOp {
168    #[default]
169    And,
170    Or,
171}
172
173#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
174pub enum SortOrder {
175    Asc,
176    Desc,
177    AscNullsFirst,
178    AscNullsLast,
179    DescNullsFirst,
180    DescNullsLast,
181}
182
183#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
184pub enum Operator {
185    Eq,
186    Ne,
187    Gt,
188    Gte,
189    Lt,
190    Lte,
191    Fuzzy,
192    In,
193    NotIn,
194    IsNull,
195    IsNotNull,
196    Contains,
197    KeyExists,
198    JsonExists,
199    JsonQuery,
200    JsonValue,
201    Like,
202    NotLike,
203    ILike,
204    NotILike,
205    Between,
206    NotBetween,
207    Exists,
208    NotExists,
209    Regex,
210    RegexI,
211    SimilarTo,
212    ContainedBy,
213    Overlaps,
214}
215
216impl Operator {
217    /// For simple operators, returns the symbol directly.
218    /// For complex operators (BETWEEN, EXISTS), returns the keyword.
219    pub fn sql_symbol(&self) -> &'static str {
220        match self {
221            Operator::Eq => "=",
222            Operator::Ne => "!=",
223            Operator::Gt => ">",
224            Operator::Gte => ">=",
225            Operator::Lt => "<",
226            Operator::Lte => "<=",
227            Operator::Fuzzy => "ILIKE",
228            Operator::In => "IN",
229            Operator::NotIn => "NOT IN",
230            Operator::IsNull => "IS NULL",
231            Operator::IsNotNull => "IS NOT NULL",
232            Operator::Contains => "@>",
233            Operator::KeyExists => "?",
234            Operator::JsonExists => "JSON_EXISTS",
235            Operator::JsonQuery => "JSON_QUERY",
236            Operator::JsonValue => "JSON_VALUE",
237            Operator::Like => "LIKE",
238            Operator::NotLike => "NOT LIKE",
239            Operator::ILike => "ILIKE",
240            Operator::NotILike => "NOT ILIKE",
241            Operator::Between => "BETWEEN",
242            Operator::NotBetween => "NOT BETWEEN",
243            Operator::Exists => "EXISTS",
244            Operator::NotExists => "NOT EXISTS",
245            Operator::Regex => "~",
246            Operator::RegexI => "~*",
247            Operator::SimilarTo => "SIMILAR TO",
248            Operator::ContainedBy => "<@",
249            Operator::Overlaps => "&&",
250        }
251    }
252
253    /// IS NULL, IS NOT NULL, EXISTS, NOT EXISTS don't need values.
254    pub fn needs_value(&self) -> bool {
255        !matches!(
256            self,
257            Operator::IsNull | Operator::IsNotNull | Operator::Exists | Operator::NotExists
258        )
259    }
260
261    pub fn is_simple_binary(&self) -> bool {
262        matches!(
263            self,
264            Operator::Eq
265                | Operator::Ne
266                | Operator::Gt
267                | Operator::Gte
268                | Operator::Lt
269                | Operator::Lte
270                | Operator::Like
271                | Operator::NotLike
272                | Operator::ILike
273                | Operator::NotILike
274        )
275    }
276}
277
278#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
279pub enum AggregateFunc {
280    Count,
281    Sum,
282    Avg,
283    Min,
284    Max,
285    ArrayAgg,
286    StringAgg,
287    JsonAgg,
288    JsonbAgg,
289    BoolAnd,
290    BoolOr,
291}
292
293impl std::fmt::Display for AggregateFunc {
294    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
295        match self {
296            AggregateFunc::Count => write!(f, "COUNT"),
297            AggregateFunc::Sum => write!(f, "SUM"),
298            AggregateFunc::Avg => write!(f, "AVG"),
299            AggregateFunc::Min => write!(f, "MIN"),
300            AggregateFunc::Max => write!(f, "MAX"),
301            AggregateFunc::ArrayAgg => write!(f, "ARRAY_AGG"),
302            AggregateFunc::StringAgg => write!(f, "STRING_AGG"),
303            AggregateFunc::JsonAgg => write!(f, "JSON_AGG"),
304            AggregateFunc::JsonbAgg => write!(f, "JSONB_AGG"),
305            AggregateFunc::BoolAnd => write!(f, "BOOL_AND"),
306            AggregateFunc::BoolOr => write!(f, "BOOL_OR"),
307        }
308    }
309}
310
311/// Join Type
312#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
313pub enum JoinKind {
314    Inner,
315    Left,
316    Right,
317    Lateral,
318    Full,
319    Cross,
320}
321
322/// Set operation type for combining queries
323#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
324pub enum SetOp {
325    Union,
326    UnionAll,
327    Intersect,
328    Except,
329}
330
331#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
332pub enum ModKind {
333    Add,
334    Drop,
335}
336
337/// GROUP BY mode for advanced aggregations
338#[derive(Debug, Clone, PartialEq, Eq, Default, Serialize, Deserialize)]
339pub enum GroupByMode {
340    #[default]
341    Simple,
342    Rollup,
343    Cube,
344    GroupingSets(Vec<Vec<String>>),
345}
346
347impl GroupByMode {
348    /// Check if this is the default Simple mode (for serde skip)
349    pub fn is_simple(&self) -> bool {
350        matches!(self, GroupByMode::Simple)
351    }
352}
353
354/// Row locking mode for SELECT...FOR UPDATE/SHARE
355#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
356pub enum LockMode {
357    Update,
358    NoKeyUpdate,
359    Share,
360    KeyShare,
361}
362
363/// OVERRIDING clause for INSERT with GENERATED columns
364#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
365pub enum OverridingKind {
366    SystemValue,
367    UserValue,
368}
369
370/// TABLESAMPLE sampling method
371#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
372pub enum SampleMethod {
373    Bernoulli,
374    System,
375}
376
377/// Distance metric for vector similarity
378#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize, Default)]
379pub enum Distance {
380    #[default]
381    Cosine,
382    Euclid,
383    Dot,
384}