Skip to content

Commit 9d5f9fb

Browse files
committed
snowflake: try_cast
1 parent da201d4 commit 9d5f9fb

3 files changed

Lines changed: 19 additions & 3 deletions

File tree

src/ast/mod.rs

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -202,6 +202,8 @@ pub enum Expr {
202202
UnaryOp { op: UnaryOperator, expr: Box<Expr> },
203203
/// CAST an expression to a different data type e.g. `CAST(foo AS VARCHAR(123))`
204204
Cast {
205+
/// try_cast is a snowflake feature
206+
try_cast: bool,
205207
expr: Box<Expr>,
206208
data_type: DataType,
207209
},
@@ -323,7 +325,17 @@ impl fmt::Display for Expr {
323325
write!(f, "{} {}", op, expr)
324326
}
325327
}
326-
Expr::Cast { expr, data_type } => write!(f, "CAST({} AS {})", expr, data_type),
328+
Expr::Cast {
329+
try_cast,
330+
expr,
331+
data_type,
332+
} => write!(
333+
f,
334+
"{}CAST({} AS {})",
335+
if *try_cast { "TRY_" } else { "" },
336+
expr,
337+
data_type
338+
),
327339
Expr::Extract { field, expr } => write!(f, "EXTRACT({} FROM {})", field, expr),
328340
Expr::Collate { expr, collation } => write!(f, "{} COLLATE {}", expr, collation),
329341
Expr::Index { expr, index_expr } => write!(f, "{}[{}]", expr, index_expr),

src/dialect/keywords.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -432,6 +432,7 @@ define_keywords!(
432432
TRIM_ARRAY,
433433
TRUE,
434434
TRUNCATE,
435+
TRY_CAST,
435436
UESCAPE,
436437
UNBOUNDED,
437438
UNCOMMITTED,

src/parser.rs

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -243,7 +243,8 @@ impl<'a> Parser<'a> {
243243
Ok(Expr::Value(self.parse_value()?))
244244
}
245245
Keyword::CASE => self.parse_case_expr(),
246-
Keyword::CAST => self.parse_cast_expr(),
246+
Keyword::CAST => self.parse_cast_expr(false),
247+
Keyword::TRY_CAST => self.parse_cast_expr(true),
247248
Keyword::EXISTS => self.parse_exists_expr(),
248249
Keyword::EXTRACT => self.parse_extract_expr(),
249250
Keyword::INTERVAL => self.parse_literal_interval(),
@@ -481,13 +482,14 @@ impl<'a> Parser<'a> {
481482
}
482483

483484
/// Parse a SQL CAST function e.g. `CAST(expr AS FLOAT)`
484-
pub fn parse_cast_expr(&mut self) -> Result<Expr, ParserError> {
485+
pub fn parse_cast_expr(&mut self, try_cast: bool) -> Result<Expr, ParserError> {
485486
self.expect_token(&Token::LParen)?;
486487
let expr = self.parse_expr()?;
487488
self.expect_keyword(Keyword::AS)?;
488489
let data_type = self.parse_data_type()?;
489490
self.expect_token(&Token::RParen)?;
490491
Ok(Expr::Cast {
492+
try_cast,
491493
expr: Box::new(expr),
492494
data_type,
493495
})
@@ -853,6 +855,7 @@ impl<'a> Parser<'a> {
853855
/// Parse a postgresql casting style which is in the form of `expr::datatype`
854856
pub fn parse_pg_cast(&mut self, expr: Expr) -> Result<Expr, ParserError> {
855857
Ok(Expr::Cast {
858+
try_cast: false,
856859
expr: Box::new(expr),
857860
data_type: self.parse_data_type()?,
858861
})

0 commit comments

Comments
 (0)