Skip to main content

linkrs_query/parser/core/
token.rs

1//! Token definitions for the query parser
2//!
3//! This module defines the lexical tokens used by the parser.
4
5use std::fmt;
6
7use linkrs_core::types::Position;
8
9#[derive(Debug, Clone, PartialEq)]
10pub struct Token {
11    pub kind: TokenKind,
12    pub lexeme: String,
13    pub line: usize,
14    pub column: usize,
15}
16
17impl Token {
18    pub fn new(kind: TokenKind, lexeme: String, line: usize, column: usize) -> Self {
19        Token {
20            kind,
21            lexeme,
22            line,
23            column,
24        }
25    }
26
27    pub fn position(&self) -> Position {
28        Position::new(self.line, self.column)
29    }
30}
31
32#[derive(Debug, Clone, PartialEq)]
33pub enum TokenKind {
34    Create,
35    Match,
36    Return,
37    Where,
38    Delete,
39    Detach,
40    Update,
41    Insert,
42    Upsert,
43    From,
44    To,
45    As,
46    With,
47    Yield,
48    Go,
49    Over,
50    Step,
51    Upto,
52    Limit,
53    Asc,
54    Desc,
55    Order,
56    By,
57    Skip,
58    Unwind,
59    Optional,
60    Distinct,
61    All,
62    Null,
63    Is,
64    Not,
65    And,
66    Or,
67    Xor,
68    Contains,
69    StartsWith,
70    EndsWith,
71    Case,
72    When,
73    Then,
74    Else,
75    End,
76    Union,
77    Intersect,
78    SetMinus,
79    Group,
80    Having,
81    Filter,
82    Rollup,
83    Cube,
84    Grouping,
85    Sets,
86    Between,
87    Admin,
88    Edge,
89    Edges,
90    Vertex,
91    Vertices,
92    Tag,
93    Tags,
94    Index,
95    Indexes,
96    Lookup,
97    Find,
98    Path,
99    Shortest,
100    AllShortestPaths,
101    Trail,
102    Acyclic,
103    Weighted,
104    Subgraph,
105    Both,
106    Out,
107    In,
108    Reversely,
109    Recursive,
110    No,
111    Overwrite,
112    Show,
113    Add,
114    Drop,
115    Remove,
116    Alter,
117    If,
118    Exists,
119    Subquery,
120    Change,
121    CreateUser,
122    AlterUser,
123    DropUser,
124    ChangePassword,
125    Grant,
126    Revoke,
127    On,
128    Of,
129    Get,
130    Set,
131    Host,
132    Hosts,
133    Space,
134    Spaces,
135    Sequence,
136    Sequences,
137    User,
138    Users,
139    Password,
140    Role,
141    Roles,
142    Functions,
143    Graphs,
144    Macros,
145    Locked,
146    God,
147    Dba,
148    Guest,
149    Comment,
150    Charset,
151    Collate,
152    Collation,
153    VIdType,
154    PartitionNum,
155    ReplicaFactor,
156    Rebuild,
157    Bool,
158    Int,
159    Int8,
160    Int16,
161    Int32,
162    Int64,
163    Float,
164    Double,
165    String,
166    FixedString,
167    Timestamp,
168    Date,
169    Time,
170    Datetime,
171    Serial,
172    Duration,
173    Geography,
174    Point,
175    Linestring,
176    Polygon,
177    List,
178    Map,
179    Struct,
180    Array,
181    Download,
182    HDFS,
183    UUID,
184    Configs,
185    Force,
186    Part,
187    Parts,
188    Data,
189    Leader,
190    Jobs,
191    Job,
192    Bidirect,
193    Stats,
194    Status,
195    Recover,
196    Explain,
197    Profile,
198    Analyze,
199    Format,
200    AtomicEdge,
201    Default,
202    Flush,
203    Compact,
204    Submit,
205    Ascending,
206    Descending,
207    Fetch,
208    Prop,
209    Stop,
210    Revert,
211    Use,
212    Begin,
213    Commit,
214    Rollback,
215    Savepoint,
216    Release,
217    Transaction,
218    Let,
219    Read,
220    Only,
221    Write,
222    SetList,
223    Clear,
224    Merge,
225    Values,
226    Divide,
227    Rename,
228    Local,
229    Sessions,
230    Session,
231    Sample,
232    Queries,
233    Query,
234    Kill,
235    Top,
236    Text,
237    Search,
238    KeywordVector,
239    VectorLiteral(Vec<f32>),
240    Client,
241    Clients,
242    Sign,
243    Service,
244    Count,
245    Sum,
246    Avg,
247    Min,
248    Max,
249    NotIn,
250    IsNull,
251    IsNotNull,
252    IsEmpty,
253    IsNotEmpty,
254    Outbound,
255    Inbound,
256    Source,
257    Destination,
258    Rank,
259    Input,
260    FindPath,
261    Weight,
262    Loop,
263    Walk,
264    Cycle,
265    TtlDuration,
266    TtlCol,
267    Copy,
268    Header,
269    Delimiter,
270    Csv,
271    Identifier(String),
272    StringLiteral(String),
273    IntegerLiteral(i64),
274    FloatLiteral(f64),
275    BooleanLiteral(bool),
276    Plus,
277    Minus,
278    Star,
279    Div,
280    Mod,
281    Exp,
282    Eq,
283    Assign,
284    Ne,
285    Lt,
286    Le,
287    Gt,
288    Ge,
289    Regex,
290    NotOp,
291    LParen,
292    RParen,
293    LBracket,
294    RBracket,
295    LBrace,
296    RBrace,
297    Comma,
298    Dot,
299    DotDot,
300    Colon,
301    DoubleColon,
302    Semicolon,
303    QMark,
304    Question,
305    Pipe,
306    DoublePipe,
307    Ampersand,
308    ShiftLeft,
309    ShiftRight,
310    Arrow,
311    BackArrow,
312    RightArrow,
313    LeftArrow,
314    At,
315    Dollar,
316    IdProp,
317    TypeProp,
318    SrcIdProp,
319    DstIdProp,
320    RankProp,
321    DstRef,
322    SrcRef,
323    InputRef,
324    // JSONB operators
325    ArrowRight,     // ->>
326    HashArrow,      // #>
327    HashArrowRight, // #>>
328    Eof,
329}
330
331impl fmt::Display for TokenKind {
332    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
333        match self {
334            TokenKind::Identifier(s) => write!(f, "{}", s),
335            TokenKind::StringLiteral(s) => write!(f, "\"{}\"", s),
336            TokenKind::IntegerLiteral(n) => write!(f, "{}", n),
337            TokenKind::FloatLiteral(n) => write!(f, "{}", n),
338            TokenKind::BooleanLiteral(b) => write!(f, "{}", b),
339            _ => write!(f, "{:?}", self),
340        }
341    }
342}
343
344pub trait TokenKindExt {
345    fn is_keyword(&self) -> bool;
346    fn is_literal(&self) -> bool;
347    fn is_operator(&self) -> bool;
348    fn is_delimiter(&self) -> bool;
349    fn is_identifier(&self) -> bool;
350}
351
352impl TokenKindExt for TokenKind {
353    fn is_keyword(&self) -> bool {
354        matches!(
355            self,
356            TokenKind::Create
357                | TokenKind::Match
358                | TokenKind::Return
359                | TokenKind::Where
360                | TokenKind::Delete
361                | TokenKind::Update
362                | TokenKind::Insert
363                | TokenKind::Upsert
364                | TokenKind::From
365                | TokenKind::To
366                | TokenKind::As
367                | TokenKind::With
368                | TokenKind::Yield
369                | TokenKind::Go
370                | TokenKind::Over
371                | TokenKind::Step
372                | TokenKind::Upto
373                | TokenKind::Limit
374                | TokenKind::Asc
375                | TokenKind::Desc
376                | TokenKind::Order
377                | TokenKind::By
378                | TokenKind::Skip
379                | TokenKind::Unwind
380                | TokenKind::Optional
381                | TokenKind::Distinct
382                | TokenKind::All
383                | TokenKind::Null
384                | TokenKind::Is
385                | TokenKind::Not
386                | TokenKind::And
387                | TokenKind::Or
388                | TokenKind::Xor
389                | TokenKind::Contains
390                | TokenKind::StartsWith
391                | TokenKind::EndsWith
392                | TokenKind::Case
393                | TokenKind::When
394                | TokenKind::Then
395                | TokenKind::Else
396                | TokenKind::End
397                | TokenKind::Union
398                | TokenKind::Intersect
399                | TokenKind::Group
400                | TokenKind::Between
401        )
402    }
403
404    fn is_literal(&self) -> bool {
405        matches!(
406            self,
407            TokenKind::StringLiteral(_)
408                | TokenKind::IntegerLiteral(_)
409                | TokenKind::FloatLiteral(_)
410                | TokenKind::BooleanLiteral(_)
411        )
412    }
413
414    fn is_operator(&self) -> bool {
415        matches!(
416            self,
417            TokenKind::Plus
418                | TokenKind::Minus
419                | TokenKind::Star
420                | TokenKind::Div
421                | TokenKind::Mod
422                | TokenKind::Exp
423                | TokenKind::Eq
424                | TokenKind::Assign
425                | TokenKind::Ne
426                | TokenKind::Lt
427                | TokenKind::Le
428                | TokenKind::Gt
429                | TokenKind::Ge
430                | TokenKind::Regex
431                | TokenKind::NotOp
432                | TokenKind::Arrow
433                | TokenKind::ArrowRight
434                | TokenKind::HashArrow
435                | TokenKind::HashArrowRight
436                | TokenKind::DoublePipe
437                | TokenKind::Ampersand
438                | TokenKind::ShiftLeft
439                | TokenKind::ShiftRight
440        )
441    }
442
443    fn is_delimiter(&self) -> bool {
444        matches!(
445            self,
446            TokenKind::LParen
447                | TokenKind::RParen
448                | TokenKind::LBracket
449                | TokenKind::RBracket
450                | TokenKind::LBrace
451                | TokenKind::RBrace
452                | TokenKind::Comma
453                | TokenKind::Dot
454                | TokenKind::DotDot
455                | TokenKind::Colon
456                | TokenKind::Semicolon
457                | TokenKind::QMark
458                | TokenKind::Question
459                | TokenKind::Pipe
460                | TokenKind::Arrow
461                | TokenKind::BackArrow
462                | TokenKind::At
463                | TokenKind::Dollar
464        )
465    }
466
467    fn is_identifier(&self) -> bool {
468        matches!(self, TokenKind::Identifier(_))
469    }
470}