From 9ff9c3fdc269472b5d1917cf1ca5022e1c0f7b6a Mon Sep 17 00:00:00 2001 From: "Levy A." Date: Fri, 4 Jul 2025 00:20:56 -0300 Subject: [PATCH] feat: add context to `ToTokens` --- vendored/sqlite3-parser/src/parser/ast/fmt.rs | 1014 +++++++++++------ vendored/sqlite3-parser/src/parser/ast/mod.rs | 2 +- 2 files changed, 659 insertions(+), 357 deletions(-) diff --git a/vendored/sqlite3-parser/src/parser/ast/fmt.rs b/vendored/sqlite3-parser/src/parser/ast/fmt.rs index 6598e71d7..1bda031a3 100644 --- a/vendored/sqlite3-parser/src/parser/ast/fmt.rs +++ b/vendored/sqlite3-parser/src/parser/ast/fmt.rs @@ -3,6 +3,7 @@ use std::fmt::{self, Display, Formatter, Write}; use crate::ast::*; use crate::dialect::TokenType::*; +use crate::to_sql_string::ToSqlContext; struct FmtTokenStream<'a, 'b> { f: &'a mut Formatter<'b>, @@ -85,18 +86,53 @@ impl TokenStream for WriteTokenStream<'_, T> { } } +struct BlankContext; + +impl ToSqlContext for BlankContext { + fn get_column_name(&self, _table_id: crate::ast::TableInternalId, _col_idx: usize) -> &str { + "" + } + + fn get_table_name(&self, _id: crate::ast::TableInternalId) -> &str { + "" + } +} + /// Stream of token pub trait TokenStream { /// Potential error raised type Error; /// Push token to this stream fn append(&mut self, ty: TokenType, value: Option<&str>) -> Result<(), Self::Error>; + + fn comma(&mut self, items: I, context: &C) -> Result<(), Self::Error> + where + I: IntoIterator, + I::Item: ToTokens, + { + let iter = items.into_iter(); + for (i, item) in iter.enumerate() { + if i != 0 { + self.append(TK_COMMA, None)?; + } + item.to_tokens_with_context(self, context)?; + } + Ok(()) + } } /// Generate token(s) from AST node pub trait ToTokens { + /// Send token(s) to the specified stream with context + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error>; /// Send token(s) to the specified stream - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error>; + fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + self.to_tokens_with_context(s, &BlankContext) + } /// Format AST node fn to_fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { let mut s = FmtTokenStream { f, spaced: true }; @@ -118,32 +154,44 @@ pub trait ToTokens { } impl ToTokens for &T { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - ToTokens::to_tokens(&**self, s) + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + ToTokens::to_tokens_with_context(&**self, s, context) } } impl ToTokens for String { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append(TK_ANY, Some(self.as_ref())) } } impl ToTokens for Cmd { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Explain(stmt) => { s.append(TK_EXPLAIN, None)?; - stmt.to_tokens(s)?; + stmt.to_tokens_with_context(s, context)?; } Self::ExplainQueryPlan(stmt) => { s.append(TK_EXPLAIN, None)?; s.append(TK_QUERY, None)?; s.append(TK_PLAN, None)?; - stmt.to_tokens(s)?; + stmt.to_tokens_with_context(s, context)?; } Self::Stmt(stmt) => { - stmt.to_tokens(s)?; + stmt.to_tokens_with_context(s, context)?; } } s.append(TK_SEMI, None) @@ -157,41 +205,45 @@ impl Display for Cmd { } impl ToTokens for Stmt { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::AlterTable(alter_table) => { let (tbl_name, body) = &**alter_table; s.append(TK_ALTER, None)?; s.append(TK_TABLE, None)?; - tbl_name.to_tokens(s)?; - body.to_tokens(s) + tbl_name.to_tokens_with_context(s, context)?; + body.to_tokens_with_context(s, context) } Self::Analyze(obj_name) => { s.append(TK_ANALYZE, None)?; if let Some(obj_name) = obj_name { - obj_name.to_tokens(s)?; + obj_name.to_tokens_with_context(s, context)?; } Ok(()) } Self::Attach { expr, db_name, key } => { s.append(TK_ATTACH, None)?; - expr.to_tokens(s)?; + expr.to_tokens_with_context(s, context)?; s.append(TK_AS, None)?; - db_name.to_tokens(s)?; + db_name.to_tokens_with_context(s, context)?; if let Some(key) = key { s.append(TK_KEY, None)?; - key.to_tokens(s)?; + key.to_tokens_with_context(s, context)?; } Ok(()) } Self::Begin(tx_type, tx_name) => { s.append(TK_BEGIN, None)?; if let Some(tx_type) = tx_type { - tx_type.to_tokens(s)?; + tx_type.to_tokens_with_context(s, context)?; } if let Some(tx_name) = tx_name { s.append(TK_TRANSACTION, None)?; - tx_name.to_tokens(s)?; + tx_name.to_tokens_with_context(s, context)?; } Ok(()) } @@ -199,7 +251,7 @@ impl ToTokens for Stmt { s.append(TK_COMMIT, None)?; if let Some(tx_name) = tx_name { s.append(TK_TRANSACTION, None)?; - tx_name.to_tokens(s)?; + tx_name.to_tokens_with_context(s, context)?; } Ok(()) } @@ -221,15 +273,15 @@ impl ToTokens for Stmt { s.append(TK_NOT, None)?; s.append(TK_EXISTS, None)?; } - idx_name.to_tokens(s)?; + idx_name.to_tokens_with_context(s, context)?; s.append(TK_ON, None)?; - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; s.append(TK_LP, None)?; - comma(columns, s)?; + comma(columns, s, context)?; s.append(TK_RP, None)?; if let Some(where_clause) = where_clause { s.append(TK_WHERE, None)?; - where_clause.to_tokens(s)?; + where_clause.to_tokens_with_context(s, context)?; } Ok(()) } @@ -249,8 +301,8 @@ impl ToTokens for Stmt { s.append(TK_NOT, None)?; s.append(TK_EXISTS, None)?; } - tbl_name.to_tokens(s)?; - body.to_tokens(s) + tbl_name.to_tokens_with_context(s, context)?; + body.to_tokens_with_context(s, context) } Self::CreateTrigger(trigger) => { let CreateTrigger { @@ -274,13 +326,13 @@ impl ToTokens for Stmt { s.append(TK_NOT, None)?; s.append(TK_EXISTS, None)?; } - trigger_name.to_tokens(s)?; + trigger_name.to_tokens_with_context(s, context)?; if let Some(time) = time { - time.to_tokens(s)?; + time.to_tokens_with_context(s, context)?; } - event.to_tokens(s)?; + event.to_tokens_with_context(s, context)?; s.append(TK_ON, None)?; - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; if *for_each_row { s.append(TK_FOR, None)?; s.append(TK_EACH, None)?; @@ -288,11 +340,11 @@ impl ToTokens for Stmt { } if let Some(when_clause) = when_clause { s.append(TK_WHEN, None)?; - when_clause.to_tokens(s)?; + when_clause.to_tokens_with_context(s, context)?; } s.append(TK_BEGIN, Some("\n"))?; for command in commands { - command.to_tokens(s)?; + command.to_tokens_with_context(s, context)?; s.append(TK_SEMI, Some("\n"))?; } s.append(TK_END, None) @@ -314,14 +366,14 @@ impl ToTokens for Stmt { s.append(TK_NOT, None)?; s.append(TK_EXISTS, None)?; } - view_name.to_tokens(s)?; + view_name.to_tokens_with_context(s, context)?; if let Some(columns) = columns { s.append(TK_LP, None)?; - comma(columns, s)?; + comma(columns, s, context)?; s.append(TK_RP, None)?; } s.append(TK_AS, None)?; - select.to_tokens(s) + select.to_tokens_with_context(s, context) } Self::CreateVirtualTable(create_virtual_table) => { let CreateVirtualTable { @@ -338,12 +390,12 @@ impl ToTokens for Stmt { s.append(TK_NOT, None)?; s.append(TK_EXISTS, None)?; } - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; s.append(TK_USING, None)?; - module_name.to_tokens(s)?; + module_name.to_tokens_with_context(s, context)?; s.append(TK_LP, None)?; if let Some(args) = args { - comma(args, s)?; + comma(args, s, context)?; } s.append(TK_RP, None) } @@ -358,35 +410,35 @@ impl ToTokens for Stmt { limit, } = &**delete; if let Some(with) = with { - with.to_tokens(s)?; + with.to_tokens_with_context(s, context)?; } s.append(TK_DELETE, None)?; s.append(TK_FROM, None)?; - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; if let Some(indexed) = indexed { - indexed.to_tokens(s)?; + indexed.to_tokens_with_context(s, context)?; } if let Some(where_clause) = where_clause { s.append(TK_WHERE, None)?; - where_clause.to_tokens(s)?; + where_clause.to_tokens_with_context(s, context)?; } if let Some(returning) = returning { s.append(TK_RETURNING, None)?; - comma(returning, s)?; + comma(returning, s, context)?; } if let Some(order_by) = order_by { s.append(TK_ORDER, None)?; s.append(TK_BY, None)?; - comma(order_by, s)?; + comma(order_by, s, context)?; } if let Some(limit) = limit { - limit.to_tokens(s)?; + limit.to_tokens_with_context(s, context)?; } Ok(()) } Self::Detach(expr) => { s.append(TK_DETACH, None)?; - expr.to_tokens(s) + expr.to_tokens_with_context(s, context) } Self::DropIndex { if_exists, @@ -398,7 +450,7 @@ impl ToTokens for Stmt { s.append(TK_IF, None)?; s.append(TK_EXISTS, None)?; } - idx_name.to_tokens(s) + idx_name.to_tokens_with_context(s, context) } Self::DropTable { if_exists, @@ -410,7 +462,7 @@ impl ToTokens for Stmt { s.append(TK_IF, None)?; s.append(TK_EXISTS, None)?; } - tbl_name.to_tokens(s) + tbl_name.to_tokens_with_context(s, context) } Self::DropTrigger { if_exists, @@ -422,7 +474,7 @@ impl ToTokens for Stmt { s.append(TK_IF, None)?; s.append(TK_EXISTS, None)?; } - trigger_name.to_tokens(s) + trigger_name.to_tokens_with_context(s, context) } Self::DropView { if_exists, @@ -434,7 +486,7 @@ impl ToTokens for Stmt { s.append(TK_IF, None)?; s.append(TK_EXISTS, None)?; } - view_name.to_tokens(s) + view_name.to_tokens_with_context(s, context) } Self::Insert(insert) => { let Insert { @@ -446,7 +498,7 @@ impl ToTokens for Stmt { returning, } = &**insert; if let Some(with) = with { - with.to_tokens(s)?; + with.to_tokens_with_context(s, context)?; } if let Some(ResolveType::Replace) = or_conflict { s.append(TK_REPLACE, None)?; @@ -454,41 +506,41 @@ impl ToTokens for Stmt { s.append(TK_INSERT, None)?; if let Some(or_conflict) = or_conflict { s.append(TK_OR, None)?; - or_conflict.to_tokens(s)?; + or_conflict.to_tokens_with_context(s, context)?; } } s.append(TK_INTO, None)?; - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; if let Some(columns) = columns { s.append(TK_LP, None)?; - comma(columns.deref(), s)?; + comma(columns.deref(), s, context)?; s.append(TK_RP, None)?; } - body.to_tokens(s)?; + body.to_tokens_with_context(s, context)?; if let Some(returning) = returning { s.append(TK_RETURNING, None)?; - comma(returning, s)?; + comma(returning, s, context)?; } Ok(()) } Self::Pragma(name, value) => { s.append(TK_PRAGMA, None)?; - name.to_tokens(s)?; + name.to_tokens_with_context(s, context)?; if let Some(value) = value { - value.to_tokens(s)?; + value.to_tokens_with_context(s, context)?; } Ok(()) } Self::Reindex { obj_name } => { s.append(TK_REINDEX, None)?; if let Some(obj_name) = obj_name { - obj_name.to_tokens(s)?; + obj_name.to_tokens_with_context(s, context)?; } Ok(()) } Self::Release(name) => { s.append(TK_RELEASE, None)?; - name.to_tokens(s) + name.to_tokens_with_context(s, context) } Self::Rollback { tx_name, @@ -497,19 +549,19 @@ impl ToTokens for Stmt { s.append(TK_ROLLBACK, None)?; if let Some(tx_name) = tx_name { s.append(TK_TRANSACTION, None)?; - tx_name.to_tokens(s)?; + tx_name.to_tokens_with_context(s, context)?; } if let Some(savepoint_name) = savepoint_name { s.append(TK_TO, None)?; - savepoint_name.to_tokens(s)?; + savepoint_name.to_tokens_with_context(s, context)?; } Ok(()) } Self::Savepoint(name) => { s.append(TK_SAVEPOINT, None)?; - name.to_tokens(s) + name.to_tokens_with_context(s, context) } - Self::Select(select) => select.to_tokens(s), + Self::Select(select) => select.to_tokens_with_context(s, context), Self::Update(update) => { let Update { with, @@ -524,49 +576,49 @@ impl ToTokens for Stmt { limit, } = &**update; if let Some(with) = with { - with.to_tokens(s)?; + with.to_tokens_with_context(s, context)?; } s.append(TK_UPDATE, None)?; if let Some(or_conflict) = or_conflict { s.append(TK_OR, None)?; - or_conflict.to_tokens(s)?; + or_conflict.to_tokens_with_context(s, context)?; } - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; if let Some(indexed) = indexed { - indexed.to_tokens(s)?; + indexed.to_tokens_with_context(s, context)?; } s.append(TK_SET, None)?; - comma(sets, s)?; + comma(sets, s, context)?; if let Some(from) = from { s.append(TK_FROM, None)?; - from.to_tokens(s)?; + from.to_tokens_with_context(s, context)?; } if let Some(where_clause) = where_clause { s.append(TK_WHERE, None)?; - where_clause.to_tokens(s)?; + where_clause.to_tokens_with_context(s, context)?; } if let Some(returning) = returning { s.append(TK_RETURNING, None)?; - comma(returning, s)?; + comma(returning, s, context)?; } if let Some(order_by) = order_by { s.append(TK_ORDER, None)?; s.append(TK_BY, None)?; - comma(order_by, s)?; + comma(order_by, s, context)?; } if let Some(limit) = limit { - limit.to_tokens(s)?; + limit.to_tokens_with_context(s, context)?; } Ok(()) } Self::Vacuum(name, expr) => { s.append(TK_VACUUM, None)?; if let Some(ref name) = name { - name.to_tokens(s)?; + name.to_tokens_with_context(s, context)?; } if let Some(ref expr) = expr { s.append(TK_INTO, None)?; - expr.to_tokens(s)?; + expr.to_tokens_with_context(s, context)?; } Ok(()) } @@ -575,7 +627,11 @@ impl ToTokens for Stmt { } impl ToTokens for Expr { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Between { lhs, @@ -583,19 +639,19 @@ impl ToTokens for Expr { start, end, } => { - lhs.to_tokens(s)?; + lhs.to_tokens_with_context(s, context)?; if *not { s.append(TK_NOT, None)?; } s.append(TK_BETWEEN, None)?; - start.to_tokens(s)?; + start.to_tokens_with_context(s, context)?; s.append(TK_AND, None)?; - end.to_tokens(s) + end.to_tokens_with_context(s, context) } Self::Binary(lhs, op, rhs) => { - lhs.to_tokens(s)?; - op.to_tokens(s)?; - rhs.to_tokens(s) + lhs.to_tokens_with_context(s, context)?; + op.to_tokens_with_context(s, context)?; + rhs.to_tokens_with_context(s, context) } Self::Case { base, @@ -604,46 +660,46 @@ impl ToTokens for Expr { } => { s.append(TK_CASE, None)?; if let Some(ref base) = base { - base.to_tokens(s)?; + base.to_tokens_with_context(s, context)?; } for (when, then) in when_then_pairs { s.append(TK_WHEN, None)?; - when.to_tokens(s)?; + when.to_tokens_with_context(s, context)?; s.append(TK_THEN, None)?; - then.to_tokens(s)?; + then.to_tokens_with_context(s, context)?; } if let Some(ref else_expr) = else_expr { s.append(TK_ELSE, None)?; - else_expr.to_tokens(s)?; + else_expr.to_tokens_with_context(s, context)?; } s.append(TK_END, None) } Self::Cast { expr, type_name } => { s.append(TK_CAST, None)?; s.append(TK_LP, None)?; - expr.to_tokens(s)?; + expr.to_tokens_with_context(s, context)?; s.append(TK_AS, None)?; if let Some(ref type_name) = type_name { - type_name.to_tokens(s)?; + type_name.to_tokens_with_context(s, context)?; } s.append(TK_RP, None) } Self::Collate(expr, collation) => { - expr.to_tokens(s)?; + expr.to_tokens_with_context(s, context)?; s.append(TK_COLLATE, None)?; double_quote(collation, s) } Self::DoublyQualified(db_name, tbl_name, col_name) => { - db_name.to_tokens(s)?; + db_name.to_tokens_with_context(s, context)?; s.append(TK_DOT, None)?; - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; s.append(TK_DOT, None)?; - col_name.to_tokens(s) + col_name.to_tokens_with_context(s, context) } Self::Exists(subquery) => { s.append(TK_EXISTS, None)?; s.append(TK_LP, None)?; - subquery.to_tokens(s)?; + subquery.to_tokens_with_context(s, context)?; s.append(TK_RP, None) } Self::FunctionCall { @@ -653,57 +709,61 @@ impl ToTokens for Expr { order_by, filter_over, } => { - name.to_tokens(s)?; + name.to_tokens_with_context(s, context)?; s.append(TK_LP, None)?; if let Some(distinctness) = distinctness { - distinctness.to_tokens(s)?; + distinctness.to_tokens_with_context(s, context)?; } if let Some(args) = args { - comma(args, s)?; + comma(args, s, context)?; } if let Some(order_by) = order_by { s.append(TK_ORDER, None)?; s.append(TK_BY, None)?; - comma(order_by, s)?; + comma(order_by, s, context)?; } s.append(TK_RP, None)?; if let Some(filter_over) = filter_over { - filter_over.to_tokens(s)?; + filter_over.to_tokens_with_context(s, context)?; } Ok(()) } Self::FunctionCallStar { name, filter_over } => { - name.to_tokens(s)?; + name.to_tokens_with_context(s, context)?; s.append(TK_LP, None)?; s.append(TK_STAR, None)?; s.append(TK_RP, None)?; if let Some(filter_over) = filter_over { - filter_over.to_tokens(s)?; + filter_over.to_tokens_with_context(s, context)?; } Ok(()) } - Self::Id(id) => id.to_tokens(s), - Self::Column { .. } => Ok(()), + Self::Id(id) => id.to_tokens_with_context(s, context), + Self::Column { table, column, .. } => { + s.append(TK_ID, Some(context.get_table_name(*table)))?; + s.append(TK_DOT, None)?; + s.append(TK_ID, Some(context.get_column_name(*table, *column))) + } Self::InList { lhs, not, rhs } => { - lhs.to_tokens(s)?; + lhs.to_tokens_with_context(s, context)?; if *not { s.append(TK_NOT, None)?; } s.append(TK_IN, None)?; s.append(TK_LP, None)?; if let Some(rhs) = rhs { - comma(rhs, s)?; + comma(rhs, s, context)?; } s.append(TK_RP, None) } Self::InSelect { lhs, not, rhs } => { - lhs.to_tokens(s)?; + lhs.to_tokens_with_context(s, context)?; if *not { s.append(TK_NOT, None)?; } s.append(TK_IN, None)?; s.append(TK_LP, None)?; - rhs.to_tokens(s)?; + rhs.to_tokens_with_context(s, context)?; s.append(TK_RP, None) } Self::InTable { @@ -712,21 +772,21 @@ impl ToTokens for Expr { rhs, args, } => { - lhs.to_tokens(s)?; + lhs.to_tokens_with_context(s, context)?; if *not { s.append(TK_NOT, None)?; } s.append(TK_IN, None)?; - rhs.to_tokens(s)?; + rhs.to_tokens_with_context(s, context)?; if let Some(args) = args { s.append(TK_LP, None)?; - comma(args, s)?; + comma(args, s, context)?; s.append(TK_RP, None)?; } Ok(()) } Self::IsNull(sub_expr) => { - sub_expr.to_tokens(s)?; + sub_expr.to_tokens_with_context(s, context)?; s.append(TK_ISNULL, None) } Self::Like { @@ -736,53 +796,53 @@ impl ToTokens for Expr { rhs, escape, } => { - lhs.to_tokens(s)?; + lhs.to_tokens_with_context(s, context)?; if *not { s.append(TK_NOT, None)?; } - op.to_tokens(s)?; - rhs.to_tokens(s)?; + op.to_tokens_with_context(s, context)?; + rhs.to_tokens_with_context(s, context)?; if let Some(escape) = escape { s.append(TK_ESCAPE, None)?; - escape.to_tokens(s)?; + escape.to_tokens_with_context(s, context)?; } Ok(()) } - Self::Literal(lit) => lit.to_tokens(s), - Self::Name(name) => name.to_tokens(s), + Self::Literal(lit) => lit.to_tokens_with_context(s, context), + Self::Name(name) => name.to_tokens_with_context(s, context), Self::NotNull(sub_expr) => { - sub_expr.to_tokens(s)?; + sub_expr.to_tokens_with_context(s, context)?; s.append(TK_NOTNULL, None) } Self::Parenthesized(exprs) => { s.append(TK_LP, None)?; - comma(exprs, s)?; + comma(exprs, s, context)?; s.append(TK_RP, None) } Self::Qualified(qualifier, qualified) => { - qualifier.to_tokens(s)?; + qualifier.to_tokens_with_context(s, context)?; s.append(TK_DOT, None)?; - qualified.to_tokens(s) + qualified.to_tokens_with_context(s, context) } Self::Raise(rt, err) => { s.append(TK_RAISE, None)?; s.append(TK_LP, None)?; - rt.to_tokens(s)?; + rt.to_tokens_with_context(s, context)?; if let Some(err) = err { s.append(TK_COMMA, None)?; - err.to_tokens(s)?; + err.to_tokens_with_context(s, context)?; } s.append(TK_RP, None) } Self::RowId { .. } => Ok(()), Self::Subquery(query) => { s.append(TK_LP, None)?; - query.to_tokens(s)?; + query.to_tokens_with_context(s, context)?; s.append(TK_RP, None) } Self::Unary(op, sub_expr) => { - op.to_tokens(s)?; - sub_expr.to_tokens(s) + op.to_tokens_with_context(s, context)?; + sub_expr.to_tokens_with_context(s, context) } Self::Variable(var) => match var.chars().next() { Some(c) if c == '$' || c == '@' || c == '#' || c == ':' => { @@ -802,7 +862,11 @@ impl Display for Expr { } impl ToTokens for Literal { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { match self { Self::Numeric(ref num) => s.append(TK_FLOAT, Some(num)), // TODO Validate TK_FLOAT Self::String(ref str) => s.append(TK_STRING, Some(str)), @@ -817,7 +881,11 @@ impl ToTokens for Literal { } impl ToTokens for LikeOperator { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append( TK_LIKE_KW, Some(match self { @@ -831,7 +899,11 @@ impl ToTokens for LikeOperator { } impl ToTokens for Operator { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { match self { Self::Add => s.append(TK_PLUS, None), Self::And => s.append(TK_AND, None), @@ -864,7 +936,11 @@ impl ToTokens for Operator { } impl ToTokens for UnaryOperator { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append( match self { Self::BitwiseNot => TK_BITNOT, @@ -878,29 +954,37 @@ impl ToTokens for UnaryOperator { } impl ToTokens for Select { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { if let Some(ref with) = self.with { - with.to_tokens(s)?; + with.to_tokens_with_context(s, context)?; } - self.body.to_tokens(s)?; + self.body.to_tokens_with_context(s, context)?; if let Some(ref order_by) = self.order_by { s.append(TK_ORDER, None)?; s.append(TK_BY, None)?; - comma(order_by, s)?; + comma(order_by, s, context)?; } if let Some(ref limit) = self.limit { - limit.to_tokens(s)?; + limit.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for SelectBody { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.select.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.select.to_tokens_with_context(s, context)?; if let Some(ref compounds) = self.compounds { for compound in compounds { - compound.to_tokens(s)?; + compound.to_tokens_with_context(s, context)?; } } Ok(()) @@ -908,14 +992,22 @@ impl ToTokens for SelectBody { } impl ToTokens for CompoundSelect { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.operator.to_tokens(s)?; - self.select.to_tokens(s) + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.operator.to_tokens_with_context(s, context)?; + self.select.to_tokens_with_context(s, context) } } impl ToTokens for CompoundOperator { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { match self { Self::Union => s.append(TK_UNION, None), Self::UnionAll => { @@ -935,7 +1027,11 @@ impl Display for CompoundOperator { } impl ToTokens for OneSelect { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Select(select) => { let SelectInner { @@ -948,23 +1044,23 @@ impl ToTokens for OneSelect { } = &**select; s.append(TK_SELECT, None)?; if let Some(ref distinctness) = distinctness { - distinctness.to_tokens(s)?; + distinctness.to_tokens_with_context(s, context)?; } - comma(columns, s)?; + comma(columns, s, context)?; if let Some(ref from) = from { s.append(TK_FROM, None)?; - from.to_tokens(s)?; + from.to_tokens_with_context(s, context)?; } if let Some(ref where_clause) = where_clause { s.append(TK_WHERE, None)?; - where_clause.to_tokens(s)?; + where_clause.to_tokens_with_context(s, context)?; } if let Some(ref group_by) = group_by { - group_by.to_tokens(s)?; + group_by.to_tokens_with_context(s, context)?; } if let Some(ref window_clause) = window_clause { s.append(TK_WINDOW, None)?; - comma(window_clause, s)?; + comma(window_clause, s, context)?; } Ok(()) } @@ -976,7 +1072,7 @@ impl ToTokens for OneSelect { s.append(TK_COMMA, None)?; } s.append(TK_LP, None)?; - comma(vals, s)?; + comma(vals, s, context)?; s.append(TK_RP, None)?; } Ok(()) @@ -986,11 +1082,18 @@ impl ToTokens for OneSelect { } impl ToTokens for FromClause { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.select.as_ref().unwrap().to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.select + .as_ref() + .unwrap() + .to_tokens_with_context(s, context)?; if let Some(ref joins) = self.joins { for join in joins { - join.to_tokens(s)?; + join.to_tokens_with_context(s, context)?; } } Ok(()) @@ -998,7 +1101,11 @@ impl ToTokens for FromClause { } impl ToTokens for Distinctness { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append( match self { Self::Distinct => TK_DISTINCT, @@ -1010,18 +1117,22 @@ impl ToTokens for Distinctness { } impl ToTokens for ResultColumn { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Expr(expr, alias) => { - expr.to_tokens(s)?; + expr.to_tokens_with_context(s, context)?; if let Some(alias) = alias { - alias.to_tokens(s)?; + alias.to_tokens_with_context(s, context)?; } Ok(()) } Self::Star => s.append(TK_STAR, None), Self::TableStar(tbl_name) => { - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; s.append(TK_DOT, None)?; s.append(TK_STAR, None) } @@ -1030,68 +1141,80 @@ impl ToTokens for ResultColumn { } impl ToTokens for As { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::As(ref name) => { s.append(TK_AS, None)?; - name.to_tokens(s) + name.to_tokens_with_context(s, context) } - Self::Elided(ref name) => name.to_tokens(s), + Self::Elided(ref name) => name.to_tokens_with_context(s, context), } } } impl ToTokens for JoinedSelectTable { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.operator.to_tokens(s)?; - self.table.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.operator.to_tokens_with_context(s, context)?; + self.table.to_tokens_with_context(s, context)?; if let Some(ref constraint) = self.constraint { - constraint.to_tokens(s)?; + constraint.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for SelectTable { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Table(name, alias, indexed) => { - name.to_tokens(s)?; + name.to_tokens_with_context(s, context)?; if let Some(alias) = alias { - alias.to_tokens(s)?; + alias.to_tokens_with_context(s, context)?; } if let Some(indexed) = indexed { - indexed.to_tokens(s)?; + indexed.to_tokens_with_context(s, context)?; } Ok(()) } Self::TableCall(name, exprs, alias) => { - name.to_tokens(s)?; + name.to_tokens_with_context(s, context)?; s.append(TK_LP, None)?; if let Some(exprs) = exprs { - comma(exprs, s)?; + comma(exprs, s, context)?; } s.append(TK_RP, None)?; if let Some(alias) = alias { - alias.to_tokens(s)?; + alias.to_tokens_with_context(s, context)?; } Ok(()) } Self::Select(select, alias) => { s.append(TK_LP, None)?; - select.to_tokens(s)?; + select.to_tokens_with_context(s, context)?; s.append(TK_RP, None)?; if let Some(alias) = alias { - alias.to_tokens(s)?; + alias.to_tokens_with_context(s, context)?; } Ok(()) } Self::Sub(from, alias) => { s.append(TK_LP, None)?; - from.to_tokens(s)?; + from.to_tokens_with_context(s, context)?; s.append(TK_RP, None)?; if let Some(alias) = alias { - alias.to_tokens(s)?; + alias.to_tokens_with_context(s, context)?; } Ok(()) } @@ -1100,12 +1223,16 @@ impl ToTokens for SelectTable { } impl ToTokens for JoinOperator { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Comma => s.append(TK_COMMA, None), Self::TypedJoin(join_type) => { if let Some(ref join_type) = join_type { - join_type.to_tokens(s)?; + join_type.to_tokens_with_context(s, context)?; } s.append(TK_JOIN, None) } @@ -1114,7 +1241,11 @@ impl ToTokens for JoinOperator { } impl ToTokens for JoinType { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { if self.contains(Self::NATURAL) { s.append(TK_JOIN_KW, Some("NATURAL"))?; } @@ -1142,16 +1273,20 @@ impl ToTokens for JoinType { } impl ToTokens for JoinConstraint { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::On(expr) => { s.append(TK_ON, None)?; - expr.to_tokens(s) + expr.to_tokens_with_context(s, context) } Self::Using(col_names) => { s.append(TK_USING, None)?; s.append(TK_LP, None)?; - comma(col_names.deref(), s)?; + comma(col_names.deref(), s, context)?; s.append(TK_RP, None) } } @@ -1159,26 +1294,38 @@ impl ToTokens for JoinConstraint { } impl ToTokens for GroupBy { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { s.append(TK_GROUP, None)?; s.append(TK_BY, None)?; - comma(&self.exprs, s)?; + comma(&self.exprs, s, context)?; if let Some(ref having) = self.having { s.append(TK_HAVING, None)?; - having.to_tokens(s)?; + having.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for Id { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { double_quote(&self.0, s) } } impl ToTokens for Name { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { double_quote(self.0.as_str(), s) } } @@ -1190,50 +1337,62 @@ impl Display for Name { } impl ToTokens for QualifiedName { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { if let Some(ref db_name) = self.db_name { - db_name.to_tokens(s)?; + db_name.to_tokens_with_context(s, context)?; s.append(TK_DOT, None)?; } - self.name.to_tokens(s)?; + self.name.to_tokens_with_context(s, context)?; if let Some(ref alias) = self.alias { s.append(TK_AS, None)?; - alias.to_tokens(s)?; + alias.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for AlterTableBody { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::RenameTo(name) => { s.append(TK_RENAME, None)?; s.append(TK_TO, None)?; - name.to_tokens(s) + name.to_tokens_with_context(s, context) } Self::AddColumn(def) => { s.append(TK_ADD, None)?; s.append(TK_COLUMNKW, None)?; - def.to_tokens(s) + def.to_tokens_with_context(s, context) } Self::RenameColumn { old, new } => { s.append(TK_RENAME, None)?; - old.to_tokens(s)?; + old.to_tokens_with_context(s, context)?; s.append(TK_TO, None)?; - new.to_tokens(s) + new.to_tokens_with_context(s, context) } Self::DropColumn(name) => { s.append(TK_DROP, None)?; s.append(TK_COLUMNKW, None)?; - name.to_tokens(s) + name.to_tokens_with_context(s, context) } } } } impl ToTokens for CreateTableBody { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::ColumnsAndConstraints { columns, @@ -1241,10 +1400,10 @@ impl ToTokens for CreateTableBody { options, } => { s.append(TK_LP, None)?; - comma(columns.values(), s)?; + comma(columns.values(), s, context)?; if let Some(constraints) = constraints { s.append(TK_COMMA, None)?; - comma(constraints, s)?; + comma(constraints, s, context)?; } s.append(TK_RP, None)?; if options.contains(TableOptions::WITHOUT_ROWID) { @@ -1258,37 +1417,49 @@ impl ToTokens for CreateTableBody { } Self::AsSelect(select) => { s.append(TK_AS, None)?; - select.to_tokens(s) + select.to_tokens_with_context(s, context) } } } } impl ToTokens for ColumnDefinition { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.col_name.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.col_name.to_tokens_with_context(s, context)?; if let Some(ref col_type) = self.col_type { - col_type.to_tokens(s)?; + col_type.to_tokens_with_context(s, context)?; } for constraint in &self.constraints { - constraint.to_tokens(s)?; + constraint.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for NamedColumnConstraint { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { if let Some(ref name) = self.name { s.append(TK_CONSTRAINT, None)?; - name.to_tokens(s)?; + name.to_tokens_with_context(s, context)?; } - self.constraint.to_tokens(s) + self.constraint.to_tokens_with_context(s, context) } } impl ToTokens for ColumnConstraint { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::PrimaryKey { order, @@ -1298,12 +1469,12 @@ impl ToTokens for ColumnConstraint { s.append(TK_PRIMARY, None)?; s.append(TK_KEY, None)?; if let Some(order) = order { - order.to_tokens(s)?; + order.to_tokens_with_context(s, context)?; } if let Some(conflict_clause) = conflict_clause { s.append(TK_ON, None)?; s.append(TK_CONFLICT, None)?; - conflict_clause.to_tokens(s)?; + conflict_clause.to_tokens_with_context(s, context)?; } if *auto_increment { s.append(TK_AUTOINCR, None)?; @@ -1321,7 +1492,7 @@ impl ToTokens for ColumnConstraint { if let Some(conflict_clause) = conflict_clause { s.append(TK_ON, None)?; s.append(TK_CONFLICT, None)?; - conflict_clause.to_tokens(s)?; + conflict_clause.to_tokens_with_context(s, context)?; } Ok(()) } @@ -1330,43 +1501,43 @@ impl ToTokens for ColumnConstraint { if let Some(conflict_clause) = conflict_clause { s.append(TK_ON, None)?; s.append(TK_CONFLICT, None)?; - conflict_clause.to_tokens(s)?; + conflict_clause.to_tokens_with_context(s, context)?; } Ok(()) } Self::Check(expr) => { s.append(TK_CHECK, None)?; s.append(TK_LP, None)?; - expr.to_tokens(s)?; + expr.to_tokens_with_context(s, context)?; s.append(TK_RP, None) } Self::Default(expr) => { s.append(TK_DEFAULT, None)?; - expr.to_tokens(s) + expr.to_tokens_with_context(s, context) } - Self::Defer(deref_clause) => deref_clause.to_tokens(s), + Self::Defer(deref_clause) => deref_clause.to_tokens_with_context(s, context), Self::Collate { collation_name } => { s.append(TK_COLLATE, None)?; - collation_name.to_tokens(s) + collation_name.to_tokens_with_context(s, context) } Self::ForeignKey { clause, deref_clause, } => { s.append(TK_REFERENCES, None)?; - clause.to_tokens(s)?; + clause.to_tokens_with_context(s, context)?; if let Some(deref_clause) = deref_clause { - deref_clause.to_tokens(s)?; + deref_clause.to_tokens_with_context(s, context)?; } Ok(()) } Self::Generated { expr, typ } => { s.append(TK_AS, None)?; s.append(TK_LP, None)?; - expr.to_tokens(s)?; + expr.to_tokens_with_context(s, context)?; s.append(TK_RP, None)?; if let Some(typ) = typ { - typ.to_tokens(s)?; + typ.to_tokens_with_context(s, context)?; } Ok(()) } @@ -1375,17 +1546,25 @@ impl ToTokens for ColumnConstraint { } impl ToTokens for NamedTableConstraint { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { if let Some(ref name) = self.name { s.append(TK_CONSTRAINT, None)?; - name.to_tokens(s)?; + name.to_tokens_with_context(s, context)?; } - self.constraint.to_tokens(s) + self.constraint.to_tokens_with_context(s, context) } } impl ToTokens for TableConstraint { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::PrimaryKey { columns, @@ -1395,7 +1574,7 @@ impl ToTokens for TableConstraint { s.append(TK_PRIMARY, None)?; s.append(TK_KEY, None)?; s.append(TK_LP, None)?; - comma(columns, s)?; + comma(columns, s, context)?; if *auto_increment { s.append(TK_AUTOINCR, None)?; } @@ -1403,7 +1582,7 @@ impl ToTokens for TableConstraint { if let Some(conflict_clause) = conflict_clause { s.append(TK_ON, None)?; s.append(TK_CONFLICT, None)?; - conflict_clause.to_tokens(s)?; + conflict_clause.to_tokens_with_context(s, context)?; } Ok(()) } @@ -1413,19 +1592,19 @@ impl ToTokens for TableConstraint { } => { s.append(TK_UNIQUE, None)?; s.append(TK_LP, None)?; - comma(columns, s)?; + comma(columns, s, context)?; s.append(TK_RP, None)?; if let Some(conflict_clause) = conflict_clause { s.append(TK_ON, None)?; s.append(TK_CONFLICT, None)?; - conflict_clause.to_tokens(s)?; + conflict_clause.to_tokens_with_context(s, context)?; } Ok(()) } Self::Check(expr) => { s.append(TK_CHECK, None)?; s.append(TK_LP, None)?; - expr.to_tokens(s)?; + expr.to_tokens_with_context(s, context)?; s.append(TK_RP, None) } Self::ForeignKey { @@ -1436,12 +1615,12 @@ impl ToTokens for TableConstraint { s.append(TK_FOREIGN, None)?; s.append(TK_KEY, None)?; s.append(TK_LP, None)?; - comma(columns, s)?; + comma(columns, s, context)?; s.append(TK_RP, None)?; s.append(TK_REFERENCES, None)?; - clause.to_tokens(s)?; + clause.to_tokens_with_context(s, context)?; if let Some(deref_clause) = deref_clause { - deref_clause.to_tokens(s)?; + deref_clause.to_tokens_with_context(s, context)?; } Ok(()) } @@ -1450,7 +1629,11 @@ impl ToTokens for TableConstraint { } impl ToTokens for SortOrder { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append( match self { Self::Asc => TK_ASC, @@ -1462,7 +1645,11 @@ impl ToTokens for SortOrder { } impl ToTokens for NullsOrder { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append(TK_NULLS, None)?; s.append( match self { @@ -1475,48 +1662,60 @@ impl ToTokens for NullsOrder { } impl ToTokens for ForeignKeyClause { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.tbl_name.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.tbl_name.to_tokens_with_context(s, context)?; if let Some(ref columns) = self.columns { s.append(TK_LP, None)?; - comma(columns, s)?; + comma(columns, s, context)?; s.append(TK_RP, None)?; } for arg in &self.args { - arg.to_tokens(s)?; + arg.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for RefArg { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::OnDelete(ref action) => { s.append(TK_ON, None)?; s.append(TK_DELETE, None)?; - action.to_tokens(s) + action.to_tokens_with_context(s, context) } Self::OnInsert(ref action) => { s.append(TK_ON, None)?; s.append(TK_INSERT, None)?; - action.to_tokens(s) + action.to_tokens_with_context(s, context) } Self::OnUpdate(ref action) => { s.append(TK_ON, None)?; s.append(TK_UPDATE, None)?; - action.to_tokens(s) + action.to_tokens_with_context(s, context) } Self::Match(ref name) => { s.append(TK_MATCH, None)?; - name.to_tokens(s) + name.to_tokens_with_context(s, context) } } } } impl ToTokens for RefAct { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { match self { Self::SetNull => { s.append(TK_SET, None)?; @@ -1537,20 +1736,28 @@ impl ToTokens for RefAct { } impl ToTokens for DeferSubclause { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { if !self.deferrable { s.append(TK_NOT, None)?; } s.append(TK_DEFERRABLE, None)?; if let Some(init_deferred) = self.init_deferred { - init_deferred.to_tokens(s)?; + init_deferred.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for InitDeferredPred { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append(TK_INITIALLY, None)?; s.append( match self { @@ -1563,26 +1770,34 @@ impl ToTokens for InitDeferredPred { } impl ToTokens for IndexedColumn { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.col_name.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.col_name.to_tokens_with_context(s, context)?; if let Some(ref collation_name) = self.collation_name { s.append(TK_COLLATE, None)?; - collation_name.to_tokens(s)?; + collation_name.to_tokens_with_context(s, context)?; } if let Some(order) = self.order { - order.to_tokens(s)?; + order.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for Indexed { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::IndexedBy(ref name) => { s.append(TK_INDEXED, None)?; s.append(TK_BY, None)?; - name.to_tokens(s) + name.to_tokens_with_context(s, context) } Self::NotIndexed => { s.append(TK_NOT, None)?; @@ -1593,37 +1808,49 @@ impl ToTokens for Indexed { } impl ToTokens for SortedColumn { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.expr.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.expr.to_tokens_with_context(s, context)?; if let Some(ref order) = self.order { - order.to_tokens(s)?; + order.to_tokens_with_context(s, context)?; } if let Some(ref nulls) = self.nulls { - nulls.to_tokens(s)?; + nulls.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for Limit { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { s.append(TK_LIMIT, None)?; - self.expr.to_tokens(s)?; + self.expr.to_tokens_with_context(s, context)?; if let Some(ref offset) = self.offset { s.append(TK_OFFSET, None)?; - offset.to_tokens(s)?; + offset.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for InsertBody { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Select(select, upsert) => { - select.to_tokens(s)?; + select.to_tokens_with_context(s, context)?; if let Some(upsert) = upsert { - upsert.to_tokens(s)?; + upsert.to_tokens_with_context(s, context)?; } Ok(()) } @@ -1636,29 +1863,37 @@ impl ToTokens for InsertBody { } impl ToTokens for Set { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { if self.col_names.len() == 1 { - comma(self.col_names.deref(), s)?; + comma(self.col_names.deref(), s, context)?; } else { s.append(TK_LP, None)?; - comma(self.col_names.deref(), s)?; + comma(self.col_names.deref(), s, context)?; s.append(TK_RP, None)?; } s.append(TK_EQ, None)?; - self.expr.to_tokens(s) + self.expr.to_tokens_with_context(s, context) } } impl ToTokens for PragmaBody { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Equals(value) => { s.append(TK_EQ, None)?; - value.to_tokens(s) + value.to_tokens_with_context(s, context) } Self::Call(value) => { s.append(TK_LP, None)?; - value.to_tokens(s)?; + value.to_tokens_with_context(s, context)?; s.append(TK_RP, None) } } @@ -1666,7 +1901,11 @@ impl ToTokens for PragmaBody { } impl ToTokens for TriggerTime { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { match self { Self::Before => s.append(TK_BEFORE, None), Self::After => s.append(TK_AFTER, None), @@ -1679,7 +1918,11 @@ impl ToTokens for TriggerTime { } impl ToTokens for TriggerEvent { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Delete => s.append(TK_DELETE, None), Self::Insert => s.append(TK_INSERT, None), @@ -1687,14 +1930,18 @@ impl ToTokens for TriggerEvent { Self::UpdateOf(ref col_names) => { s.append(TK_UPDATE, None)?; s.append(TK_OF, None)?; - comma(col_names.deref(), s) + comma(col_names.deref(), s, context) } } } } impl ToTokens for TriggerCmd { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Update(update) => { let TriggerCmdUpdate { @@ -1707,18 +1954,18 @@ impl ToTokens for TriggerCmd { s.append(TK_UPDATE, None)?; if let Some(or_conflict) = or_conflict { s.append(TK_OR, None)?; - or_conflict.to_tokens(s)?; + or_conflict.to_tokens_with_context(s, context)?; } - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; s.append(TK_SET, None)?; - comma(sets, s)?; + comma(sets, s, context)?; if let Some(from) = from { s.append(TK_FROM, None)?; - from.to_tokens(s)?; + from.to_tokens_with_context(s, context)?; } if let Some(where_clause) = where_clause { s.append(TK_WHERE, None)?; - where_clause.to_tokens(s)?; + where_clause.to_tokens_with_context(s, context)?; } Ok(()) } @@ -1737,43 +1984,47 @@ impl ToTokens for TriggerCmd { s.append(TK_INSERT, None)?; if let Some(or_conflict) = or_conflict { s.append(TK_OR, None)?; - or_conflict.to_tokens(s)?; + or_conflict.to_tokens_with_context(s, context)?; } } s.append(TK_INTO, None)?; - tbl_name.to_tokens(s)?; + tbl_name.to_tokens_with_context(s, context)?; if let Some(col_names) = col_names { s.append(TK_LP, None)?; - comma(col_names.deref(), s)?; + comma(col_names.deref(), s, context)?; s.append(TK_RP, None)?; } - select.to_tokens(s)?; + select.to_tokens_with_context(s, context)?; if let Some(upsert) = upsert { - upsert.to_tokens(s)?; + upsert.to_tokens_with_context(s, context)?; } if let Some(returning) = returning { s.append(TK_RETURNING, None)?; - comma(returning, s)?; + comma(returning, s, context)?; } Ok(()) } Self::Delete(delete) => { s.append(TK_DELETE, None)?; s.append(TK_FROM, None)?; - delete.tbl_name.to_tokens(s)?; + delete.tbl_name.to_tokens_with_context(s, context)?; if let Some(where_clause) = &delete.where_clause { s.append(TK_WHERE, None)?; - where_clause.to_tokens(s)?; + where_clause.to_tokens_with_context(s, context)?; } Ok(()) } - Self::Select(select) => select.to_tokens(s), + Self::Select(select) => select.to_tokens_with_context(s, context), } } } impl ToTokens for ResolveType { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append( match self { Self::Rollback => TK_ROLLBACK, @@ -1788,21 +2039,29 @@ impl ToTokens for ResolveType { } impl ToTokens for With { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { s.append(TK_WITH, None)?; if self.recursive { s.append(TK_RECURSIVE, None)?; } - comma(&self.ctes, s) + comma(&self.ctes, s, context) } } impl ToTokens for CommonTableExpr { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.tbl_name.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.tbl_name.to_tokens_with_context(s, context)?; if let Some(ref columns) = self.columns { s.append(TK_LP, None)?; - comma(columns, s)?; + comma(columns, s, context)?; s.append(TK_RP, None)?; } s.append(TK_AS, None)?; @@ -1817,19 +2076,23 @@ impl ToTokens for CommonTableExpr { } }; s.append(TK_LP, None)?; - self.select.to_tokens(s)?; + self.select.to_tokens_with_context(s, context)?; s.append(TK_RP, None) } } impl ToTokens for Type { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self.size { None => s.append(TK_ID, Some(&self.name)), Some(ref size) => { s.append(TK_ID, Some(&self.name))?; // TODO check there is no forbidden chars s.append(TK_LP, None)?; - size.to_tokens(s)?; + size.to_tokens_with_context(s, context)?; s.append(TK_RP, None) } } @@ -1837,20 +2100,28 @@ impl ToTokens for Type { } impl ToTokens for TypeSize { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { - Self::MaxSize(size) => size.to_tokens(s), + Self::MaxSize(size) => size.to_tokens_with_context(s, context), Self::TypeSize(size1, size2) => { - size1.to_tokens(s)?; + size1.to_tokens_with_context(s, context)?; s.append(TK_COMMA, None)?; - size2.to_tokens(s) + size2.to_tokens_with_context(s, context) } } } } impl ToTokens for TransactionType { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append( match self { Self::Deferred => TK_DEFERRED, @@ -1863,44 +2134,56 @@ impl ToTokens for TransactionType { } impl ToTokens for Upsert { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { s.append(TK_ON, None)?; s.append(TK_CONFLICT, None)?; if let Some(ref index) = self.index { - index.to_tokens(s)?; + index.to_tokens_with_context(s, context)?; } - self.do_clause.to_tokens(s)?; + self.do_clause.to_tokens_with_context(s, context)?; if let Some(ref next) = self.next { - next.to_tokens(s)?; + next.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for UpsertIndex { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { s.append(TK_LP, None)?; - comma(&self.targets, s)?; + comma(&self.targets, s, context)?; s.append(TK_RP, None)?; if let Some(ref where_clause) = self.where_clause { s.append(TK_WHERE, None)?; - where_clause.to_tokens(s)?; + where_clause.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for UpsertDo { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::Set { sets, where_clause } => { s.append(TK_DO, None)?; s.append(TK_UPDATE, None)?; s.append(TK_SET, None)?; - comma(sets, s)?; + comma(sets, s, context)?; if let Some(where_clause) = where_clause { s.append(TK_WHERE, None)?; - where_clause.to_tokens(s)?; + where_clause.to_tokens_with_context(s, context)?; } Ok(()) } @@ -1913,83 +2196,107 @@ impl ToTokens for UpsertDo { } impl ToTokens for FunctionTail { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { if let Some(ref filter_clause) = self.filter_clause { s.append(TK_FILTER, None)?; s.append(TK_LP, None)?; s.append(TK_WHERE, None)?; - filter_clause.to_tokens(s)?; + filter_clause.to_tokens_with_context(s, context)?; s.append(TK_RP, None)?; } if let Some(ref over_clause) = self.over_clause { s.append(TK_OVER, None)?; - over_clause.to_tokens(s)?; + over_clause.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for Over { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { - Self::Window(ref window) => window.to_tokens(s), - Self::Name(ref name) => name.to_tokens(s), + Self::Window(ref window) => window.to_tokens_with_context(s, context), + Self::Name(ref name) => name.to_tokens_with_context(s, context), } } } impl ToTokens for WindowDef { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.name.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.name.to_tokens_with_context(s, context)?; s.append(TK_AS, None)?; - self.window.to_tokens(s) + self.window.to_tokens_with_context(s, context) } } impl ToTokens for Window { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { s.append(TK_LP, None)?; if let Some(ref base) = self.base { - base.to_tokens(s)?; + base.to_tokens_with_context(s, context)?; } if let Some(ref partition_by) = self.partition_by { s.append(TK_PARTITION, None)?; s.append(TK_BY, None)?; - comma(partition_by, s)?; + comma(partition_by, s, context)?; } if let Some(ref order_by) = self.order_by { s.append(TK_ORDER, None)?; s.append(TK_BY, None)?; - comma(order_by, s)?; + comma(order_by, s, context)?; } if let Some(ref frame_clause) = self.frame_clause { - frame_clause.to_tokens(s)?; + frame_clause.to_tokens_with_context(s, context)?; } s.append(TK_RP, None) } } impl ToTokens for FrameClause { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { - self.mode.to_tokens(s)?; + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { + self.mode.to_tokens_with_context(s, context)?; if let Some(ref end) = self.end { s.append(TK_BETWEEN, None)?; - self.start.to_tokens(s)?; + self.start.to_tokens_with_context(s, context)?; s.append(TK_AND, None)?; - end.to_tokens(s)?; + end.to_tokens_with_context(s, context)?; } else { - self.start.to_tokens(s)?; + self.start.to_tokens_with_context(s, context)?; } if let Some(ref exclude) = self.exclude { s.append(TK_EXCLUDE, None)?; - exclude.to_tokens(s)?; + exclude.to_tokens_with_context(s, context)?; } Ok(()) } } impl ToTokens for FrameMode { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { s.append( match self { Self::Groups => TK_GROUPS, @@ -2002,18 +2309,22 @@ impl ToTokens for FrameMode { } impl ToTokens for FrameBound { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + context: &C, + ) -> Result<(), S::Error> { match self { Self::CurrentRow => { s.append(TK_CURRENT, None)?; s.append(TK_ROW, None) } Self::Following(value) => { - value.to_tokens(s)?; + value.to_tokens_with_context(s, context)?; s.append(TK_FOLLOWING, None) } Self::Preceding(value) => { - value.to_tokens(s)?; + value.to_tokens_with_context(s, context)?; s.append(TK_PRECEDING, None) } Self::UnboundedFollowing => { @@ -2029,7 +2340,11 @@ impl ToTokens for FrameBound { } impl ToTokens for FrameExclude { - fn to_tokens(&self, s: &mut S) -> Result<(), S::Error> { + fn to_tokens_with_context( + &self, + s: &mut S, + _: &C, + ) -> Result<(), S::Error> { match self { Self::NoOthers => { s.append(TK_NO, None)?; @@ -2045,7 +2360,11 @@ impl ToTokens for FrameExclude { } } -fn comma(items: I, s: &mut S) -> Result<(), S::Error> +pub fn comma( + items: I, + s: &mut S, + context: &C, +) -> Result<(), S::Error> where I: IntoIterator, I::Item: ToTokens, @@ -2055,32 +2374,15 @@ where if i != 0 { s.append(TK_COMMA, None)?; } - item.to_tokens(s)?; + item.to_tokens_with_context(s, context)?; } Ok(()) } // TK_ID: [...] / `...` / "..." / some keywords / non keywords -fn double_quote(name: &str, s: &mut S) -> Result<(), S::Error> { +fn double_quote(name: &str, s: &mut S) -> Result<(), S::Error> { if name.is_empty() { return s.append(TK_ID, Some("\"\"")); } - if is_identifier(name) { - // identifier must be quoted when they match a keyword... - /*if is_keyword(name) { - f.write_char('`')?; - f.write_str(name)?; - return f.write_char('`'); - }*/ - return s.append(TK_ID, Some(name)); - } - /*f.write_char('"')?; - for c in name.chars() { - if c == '"' { - f.write_char(c)?; - } - f.write_char(c)?; - } - f.write_char('"')*/ s.append(TK_ID, Some(name)) } diff --git a/vendored/sqlite3-parser/src/parser/ast/mod.rs b/vendored/sqlite3-parser/src/parser/ast/mod.rs index 630c1063c..9c661e5bc 100644 --- a/vendored/sqlite3-parser/src/parser/ast/mod.rs +++ b/vendored/sqlite3-parser/src/parser/ast/mod.rs @@ -14,7 +14,7 @@ use indexmap::{IndexMap, IndexSet}; use crate::custom_err; use crate::dialect::TokenType::{self, *}; -use crate::dialect::{from_token, is_identifier, Token}; +use crate::dialect::{from_token, Token}; use crate::parser::{parse::YYCODETYPE, ParserError}; /// `?` or `$` Prepared statement arg placeholder(s)