File tree Expand file tree Collapse file tree 4 files changed +60
-1
lines changed
Expand file tree Collapse file tree 4 files changed +60
-1
lines changed Original file line number Diff line number Diff line change @@ -139,6 +139,11 @@ pub enum BinaryOperator {
139139 DuckIntegerDivide ,
140140 /// MySQL [`DIV`](https://dev.mysql.com/doc/refman/8.0/en/arithmetic-functions.html) integer division
141141 MyIntegerDivide ,
142+ /// MATCH operator, e.g. `a MATCH b` (SQLite-specific)
143+ /// See <https://www.sqlite.org/lang_expr.html#the_like_glob_regexp_match_and_extract_operators>
144+ Match ,
145+ /// REGEXP operator, e.g. `a REGEXP b` (SQLite-specific)
146+ Regexp ,
142147 /// Support for custom operators (such as Postgres custom operators)
143148 Custom ( String ) ,
144149 /// Bitwise XOR, e.g. `a # b` (PostgreSQL-specific)
@@ -350,6 +355,8 @@ impl fmt::Display for BinaryOperator {
350355 BinaryOperator :: BitwiseXor => f. write_str ( "^" ) ,
351356 BinaryOperator :: DuckIntegerDivide => f. write_str ( "//" ) ,
352357 BinaryOperator :: MyIntegerDivide => f. write_str ( "DIV" ) ,
358+ BinaryOperator :: Match => f. write_str ( "MATCH" ) ,
359+ BinaryOperator :: Regexp => f. write_str ( "REGEXP" ) ,
353360 BinaryOperator :: Custom ( s) => f. write_str ( s) ,
354361 BinaryOperator :: PGBitwiseXor => f. write_str ( "#" ) ,
355362 BinaryOperator :: PGBitwiseShiftLeft => f. write_str ( "<<" ) ,
Original file line number Diff line number Diff line change @@ -619,6 +619,7 @@ pub trait Dialect: Debug + Any {
619619 Token :: Word ( w) if w. keyword == Keyword :: ILIKE => Ok ( p ! ( Like ) ) ,
620620 Token :: Word ( w) if w. keyword == Keyword :: RLIKE => Ok ( p ! ( Like ) ) ,
621621 Token :: Word ( w) if w. keyword == Keyword :: REGEXP => Ok ( p ! ( Like ) ) ,
622+ Token :: Word ( w) if w. keyword == Keyword :: MATCH => Ok ( p ! ( Like ) ) ,
622623 Token :: Word ( w) if w. keyword == Keyword :: SIMILAR => Ok ( p ! ( Like ) ) ,
623624 _ => Ok ( self . prec_unknown ( ) ) ,
624625 } ,
@@ -630,6 +631,7 @@ pub trait Dialect: Debug + Any {
630631 Token :: Word ( w) if w. keyword == Keyword :: ILIKE => Ok ( p ! ( Like ) ) ,
631632 Token :: Word ( w) if w. keyword == Keyword :: RLIKE => Ok ( p ! ( Like ) ) ,
632633 Token :: Word ( w) if w. keyword == Keyword :: REGEXP => Ok ( p ! ( Like ) ) ,
634+ Token :: Word ( w) if w. keyword == Keyword :: MATCH => Ok ( p ! ( Like ) ) ,
633635 Token :: Word ( w) if w. keyword == Keyword :: SIMILAR => Ok ( p ! ( Like ) ) ,
634636 Token :: Word ( w) if w. keyword == Keyword :: OPERATOR => Ok ( p ! ( Between ) ) ,
635637 Token :: Word ( w) if w. keyword == Keyword :: DIV => Ok ( p ! ( MulDivModOp ) ) ,
Original file line number Diff line number Diff line change 1515// specific language governing permissions and limitations
1616// under the License.
1717
18- use crate :: ast:: Statement ;
18+ use crate :: ast:: BinaryOperator ;
19+ use crate :: ast:: { Expr , Statement } ;
1920use crate :: dialect:: Dialect ;
2021use crate :: keywords:: Keyword ;
2122use crate :: parser:: { Parser , ParserError } ;
@@ -70,6 +71,27 @@ impl Dialect for SQLiteDialect {
7071 }
7172 }
7273
74+ fn parse_infix (
75+ & self ,
76+ parser : & mut crate :: parser:: Parser ,
77+ expr : & crate :: ast:: Expr ,
78+ _precedence : u8 ,
79+ ) -> Option < Result < crate :: ast:: Expr , ParserError > > {
80+ // Parse MATCH and REGEXP as operators
81+ // See <https://www.sqlite.org/lang_expr.html#the_like_glob_regexp_match_and_extract_operators>
82+ for ( keyword, op) in [
83+ ( Keyword :: REGEXP , BinaryOperator :: Regexp ) ,
84+ ( Keyword :: MATCH , BinaryOperator :: Match ) ,
85+ ] {
86+ if parser. parse_keyword ( keyword) {
87+ let left = Box :: new ( expr. clone ( ) ) ;
88+ let right = Box :: new ( parser. parse_expr ( ) . unwrap ( ) ) ;
89+ return Some ( Ok ( Expr :: BinaryOp { left, op, right } ) ) ;
90+ }
91+ }
92+ None
93+ }
94+
7395 fn supports_in_empty_list ( & self ) -> bool {
7496 true
7597 }
Original file line number Diff line number Diff line change @@ -562,6 +562,34 @@ fn test_dollar_identifier_as_placeholder() {
562562 }
563563}
564564
565+ #[ test]
566+ fn test_match_operator ( ) {
567+ assert_eq ! (
568+ sqlite( ) . verified_expr( "col MATCH 'pattern'" ) ,
569+ Expr :: BinaryOp {
570+ op: BinaryOperator :: Match ,
571+ left: Box :: new( Expr :: Identifier ( Ident :: new( "col" ) ) ) ,
572+ right: Box :: new( Expr :: Value (
573+ ( Value :: SingleQuotedString ( "pattern" . to_string( ) ) ) . with_empty_span( )
574+ ) )
575+ }
576+ ) ;
577+ }
578+
579+ #[ test]
580+ fn test_regexp_operator ( ) {
581+ assert_eq ! (
582+ sqlite( ) . verified_expr( "col REGEXP 'pattern'" ) ,
583+ Expr :: BinaryOp {
584+ op: BinaryOperator :: Regexp ,
585+ left: Box :: new( Expr :: Identifier ( Ident :: new( "col" ) ) ) ,
586+ right: Box :: new( Expr :: Value (
587+ ( Value :: SingleQuotedString ( "pattern" . to_string( ) ) ) . with_empty_span( )
588+ ) )
589+ }
590+ ) ;
591+ }
592+
565593fn sqlite ( ) -> TestedDialects {
566594 TestedDialects :: new ( vec ! [ Box :: new( SQLiteDialect { } ) ] )
567595}
You can’t perform that action at this time.
0 commit comments