Skip to main content

rudb_parse/
transform.rs

1//! From the parse tree to the AST.
2//!
3//! This is the one module that reads rule names out of the vendored grammar, and that is deliberate
4//! containment: an upstream bump that renames a rule breaks a match arm here and nothing else in
5//! the repository. `spec/04-architecture.md` section 4.5 says this transformer is ours and has to
6//! be total over the rule table, and total is the load bearing word. Every rule reaches a defined
7//! answer. For the ones this milestone covers that answer is an AST node, and for the rest it is a
8//! `Not implemented` error naming the construct, which is what DuckDB itself answers for syntax it
9//! parses and does not support. There is no arm that panics and none that silently drops a clause,
10//! because a dropped clause is a wrong answer and a wrong answer is worse than an error.
11//!
12//! The mechanism that makes it tractable is the default arm. Two thirds of the parse tree is the
13//! expression precedence chain, twenty rules of the form `X <- Y Tail*` that exist to make the
14//! grammar unambiguous and that carry no meaning once it has been parsed. Rather than name all
15//! twenty, the expression walker handles the case where a rule matched something interesting and
16//! otherwise descends through any node with exactly one child. That is not a shortcut. It is the
17//! statement that a rule with one child said nothing, which is true of every chain link, and it
18//! means the twenty first precedence level upstream adds costs us nothing.
19
20use std::collections::HashMap;
21
22use rudb_common::{Error, IdentifierCase, Result, Span, Value};
23
24use crate::ast::{
25    AlterAction, Ast, Attach, BinaryOp, CaseArm, ColumnDef, Conflict, ConflictAction, Constraint,
26    CopyTo, CreateTable, CreateView, Cte, Distinct, DropTable, Expr, ExprRef, Index, Insert,
27    JoinKind, LiteralKind, Nulls, Order, OrderItem, Quantifier, Query, QueryBody, QueryRef, Scope,
28    Select, SelectRef, SetOp, Setting, Slice, Source, SourceRef, Statement, StrRef, Target,
29    Transaction, UnaryOp, WindowBound, WindowExclude, WindowRef, WindowSpec, WindowUnit,
30};
31use crate::generated::rules::PROGRAM;
32use crate::matcher::{NONE, Tree, parse_tokens};
33use crate::token::{Kind, Token};
34use crate::tokenize::tokenize;
35
36/// Parse a script and transform it into the AST.
37///
38/// The tokens are produced once and handed to both halves. Calling [`crate::parse`] here instead
39/// would be shorter and would tokenize the query a second time, which `cargo xtask bench` prices
40/// at about a tenth of the whole front end.
41pub fn parse_ast(query: &str) -> Result<Ast> {
42    parse_ast_with_case(query, IdentifierCase::Preserve)
43}
44
45/// Parse a script while folding its unquoted identifiers for this session.
46pub fn parse_ast_with_case(query: &str, identifier_case: IdentifierCase) -> Result<Ast> {
47    let tokens = tokenize(query)?;
48    let tree = parse_tokens(query, &tokens, PROGRAM, true)?;
49    transform_with_case(query, &tokens, &tree, identifier_case)
50}
51
52/// Transform a parse tree that has already been produced.
53pub fn transform(query: &str, tokens: &[Token], tree: &Tree) -> Result<Ast> {
54    transform_with_case(query, tokens, tree, IdentifierCase::Preserve)
55}
56
57/// Transform a parse tree while folding its unquoted identifiers for this session.
58pub fn transform_with_case(
59    query: &str,
60    tokens: &[Token],
61    tree: &Tree,
62    identifier_case: IdentifierCase,
63) -> Result<Ast> {
64    let mut transform = Transform {
65        query,
66        tokens,
67        tree,
68        ast: Ast::default(),
69        interned: HashMap::new(),
70        anonymous: 0,
71        identifier_case,
72        current_span: Span::new(0, 0),
73        ctes: Vec::new(),
74        named_windows: Vec::new(),
75        query_depth: 0,
76    };
77    transform.program(tree.root())?;
78    Ok(transform.ast)
79}
80
81/// Whether a bare `PRAGMA name` is a statement rather than a query.
82///
83/// This is a question about shape and not about meaning, which is why it is answered here and the
84/// catalog answers the rest. `PRAGMA version` returns rows and `PRAGMA disable_optimizer` returns
85/// none, and the difference between the two is visible from the name alone on all thirty eight the
86/// pin has: the ones that do something are the `enable_` and `disable_` pairs, plus `force_checkpoint`
87/// and `verify_parallelism`, which are the two that toggle a flag without saying so in the name.
88///
89/// A name of that shape that is not one the engine knows still reaches the catalog, and the catalog
90/// says the same thing about it that it says about a missing `pragma_*` function. That is why this
91/// can be a rule about spelling rather than a second copy of the list: being wrong here means the
92/// error arrives from one place instead of another and says the same sentence either way.
93fn is_statement(name: &str) -> bool {
94    let folded = name.to_ascii_lowercase();
95    folded.starts_with("enable_")
96        || folded.starts_with("disable_")
97        || folded == "force_checkpoint"
98        || folded == "verify_parallelism"
99        || folded == "device_card_refresh"
100}
101
102/// One `FOREIGN KEY` as the transform collects it: the columns, the referenced table's name parts
103/// and the referenced columns.
104type Foreign = (Slice, Slice, Slice);
105
106/// Where the constraints of a `CREATE TABLE` are collected: the keys, which of them is primary,
107/// the checks and the foreign keys.
108type Constraints<'c> = (
109    &'c mut Vec<Slice>,
110    &'c mut u32,
111    &'c mut Vec<ExprRef>,
112    &'c mut Vec<Foreign>,
113    &'c mut Vec<Constraint>,
114);
115
116struct Transform<'a> {
117    query: &'a str,
118    tokens: &'a [Token],
119    tree: &'a Tree,
120    ast: Ast,
121    interned: HashMap<String, StrRef>,
122    /// How many bare `?` parameters have been seen, which is what numbers the next one.
123    anonymous: u32,
124    identifier_case: IdentifierCase,
125    current_span: Span,
126    /// Non-recursive CTEs visible while their containing query is transformed.
127    ///
128    /// A plain reference becomes an ordinary subquery source here. That is the inlined shape the
129    /// binder already understands, and keeping it at this boundary avoids teaching every later name
130    /// resolver about a second kind of relation. A materialised one cannot be inlined, because the
131    /// point of it is that it runs once, so it stays a definition and its references stay
132    /// references. Both kinds are in one list because shadowing does not care which kind a name is.
133    ctes: Vec<(StrRef, Held, Slice)>,
134    /// Windows named by a `WINDOW` clause, with whether the definition wrote a frame.
135    ///
136    /// Scoped the way the CTE list is scoped, and for the same reason. A subquery written inside a
137    /// select block can use that block's names, which was measured: the inner half of
138    /// `SELECT (SELECT sum(j) OVER w FROM s) FROM t WINDOW w AS (ORDER BY j)` resolves `w` on the
139    /// reference binary and comes back out of the catalog with it inlined.
140    named_windows: Vec<(StrRef, WindowRef, bool)>,
141    /// How many queries deep the one being transformed is, counting itself.
142    ///
143    /// A statement's own query is one, a subquery written inside it is two, and a `WITH`
144    /// definition is one deeper than the query that wrote it. Only [`Transform::worth_holding`]
145    /// reads it, to tell a definition with nothing outside it from one that may name a column of
146    /// the query it sits in.
147    query_depth: usize,
148}
149
150/// What a `WITH` name stands for.
151#[derive(Debug, Clone, Copy)]
152enum Held {
153    /// A plain or `NOT MATERIALIZED` one, put into every place it is named.
154    Inline(QueryRef),
155    /// A `MATERIALIZED` one, which is an index into `Ast::ctes`.
156    Once(u32),
157}
158
159impl<'a> Transform<'a> {
160    // The parts that walk the parse tree without caring what it says.
161
162    /// The text a node covers.
163    fn text(&self, node: u32) -> &'a str {
164        self.tree.text(node, self.query, self.tokens)
165    }
166
167    /// The byte range covered by a parse node.
168    fn span(&self, node: u32) -> Span {
169        let parsed = self.tree.node(node);
170        if parsed.start >= parsed.end {
171            let at = self
172                .tokens
173                .get(parsed.start as usize)
174                .map_or(self.query.len() as u32, |token| token.start);
175            return Span::new(at, at);
176        }
177        let first = self.tokens[parsed.start as usize];
178        let last = self.tokens[parsed.end as usize - 1];
179        Span::new(first.start, last.end)
180    }
181
182    /// The name of the rule a node is.
183    fn name(&self, node: u32) -> &'static str {
184        self.tree.name(node)
185    }
186
187    /// The children of a node.
188    ///
189    /// Returned with the tree's lifetime rather than the borrow of `self`, so that the caller can
190    /// iterate it while calling the `&mut self` methods that build the arena. Copying the `&Tree`
191    /// out first is what buys that, and it is why every walker here starts by doing so.
192    fn kids(&self, node: u32) -> impl Iterator<Item = u32> + use<'a> {
193        let tree = self.tree;
194        tree.children(node)
195    }
196
197    /// How many children a node has.
198    fn count(&self, node: u32) -> usize {
199        self.kids(node).count()
200    }
201
202    /// The n'th child, or `NONE`.
203    fn nth(&self, node: u32, n: usize) -> u32 {
204        self.kids(node).nth(n).unwrap_or(NONE)
205    }
206
207    /// The first child, or `NONE`.
208    fn first(&self, node: u32) -> u32 {
209        self.nth(node, 0)
210    }
211
212    /// The first child named `name`, or `NONE`.
213    ///
214    /// Optional parts of a sequence do not leave a placeholder behind, so `SimpleSelect` with a
215    /// `WHERE` and no `GROUP BY` has the where clause as its second child and a `SimpleSelect` with
216    /// neither has something else there. Positional indexing into an optional sequence is the
217    /// single easiest way to write a transformer that is subtly wrong, so nothing here does it.
218    fn find(&self, node: u32, name: &str) -> u32 {
219        self.kids(node).find(|&kid| self.name(kid) == name).unwrap_or(NONE)
220    }
221
222    /// The first node named `name` anywhere under `node`, or `NONE`.
223    fn descendant(&self, node: u32, name: &str) -> u32 {
224        if self.name(node) == name {
225            return node;
226        }
227        self.kids(node)
228            .map(|kid| self.descendant(kid, name))
229            .find(|&found| found != NONE)
230            .unwrap_or(NONE)
231    }
232
233    /// Whether a subtree contains a node with this rule name.
234    fn contains(&self, node: u32, name: &str) -> bool {
235        self.name(node) == name || self.kids(node).any(|kid| self.contains(kid, name))
236    }
237
238    /// Every leaf of a subtree, in order.
239    ///
240    /// A leaf is a rule that matched only terminals, which for a name is the identifier itself. It
241    /// is how all thirty odd spellings of a qualified name collapse into one walk: whether the
242    /// parse said `SchemaQualification ReservedTableQualification ReservedColumnName` or
243    /// `IdentifierDot IdentifierDot ColumnName`, the leaves are the parts in order.
244    fn leaves(&self, node: u32, out: &mut Vec<u32>) {
245        let mut any = false;
246        for kid in self.kids(node) {
247            any = true;
248            self.leaves(kid, &mut *out);
249        }
250        if !any {
251            out.push(node);
252        }
253    }
254
255    // The parts that build the arena.
256
257    /// Intern a string, returning its index.
258    fn intern(&mut self, text: &str) -> StrRef {
259        if let Some(&index) = self.interned.get(text) {
260            return index;
261        }
262        let index = u32::try_from(self.ast.strings.len())
263            .map_err(|_| Error::internal("more than four billion strings in one query"))
264            .unwrap_or(NONE);
265        self.ast.strings.push(text.to_string());
266        self.interned.insert(text.to_string(), index);
267        index
268    }
269
270    /// Push an expression and return its index.
271    fn push(&mut self, expr: Expr) -> ExprRef {
272        let index = self.ast.exprs.len() as u32;
273        self.ast.exprs.push(expr);
274        self.ast.expr_spans.push(self.current_span);
275        index
276    }
277
278    /// Push a from item and return its index.
279    fn push_source(&mut self, source: Source) -> SourceRef {
280        let index = self.ast.sources.len() as u32;
281        self.ast.sources.push(source);
282        index
283    }
284
285    /// Push a query and return its index.
286    fn push_query(&mut self, query: Query) -> QueryRef {
287        let index = self.ast.queries.len() as u32;
288        self.ast.queries.push(query);
289        self.ast.query_spans.push(self.current_span);
290        index
291    }
292
293    /// Push a select and return its index.
294    fn push_select(&mut self, select: Select) -> SelectRef {
295        let index = self.ast.selects.len() as u32;
296        self.ast.selects.push(select);
297        index
298    }
299
300    /// Push a window and return its index.
301    fn push_window(&mut self, spec: WindowSpec) -> WindowRef {
302        let index = self.ast.windows.len() as u32;
303        self.ast.windows.push(spec);
304        index
305    }
306
307    /// Turn a vector of order by entries into a slice of the order item arena.
308    fn order_slice(&mut self, items: Vec<OrderItem>) -> Slice {
309        let start = self.ast.order_items.len() as u32;
310        self.ast.order_items.extend(items);
311        Slice { start, len: self.ast.order_items.len() as u32 - start }
312    }
313
314    /// Turn a vector of expressions into a slice of the expression list arena.
315    fn expr_slice(&mut self, items: Vec<ExprRef>) -> Slice {
316        let start = self.ast.expr_lists.len() as u32;
317        self.ast.expr_lists.extend(items);
318        Slice { start, len: self.ast.expr_lists.len() as u32 - start }
319    }
320
321    /// Turn a vector of strings into a slice of the name arena.
322    fn part_slice(&mut self, items: Vec<StrRef>) -> Slice {
323        let start = self.ast.parts.len() as u32;
324        self.ast.parts.extend(items);
325        Slice { start, len: self.ast.parts.len() as u32 - start }
326    }
327
328    /// Turn a vector of materialised `WITH` indexes into a slice of the list pool.
329    fn cte_slice(&mut self, items: Vec<u32>) -> Slice {
330        let start = self.ast.cte_lists.len() as u32;
331        self.ast.cte_lists.extend(items);
332        Slice { start, len: self.ast.cte_lists.len() as u32 - start }
333    }
334
335    /// Turn a vector of column definitions into a slice of the column arena.
336    fn column_def_slice(&mut self, items: Vec<ColumnDef>) -> Slice {
337        let start = self.ast.column_defs.len() as u32;
338        self.ast.column_defs.extend(items);
339        Slice { start, len: self.ast.column_defs.len() as u32 - start }
340    }
341
342    /// Turn a vector of targets into a slice of the target arena.
343    fn target_slice(&mut self, items: Vec<Target>) -> Slice {
344        let start = self.ast.targets.len() as u32;
345        self.ast.targets.extend(items);
346        Slice { start, len: self.ast.targets.len() as u32 - start }
347    }
348
349    /// Turn a vector of qualified names into a slice of the name list arena.
350    fn name_list_slice(&mut self, items: Vec<Slice>) -> Slice {
351        let start = self.ast.name_lists.len() as u32;
352        self.ast.name_lists.extend(items);
353        Slice { start, len: self.ast.name_lists.len() as u32 - start }
354    }
355
356    /// The error for a construct the transformer does not cover yet.
357    ///
358    /// Both halves matter. The text is what the user wrote, which is the only part they can act on,
359    /// and the rule name is what we act on, because it is the exact grammar rule to go implement.
360    fn unsupported<T>(&self, node: u32) -> Result<T> {
361        let text = self.text(node);
362        let text = if text.chars().count() > 60 {
363            let cut = text.char_indices().nth(60).map_or(text.len(), |(at, _)| at);
364            format!("{}...", &text[..cut])
365        } else {
366            text.to_string()
367        };
368        Err(Error::not_implemented(format!(
369            "{text} is not supported yet, the grammar rule is {}",
370            self.name(node)
371        )))
372    }
373
374    // Names.
375
376    /// One identifier out of a subtree, with the quoting and any trailing dot removed.
377    fn identifier(&mut self, node: u32) -> StrRef {
378        let mut leaves = Vec::new();
379        self.leaves(node, &mut leaves);
380        let text = leaves.last().map_or("", |&leaf| self.text(leaf));
381        let text = self.fold_identifier(text.strip_suffix('.').unwrap_or(text));
382        self.intern(&text)
383    }
384
385    /// The one part of a name written with nothing qualifying it, folded the way a name is folded.
386    ///
387    /// `None` for a name with a schema or a table in front of it, which is the same test
388    /// [`Transform::inner_table_ref`] makes before it looks a name up in the `WITH` list, since a
389    /// definition is reachable by its bare name and by nothing else.
390    fn bare_name(&self, node: u32) -> Option<String> {
391        let mut leaves = Vec::new();
392        self.leaves(node, &mut leaves);
393        let mut parts = leaves
394            .iter()
395            .map(|&leaf| self.text(leaf))
396            .filter(|text| !text.is_empty() && *text != "*");
397        let only = parts.next()?;
398        if parts.next().is_some() {
399            return None;
400        }
401        Some(self.fold_identifier(only.strip_suffix('.').unwrap_or(only)))
402    }
403
404    /// Every part of a qualified name, outermost first.
405    fn name_parts(&mut self, node: u32) -> Slice {
406        let mut leaves = Vec::new();
407        self.leaves(node, &mut leaves);
408        let mut parts = Vec::with_capacity(leaves.len());
409        for leaf in leaves {
410            let text = self.text(leaf);
411            // A node that covers no tokens is an optional part that was not written, and a bare
412            // `*` is the star and not a name part. Neither is a component of anything.
413            if text.is_empty() || text == "*" {
414                continue;
415            }
416            let text = self.fold_identifier(text.strip_suffix('.').unwrap_or(text));
417            let interned = self.intern(&text);
418            parts.push(interned);
419        }
420        self.part_slice(parts)
421    }
422
423    fn fold_identifier(&self, text: &str) -> String {
424        if text.starts_with(['"', '\'']) {
425            return unquote(text);
426        }
427        match self.identifier_case {
428            IdentifierCase::Preserve => text.to_string(),
429            IdentifierCase::Lower => text.to_ascii_lowercase(),
430            IdentifierCase::Upper => text.to_ascii_uppercase(),
431        }
432    }
433
434    // Statements.
435
436    /// `Program <- TopLevelStatement*`.
437    fn program(&mut self, node: u32) -> Result<()> {
438        for top in self.kids(node) {
439            // A script that ends in a semicolon produces a last `TopLevelStatement` whose only
440            // child is the end of input, because the grammar says `Statement? (';'+ / EndOfInput)`
441            // and both halves of that are happy to match nothing. It is a real node and it is not a
442            // statement, so it is dropped here rather than pretended away in the matcher.
443            let Some(statement) = self.kids(top).find(|&kid| self.name(kid) == "Statement") else {
444                continue;
445            };
446            let statement = self.statement(statement)?;
447            self.ast.statements.push(statement);
448        }
449        Ok(())
450    }
451
452    /// `Statement <- SelectStatement / ...`, twenty seven alternatives of which ten are done.
453    fn statement(&mut self, node: u32) -> Result<Statement> {
454        let inner = self.first(node);
455        match self.name(inner) {
456            "SelectStatement" => {
457                let query = self.query(self.first(inner))?;
458                Ok(Statement::Query(query))
459            }
460            "CreateStatement" => self.create_statement(inner),
461            "DropStatement" => self.drop_statement(inner),
462            "AlterStatement" => self.alter_statement(inner),
463            "InsertStatement" | "UpdateStatement" | "DeleteStatement" => {
464                self.write_statement(inner)
465            }
466            "TruncateStatement" => {
467                let name = self.name_parts(self.find(inner, "BaseTableName"));
468                self.changed_rows(inner, name, NONE, Vec::new(), true)
469            }
470            "SetStatement" => self.set_statement(inner),
471            "ResetStatement" => self.reset_statement(inner),
472            "UseStatement" => self.use_statement(inner),
473            "PragmaStatement" => self.pragma_statement(inner),
474            "ExplainStatement" => self.explain_statement(inner),
475            "CheckpointStatement" => {
476                let name = self.find(inner, "CatalogName");
477                let name = if name == NONE { NONE } else { self.identifier(name) };
478                Ok(Statement::Checkpoint(name))
479            }
480            "AttachStatement" => self.attach_statement(inner),
481            "DetachStatement" => {
482                let if_exists = self.find(inner, "IfExists") != NONE;
483                let name = self.identifier(self.find(inner, "CatalogName"));
484                Ok(Statement::Detach { name, if_exists })
485            }
486            "CopyStatement" => self.copy_statement(inner),
487            "TransactionStatement" => {
488                let kind = self.first(inner);
489                Ok(Statement::Transaction(match self.name(kind) {
490                    "BeginTransaction" => {
491                        let mode = self.find(kind, "ReadOrWrite");
492                        let read_only = mode != NONE && self.descendant(mode, "ReadOnly") != NONE;
493                        Transaction::Begin { read_only }
494                    }
495                    "CommitTransaction" => Transaction::Commit,
496                    _ => Transaction::Rollback,
497                }))
498            }
499            "CallStatement" => {
500                let query = self.call_query(inner)?;
501                Ok(Statement::Query(query))
502            }
503            _ => self.unsupported(inner),
504        }
505    }
506
507    /// `ExplainStatement <- 'EXPLAIN' AnalyzeKeyword? ExplainOptionList? ExplainableStatements`.
508    ///
509    /// Of the twenty one explainable statements, the one that is done is the query. The other
510    /// twenty either do not exist here yet or have nothing to show: a plan is what `EXPLAIN`
511    /// prints, and a `SET` has no plan. An `INSERT` has a plan for its source and showing that
512    /// would answer a question nobody asked, since the source is not what the statement does.
513    ///
514    /// Four of the option names are answered and the rest are refused. `ANALYZE` in the list is
515    /// the keyword written the other way and DuckDB takes both, `LOGICAL` names the plan this
516    /// already prints, and `STATISTICS` asks for the section that says what the planner knew, which
517    /// is what `spec/stats/05-every-query.md` section 5.1.1 asks `EXPLAIN` to print. `CODEGEN` is
518    /// ours and asks for what the compiled engine generated, per `spec/compiler/16-observability.md`.
519    /// Anything else,
520    /// `FORMAT JSON` above all, asks for the plan in a shape nothing here writes, and answering it
521    /// with the text form would be answering a different question quietly.
522    ///
523    /// The refusal is `Unimplemented explain type` with the name in lower case, which is word for
524    /// word what DuckDB 1.5 says for an option name it parses and does not answer. It says it for
525    /// `LOGICAL` and `STATISTICS` as well, so those two are a divergence in the direction of doing
526    /// something: a query that errors there runs here, and nothing that works there stops working.
527    /// `FORMAT` is a divergence the other way, since DuckDB answers it and this does not, which is
528    /// the same refusal as before this could read an option list at all.
529    fn explain_statement(&mut self, node: u32) -> Result<Statement> {
530        let mut analyze = self.find(node, "AnalyzeKeyword") != NONE;
531        let mut statistics = false;
532        let mut codegen = false;
533        let list = self.find(node, "ExplainOptionList");
534        if list != NONE {
535            for option in self.kids(list).filter(|&kid| self.name(kid) == "ExplainOption") {
536                let name = self.text(self.find(option, "ExplainOptionName"));
537                match name.to_ascii_lowercase().as_str() {
538                    "analyze" => analyze = true,
539                    "logical" => {}
540                    "statistics" => statistics = true,
541                    "codegen" => codegen = true,
542                    lowered => {
543                        return Err(Error::not_implemented(format!(
544                            "Unimplemented explain type: {lowered}"
545                        )));
546                    }
547                }
548                // An option carries a value in the grammar and none of these three has one to
549                // carry, so an option with one is refused rather than read for its name alone.
550                // DuckDB takes `(ANALYZE false)` and analyzes anyway, and doing the opposite of
551                // what somebody wrote is worse than saying no to it.
552                if self.count(option) != 1 {
553                    return self.unsupported(option);
554                }
555            }
556        }
557        let inner = self.first(self.find(node, "ExplainableStatements"));
558        let query = match self.name(inner) {
559            "ExplainSelectStatement" => self.query(self.find(inner, "SelectStatementInternal"))?,
560            // A call is a query with the `SELECT *` left off, so it has the plan the query has and
561            // there is no reason for the two spellings to differ about what `EXPLAIN` prints.
562            "CallStatement" => self.call_query(inner)?,
563            _ => return self.unsupported(inner),
564        };
565        // The generated code is printed instead of the plan, so there is nothing for `ANALYZE` or
566        // `STATISTICS` to add to, and taking them would print something other than what they ask.
567        if codegen && (analyze || statistics) {
568            return Err(Error::not_implemented(
569                "EXPLAIN (CODEGEN) cannot be combined with ANALYZE or STATISTICS",
570            ));
571        }
572        Ok(Statement::Explain { query, analyze, statistics, codegen })
573    }
574
575    /// `CallStatement <- 'CALL' QualifiedTableFunction TableFunctionArguments`, which is the table
576    /// function in the `FROM` clause with the clause left off.
577    ///
578    /// The two sub-rules are the same two the `FROM` clause form reads, so this is one statement
579    /// written two ways and not two things that resemble each other. It becomes the query the long
580    /// spelling would have produced, which is how the pragma call is handled a few hundred lines up
581    /// and for the same reason: one plan means one set of answers, and a second path through the
582    /// binder for a statement that does the same work is a place for the two to drift apart.
583    ///
584    /// The rule has no alias and no `WITH ORDINALITY`, so there is nothing here to turn away. What
585    /// the function is called and whether it exists are the binder's questions, and a name that is
586    /// not a table function gets the binder's own words about it rather than a parse error, which
587    /// is what the other spelling gets.
588    fn call_query(&mut self, node: u32) -> Result<QueryRef> {
589        let name = self.name_parts(self.find(node, "QualifiedTableFunction"));
590        let mut args = Vec::new();
591        // `TableFunctionArguments <- Parens(List(FunctionArgument)?)`, so `CALL f()` has the
592        // wrapper with no list under it and comes through here with no arguments.
593        for kid in self.kids(self.find(node, "TableFunctionArguments")) {
594            args.push(self.table_argument(kid)?);
595        }
596        let args = self.target_slice(args);
597        let source = self.push_source(Source::Function {
598            name,
599            args,
600            alias: NONE,
601            columns: Slice::default(),
602            pragma: false,
603        });
604        Ok(self.star_over(source))
605    }
606
607    /// `SetStatement <- 'SET' SetAssignmentOrTimeZone`.
608    ///
609    /// `SET SCHEMA 'name'` is the `schema` setting written another way, and `SET TIME ZONE` is the
610    /// `TimeZone` one.
611    fn set_statement(&mut self, node: u32) -> Result<Statement> {
612        let inner = self.first(self.find(node, "SetAssignmentOrTimeZone"));
613        if self.name(inner) == "SetTimeZone" {
614            return self.set_time_zone(inner);
615        }
616        if self.name(inner) == "SetSchema" {
617            let text = self.string_value(self.find(inner, "StringLiteral"))?;
618            return Ok(self.set_schema(&text));
619        }
620        if self.name(inner) != "StandardAssignment" {
621            return self.unsupported(inner);
622        }
623        let (name, scope) = self.setting_name(self.find(inner, "SetVariableOrSetting"))?;
624        let assignment = self.find(inner, "SetAssignment");
625        let list = self.find(assignment, "VariableList");
626        let kids: Vec<u32> = self.kids(list).collect();
627        if kids.len() == 1 && self.contains(list, "DefaultExpression") {
628            let index = self.ast.settings.len() as u32;
629            self.ast.settings.push(Setting { name, scope, value: NONE, pragma: false });
630            return Ok(Statement::Reset(index));
631        }
632        let mut values = Vec::new();
633        for kid in kids {
634            values.push(self.expr(kid)?);
635        }
636        // The grammar takes a list because `SET search_path = a, b` is a list in postgres. The pin
637        // refuses one from the parser, and `search_path` takes its list as one string instead.
638        let [value] = values[..] else {
639            return Err(Error::parser("SET can only contain a single value"));
640        };
641        let index = self.ast.settings.len() as u32;
642        self.ast.settings.push(Setting { name, scope, value, pragma: false });
643        Ok(Statement::Set(index))
644    }
645
646    /// `ATTACH [OR REPLACE] [IF NOT EXISTS] [DATABASE] path [AS alias] [(options)]`.
647    ///
648    /// The options are the generic copy option list, a name with a value or without one, and what
649    /// each name means is the layer above's business, the same as for a setting.
650    fn attach_statement(&mut self, node: u32) -> Result<Statement> {
651        let path = self.expr(self.first(self.find(node, "DatabasePath")))?;
652        let alias = self.find(node, "AttachAlias");
653        let alias = if alias == NONE { NONE } else { self.identifier(self.find(alias, "ColId")) };
654        let mut names = Vec::new();
655        let mut values = Vec::new();
656        let options = self.find(node, "AttachOptions");
657        if options != NONE {
658            let mut found = Vec::new();
659            self.named_nodes(options, "GenericCopyOption", &mut found);
660            for option in found {
661                let name = self.identifier(self.find(option, "CopyOptionName"));
662                let value = self.find(option, "GenericCopyOptionValue");
663                let value = if value == NONE {
664                    NONE
665                } else {
666                    let inner = self.first(value);
667                    if self.name(inner) != "GenericCopyOptionExpression" {
668                        return self.unsupported(inner);
669                    }
670                    self.expr(self.first(inner))?
671                };
672                names.push(name);
673                values.push(value);
674            }
675        }
676        let names = self.part_slice(names);
677        let values = self.expr_slice(values);
678        let index = self.ast.attaches.len() as u32;
679        self.ast.attaches.push(Attach {
680            path,
681            alias,
682            or_replace: self.find(node, "OrReplace") != NONE,
683            if_not_exists: self.find(node, "IfNotExists") != NONE,
684            names,
685            values,
686        });
687        Ok(Statement::Attach(index))
688    }
689
690    /// A `SET schema` to this text, which is what `SET SCHEMA 'name'` and `USE` both come to.
691    fn set_schema(&mut self, text: &str) -> Statement {
692        let name = self.intern("schema");
693        let text = self.intern(text);
694        let value = self.push(Expr::Literal { kind: LiteralKind::String, text });
695        let index = self.ast.settings.len() as u32;
696        self.ast.settings.push(Setting { name, scope: Scope::Unwritten, value, pragma: false });
697        Statement::Set(index)
698    }
699
700    /// `UseStatement <- 'USE' UseTarget`, which the pin turns into a `SET schema` to the name
701    /// written back out, so `USE db` and `USE db.s` land where `SET schema` would.
702    fn use_statement(&mut self, node: u32) -> Result<Statement> {
703        let target = self.first(self.find(node, "UseTarget"));
704        let mut parts = Vec::new();
705        if self.name(target) == "UseTargetCatalogSchema" {
706            if self.contains(target, "DotIdentifier") {
707                return Err(Error::parser("Expected \"USE database\" or \"USE database.schema\""));
708            }
709            for rule in ["CatalogName", "ReservedSchemaName"] {
710                let part = self.identifier(self.find(target, rule));
711                parts.push(crate::quoted(self.ast.string(part)));
712            }
713        } else {
714            let part = self.identifier(target);
715            parts.push(crate::quoted(self.ast.string(part)));
716        }
717        Ok(self.set_schema(&parts.join(".")))
718    }
719
720    /// `SET TIME ZONE value`, normalized to the `TimeZone` setting DuckDB exposes beside it.
721    fn set_time_zone(&mut self, node: u32) -> Result<Statement> {
722        let zone = self.first(self.find(node, "ZoneValue"));
723        let name = self.intern("TimeZone");
724        if matches!(self.name(zone), "ZoneDefault" | "ZoneLocal") {
725            let index = self.ast.settings.len() as u32;
726            self.ast.settings.push(Setting {
727                name,
728                scope: Scope::Unwritten,
729                value: NONE,
730                pragma: false,
731            });
732            return Ok(Statement::Reset(index));
733        }
734        let text = match self.name(zone) {
735            "ZoneStringLiteral" => self.string_value(self.find(zone, "StringLiteral"))?,
736            "ZoneIdentifier" => {
737                let identifier = self.find(zone, "Identifier");
738                let identifier = self.identifier(identifier);
739                self.ast.string(identifier).to_string()
740            }
741            _ => return self.unsupported(zone),
742        };
743        let text = self.intern(&text);
744        let value = self.push(Expr::Literal { kind: LiteralKind::String, text });
745        let index = self.ast.settings.len() as u32;
746        self.ast.settings.push(Setting { name, scope: Scope::Unwritten, value, pragma: false });
747        Ok(Statement::Set(index))
748    }
749
750    /// `ResetStatement <- 'RESET' SetVariableOrSetting`.
751    fn reset_statement(&mut self, node: u32) -> Result<Statement> {
752        let (name, scope) = self.setting_name(self.find(node, "SetVariableOrSetting"))?;
753        let index = self.ast.settings.len() as u32;
754        self.ast.settings.push(Setting { name, scope, value: NONE, pragma: false });
755        Ok(Statement::Reset(index))
756    }
757
758    /// `PragmaStatement <- 'PRAGMA' PragmaAssignOrFunction`, which is two statements in one word.
759    ///
760    /// `PRAGMA memory_limit = '1GB'` is a `SET` with a different spelling and nothing else, so it
761    /// lands on the same [`Statement::Set`] and the same setting arena entry. The scope is
762    /// unwritten because the grammar has no room for one here, which is the same thing as a plain
763    /// `SET` with no scope word.
764    ///
765    /// `PRAGMA version` is a query. Upstream rewrites it to `SELECT * FROM pragma_version()` and
766    /// gives that away in its own error messages, which print the rewritten call back, so the
767    /// rewrite happens here rather than being a statement kind the planner has to know about. The
768    /// whole family comes out of it for free: an unknown pragma is the catalog's complaint, a bad
769    /// argument is the function's, and the answer is a relation like any other.
770    fn pragma_statement(&mut self, node: u32) -> Result<Statement> {
771        let inner = self.first(self.find(node, "PragmaAssignOrFunction"));
772        match self.name(inner) {
773            "PragmaAssign" => self.pragma_assign(inner),
774            "PragmaFunction" => self.pragma_function(inner),
775            _ => self.unsupported(inner),
776        }
777    }
778
779    /// `PragmaAssign <- SettingName '=' VariableList`, which is a `SET` and is treated as one.
780    fn pragma_assign(&mut self, node: u32) -> Result<Statement> {
781        let name = self.identifier(self.find(node, "SettingName"));
782        let list = self.find(node, "VariableList");
783        let mut values = Vec::new();
784        for kid in self.kids(list) {
785            values.push(self.expr(kid)?);
786        }
787        // The same refusal `set_statement` makes about a list, for the same reason. Nothing here
788        // reads one and taking the first of several would be worse than saying so.
789        let [value] = values[..] else {
790            return self.unsupported(list);
791        };
792        let index = self.ast.settings.len() as u32;
793        self.ast.settings.push(Setting { name, scope: Scope::Unwritten, value, pragma: false });
794        Ok(Statement::Set(index))
795    }
796
797    /// `PragmaFunction <- PragmaName PragmaParameters?`, rewritten into the call it stands for.
798    ///
799    /// The name is written without the prefix and the function carries it, so `PRAGMA table_info`
800    /// is `pragma_table_info`. The case the user wrote is kept rather than folded, because the name
801    /// goes back out in the message about a pragma that does not exist and upstream prints that
802    /// name back as it was typed.
803    ///
804    /// `PRAGMA version()` with empty parentheses is a parser error rather than a call, on both
805    /// engines, and that falls out of the grammar here without anything being done about it:
806    /// `PragmaParameters` is `Parens(List(Expression))` and a list of no expressions does not match.
807    ///
808    /// The other half of the family is not a query at all. `PRAGMA disable_optimizer` writes a
809    /// setting and returns no rows, so it becomes the [`Statement::Set`] it stands for rather than
810    /// a call, with the name carrying both halves of the assignment and [`is_statement`] deciding
811    /// which of the two a pragma is.
812    fn pragma_function(&mut self, node: u32) -> Result<Statement> {
813        let interned = self.identifier(self.find(node, "PragmaName"));
814        let written = self.ast.string(interned).to_string();
815        // The parameters are optional in the rule, so `PRAGMA version` has no node here at all
816        // rather than a node covering nothing.
817        let parameters = self.find(node, "PragmaParameters");
818        if parameters == NONE && is_statement(&written) {
819            let index = self.ast.settings.len() as u32;
820            self.ast.settings.push(Setting {
821                name: interned,
822                scope: Scope::Unwritten,
823                value: NONE,
824                pragma: true,
825            });
826            return Ok(Statement::Set(index));
827        }
828        let part = self.intern(&format!("pragma_{written}"));
829        let name = self.part_slice(vec![part]);
830        let mut args = Vec::new();
831        if parameters != NONE {
832            for kid in self.kids(parameters) {
833                let expr = self.expr(kid)?;
834                args.push(Target { expr: self.quoted(expr), alias: NONE });
835            }
836        }
837        let args = self.target_slice(args);
838        let source = self.push_source(Source::Function {
839            name,
840            args,
841            alias: NONE,
842            columns: Slice::default(),
843            pragma: true,
844        });
845        Ok(Statement::Query(self.star_over(source)))
846    }
847
848    /// A bare name in a pragma's parentheses is the name of a thing and not a column reference.
849    ///
850    /// `PRAGMA table_info(t)` and `PRAGMA table_info('t')` are the same statement on the pin, and
851    /// so are `PRAGMA table_info(s.u)` and `PRAGMA table_info('s.u')`, because there is no `FROM`
852    /// clause here for a column to come out of. Only a name is turned: `PRAGMA table_info(1)` stays
853    /// an integer and is told there is no overload that takes one, which is what the pin says too.
854    fn quoted(&mut self, expr: ExprRef) -> ExprRef {
855        let Expr::Column { name } = self.ast.exprs[expr as usize] else {
856            return expr;
857        };
858        let written: Vec<&str> = self.ast.name(name).collect();
859        let joined = written.join(".");
860        let text = self.intern(&joined);
861        self.push(Expr::Literal { kind: LiteralKind::String, text })
862    }
863
864    /// `SetVariableOrSetting <- SetVariable / SetSetting`, where the setting carries a scope word.
865    ///
866    /// `SET VARIABLE x = 1` is the other alternative and is a different feature: a variable is a
867    /// value the session holds and `getvariable` reads back, where a setting is a knob on the
868    /// engine. Refused rather than treated as a setting of that name.
869    fn setting_name(&mut self, node: u32) -> Result<(StrRef, Scope)> {
870        let inner = self.first(node);
871        if self.name(inner) != "SetSetting" {
872            return self.unsupported(inner);
873        }
874        let written = self.find(inner, "SettingScope");
875        let scope = if written == NONE {
876            Scope::Unwritten
877        } else {
878            match self.name(self.first(written)) {
879                "GlobalScope" => Scope::Global,
880                "SessionScope" => Scope::Session,
881                "LocalScope" => Scope::Local,
882                _ => return self.unsupported(written),
883            }
884        };
885        Ok((self.identifier(self.find(inner, "SettingName")), scope))
886    }
887
888    /// `CreateStatement <- 'CREATE' OrReplace? Temporary? CreateStatementVariation`.
889    ///
890    /// Of the nine variations, `CreateTableStmt` and `CreateViewStmt` are the ones that are done.
891    /// The other seven are a macro, a sequence, a type, a schema, an index, a secret and a trigger,
892    /// and each of them is a catalog entry this database has no room for yet.
893    fn create_statement(&mut self, node: u32) -> Result<Statement> {
894        let or_replace = self.find(node, "OrReplace") != NONE;
895        let temporary = self.find(node, "Temporary") != NONE;
896        let variation = self.find(node, "CreateStatementVariation");
897        let inner = self.first(variation);
898        // duckdb refuses this pair in the parser, with a caret under the `NOT`, because none of its
899        // create rules has room for both. The vendored grammar has room for both, so the refusal is
900        // here instead, which is the same stage and therefore the same sentence.
901        if or_replace && self.find(inner, "IfNotExists") != NONE {
902            return Err(Error::parser(
903                "Cannot specify both OR REPLACE and IF NOT EXISTS within single create statement",
904            ));
905        }
906        match self.name(inner) {
907            "CreateTableStmt" => self.create_table_statement(inner, or_replace, temporary),
908            "CreateViewStmt" => self.create_view_statement(inner, or_replace, temporary),
909            "CreateSchemaStmt" => {
910                let name = self.name_parts(self.find(inner, "QualifiedName"));
911                let quiet = self.find(inner, "IfNotExists") != NONE;
912                let schema = crate::ast::Schema {
913                    name,
914                    drop: false,
915                    quiet,
916                    or_replace,
917                    temporary,
918                    cascade: false,
919                };
920                Ok(self.schema_statement(schema))
921            }
922            "CreateSequenceStmt" => self.create_sequence_statement(inner, or_replace, temporary),
923            "CreateTypeStmt" => {
924                // `CreateType <- EnumSelectType / EnumStringLiteralList / CreateTypeFromType`. A
925                // list of strings is the text of an `ENUM` type as it stands, and an `ENUM` over a
926                // query is not something this engine makes yet.
927                let made = self.first(self.find(inner, "CreateType"));
928                let text = match self.name(made) {
929                    "CreateTypeFromType" => self.text(self.first(made)).to_string(),
930                    "EnumStringLiteralList" => self.text(made).to_string(),
931                    _ => return self.unsupported(made),
932                };
933                let made = crate::ast::TypeDef {
934                    name: self.name_parts(self.find(inner, "QualifiedName")),
935                    drop: false,
936                    quiet: self.find(inner, "IfNotExists") != NONE,
937                    or_replace,
938                    temporary,
939                    cascade: false,
940                    ty: self.intern(&text),
941                };
942                Ok(self.type_statement(made))
943            }
944            "CreateIndexStmt" => self.create_index_statement(inner, or_replace, temporary),
945            _ => self.unsupported(inner),
946        }
947    }
948
949    /// `CreateIndexStmt <- UniqueIndex? 'INDEX' IfNotExists? IndexName? 'ON' BaseTableName
950    /// InsertColumnList? IndexType? Parens(List(IndexElement))? WithList? WhereClause?`.
951    ///
952    /// The refusals are the pin's, at the stage the pin gives them. `ON t(a)` matches the column
953    /// list and `ON t(a DESC)` or `ON t((a + 1))` the element list, and both are elements here. An
954    /// order on an element is dropped, as the pin drops it, and so are the `WITH` options.
955    fn create_index_statement(
956        &mut self,
957        inner: u32,
958        or_replace: bool,
959        temporary: bool,
960    ) -> Result<Statement> {
961        if temporary {
962            return Err(Error::parser("Temporary indexes are not supported"));
963        }
964        if self.find(inner, "WhereClause") != NONE {
965            return Err(Error::not_implemented(
966                "Creating partial indexes is not supported currently",
967            ));
968        }
969        let named = self.find(inner, "IndexName");
970        if named == NONE {
971            return Err(Error::not_implemented(
972                "Please provide an index name, e.g., CREATE INDEX my_name ...",
973            ));
974        }
975        let name = self.name_parts(named);
976        let table = self.name_parts(self.find(inner, "BaseTableName"));
977        let mut elements = Vec::new();
978        let list = self.find(inner, "InsertColumnList");
979        if list == NONE {
980            let mut found = Vec::new();
981            self.named_nodes(inner, "IndexElement", &mut found);
982            for element in found {
983                let expr = self.expr(self.find(element, "Expression"))?;
984                if let Expr::Binary { op: BinaryOp::Collate, .. } = self.ast.exprs[expr as usize] {
985                    return Err(Error::not_implemented("Index with collation not supported yet!"));
986                }
987                elements.push(expr);
988            }
989        } else {
990            for kid in self.kids(self.find(list, "ColumnList")).collect::<Vec<_>>() {
991                let part = self.identifier(kid);
992                let name = self.part_slice(vec![part]);
993                elements.push(self.push(Expr::Column { name }));
994            }
995        }
996        let kind = self.find(inner, "IndexType");
997        let using = if kind == NONE {
998            NONE
999        } else {
1000            let text = self.text(self.find(kind, "Identifier")).to_string();
1001            let text = self.fold_identifier(&text);
1002            self.intern(&text)
1003        };
1004        let index = Index {
1005            name,
1006            table,
1007            drop: false,
1008            quiet: self.find(inner, "IfNotExists") != NONE,
1009            unique: self.find(inner, "UniqueIndex") != NONE,
1010            or_replace,
1011            using,
1012            elements: self.expr_slice(elements),
1013        };
1014        Ok(self.index_statement(index))
1015    }
1016
1017    fn index_statement(&mut self, index: Index) -> Statement {
1018        let at = self.ast.indexes.len() as u32;
1019        self.ast.indexes.push(index);
1020        Statement::Index(at)
1021    }
1022
1023    /// `CreateSequenceStmt <- 'SEQUENCE' IfNotExists? QualifiedName SequenceOption*`.
1024    ///
1025    /// The options are settled here the way the pin's transformer settles them, which is where
1026    /// every one of its refusals of a bad combination comes from.
1027    fn create_sequence_statement(
1028        &mut self,
1029        inner: u32,
1030        or_replace: bool,
1031        temporary: bool,
1032    ) -> Result<Statement> {
1033        let name = self.name_parts(self.find(inner, "QualifiedName"));
1034        let quiet = self.find(inner, "IfNotExists") != NONE;
1035        // Each option under the key the pin files it under, with its value: `None` for a NULL,
1036        // and 1 or 0 for `CYCLE` and `NO CYCLE`.
1037        let mut given: Vec<(&'static str, Option<i64>)> = Vec::new();
1038        let written: Vec<u32> =
1039            self.kids(inner).filter(|&kid| self.name(kid) == "SequenceOption").collect();
1040        for option in written {
1041            let option = self.first(option);
1042            let (key, value) = match self.name(option) {
1043                "SeqSetCycle" => {
1044                    ("cycle", Some(i64::from(self.name(self.first(option)) == "SeqCycle")))
1045                }
1046                "SeqSetIncrement" => {
1047                    ("increment", self.sequence_value(self.find(option, "Expression"), true)?)
1048                }
1049                "SeqSetMinMax" => {
1050                    let which = self.first(self.find(option, "SeqMinOrMax"));
1051                    let key = if self.name(which) == "MinValue" { "minvalue" } else { "maxvalue" };
1052                    (key, self.sequence_value(self.find(option, "Expression"), true)?)
1053                }
1054                "SeqNoMinMax" => {
1055                    let which = self.first(self.find(option, "SeqMinOrMax"));
1056                    let key =
1057                        if self.name(which) == "MinValue" { "nominvalue" } else { "nomaxvalue" };
1058                    (key, None)
1059                }
1060                "SeqStartWith" => {
1061                    ("start", self.sequence_value(self.find(option, "Expression"), false)?)
1062                }
1063                "SeqOwnedBy" => ("owned", None),
1064                _ => return self.unsupported(option),
1065            };
1066            if given.iter().any(|(held, _)| *held == key) {
1067                let mut capital = key.to_string();
1068                capital[..1].make_ascii_uppercase();
1069                return Err(Error::parser(format!("{capital} should be passed at most once")));
1070            }
1071            given.push((key, value));
1072        }
1073        let has = |key: &str| given.iter().any(|(held, _)| *held == key);
1074        let no_min = has("nominvalue");
1075        if no_min && has("minvalue") {
1076            return Err(Error::parser("Minvalue should be passed at most once"));
1077        }
1078        let no_max = has("nomaxvalue");
1079        if no_max && has("maxvalue") {
1080            return Err(Error::parser("Maxvalue should be passed at most once"));
1081        }
1082        if has("owned") {
1083            return Err(Error::parser("Unrecognized option \"owned\" for CREATE SEQUENCE"));
1084        }
1085        let value =
1086            |key: &str| given.iter().find(|(held, _)| *held == key).map(|(_, value)| *value);
1087        let mut options = rudb_common::sequence::Options {
1088            increment: 1,
1089            min: 1,
1090            max: i64::MAX,
1091            start: 1,
1092            // flatten: an option that may be missing and may be given without a number.
1093            cycle: value("cycle").flatten() == Some(1),
1094        };
1095        let min = if no_min { None } else { value("minvalue") };
1096        let max = if no_max { None } else { value("maxvalue") };
1097        if let Some(increment) = value("increment") {
1098            let increment = increment.ok_or_else(|| Error::parser("INCREMENT must not be NULL"))?;
1099            if increment == 0 {
1100                return Err(Error::parser("Increment must not be zero"));
1101            }
1102            options.increment = increment;
1103            if increment < 0 {
1104                options.min = i64::MIN;
1105                options.max = -1;
1106            }
1107        }
1108        if let Some(min) = min {
1109            options.min = min.ok_or_else(|| Error::parser("MINVALUE must not be NULL"))?;
1110        }
1111        if let Some(max) = max {
1112            options.max = max.ok_or_else(|| Error::parser("MAXVALUE must not be NULL"))?;
1113        }
1114        options.start = match value("start") {
1115            Some(start) => start.ok_or_else(|| Error::parser("START value must not be NULL"))?,
1116            None if options.increment < 0 => options.max,
1117            None => options.min,
1118        };
1119        if options.max <= options.min {
1120            return Err(Error::parser(format!(
1121                "MINVALUE ({}) must be less than MAXVALUE ({})",
1122                options.min, options.max
1123            )));
1124        }
1125        if options.start < options.min {
1126            return Err(Error::parser(format!(
1127                "START value ({}) cannot be less than MINVALUE ({})",
1128                options.start, options.min
1129            )));
1130        }
1131        if options.start > options.max {
1132            return Err(Error::parser(format!(
1133                "START value ({}) cannot be greater than MAXVALUE ({})",
1134                options.start, options.max
1135            )));
1136        }
1137        let sequence = crate::ast::Sequence {
1138            name,
1139            drop: false,
1140            quiet,
1141            or_replace,
1142            temporary,
1143            cascade: false,
1144            options,
1145            owner: Slice::default(),
1146        };
1147        Ok(self.sequence_statement(sequence))
1148    }
1149
1150    /// The value of one sequence option, `None` for a NULL.
1151    ///
1152    /// Only a constant is taken. `minus` says a minus in front of one is taken too, which the pin
1153    /// allows for `INCREMENT`, `MINVALUE` and `MAXVALUE` and reads by negating the first thing the
1154    /// minus applies to, so `5 - 1` is read as -5 there just as it is here.
1155    fn sequence_value(&mut self, node: u32, minus: bool) -> Result<Option<i64>> {
1156        let expr = self.expr(node)?;
1157        self.constant_value(expr, minus)
1158    }
1159
1160    fn constant_value(&self, expr: ExprRef, minus: bool) -> Result<Option<i64>> {
1161        let negated = |operand: ExprRef| -> Result<Option<i64>> {
1162            if !matches!(self.ast.expr(operand), Expr::Literal { .. }) {
1163                return Err(Error::invalid_input(
1164                    "Expected constant expression as child of minus function",
1165                ));
1166            }
1167            Ok(self.constant_value(operand, false)?.map(i64::wrapping_neg))
1168        };
1169        match self.ast.expr(expr) {
1170            Expr::Literal { kind: LiteralKind::Null, .. } => Ok(None),
1171            Expr::Literal { kind: LiteralKind::True, .. } => Ok(Some(1)),
1172            Expr::Literal { kind: LiteralKind::False, .. } => Ok(Some(0)),
1173            Expr::Literal { kind: LiteralKind::Number, text } => {
1174                let text = self.ast.string(text);
1175                text.parse::<i64>()
1176                    .ok()
1177                    .or_else(|| {
1178                        text.parse::<f64>()
1179                            .ok()
1180                            .filter(|value| value.abs() < 9.2e18)
1181                            .map(|value| value.round() as i64)
1182                    })
1183                    .map(Some)
1184                    .ok_or_else(|| {
1185                        Error::conversion(format!(
1186                            "Type DECIMAL with value {text} can't be cast because the value is out \
1187                             of range for the destination type INT64"
1188                        ))
1189                    })
1190            }
1191            Expr::Literal { kind: LiteralKind::String, text } => {
1192                let text = self.ast.string(text);
1193                text.trim().parse::<i64>().map(Some).map_err(|_| {
1194                    Error::invalid_input(format!("Could not convert string '{text}' to INT64"))
1195                })
1196            }
1197            Expr::Unary { op: UnaryOp::Negate, operand } => negated(operand),
1198            Expr::Binary { op: BinaryOp::Subtract, left, .. } if minus => negated(left),
1199            Expr::Binary { op, .. } if minus => {
1200                let name = match op {
1201                    BinaryOp::Add => "+",
1202                    BinaryOp::Multiply => "*",
1203                    BinaryOp::Divide => "/",
1204                    BinaryOp::IntegerDivide => "//",
1205                    BinaryOp::Modulo => "%",
1206                    BinaryOp::Power => "**",
1207                    BinaryOp::Caret => "^",
1208                    BinaryOp::Concat => "||",
1209                    _ => return Err(Error::parser("Expected constant expression.")),
1210                };
1211                Err(Error::invalid_input(format!(
1212                    "Expected a minus function instead of \"{name}\""
1213                )))
1214            }
1215            _ => Err(Error::parser("Expected constant expression.")),
1216        }
1217    }
1218
1219    /// `ALTER SEQUENCE name OWNED BY table`, the one `ALTER` there is so far.
1220    ///
1221    /// The pin reads only the `OWNED BY` out of a list of options, so any others written beside it
1222    /// are dropped without a word, and a list with no `OWNED BY` in it is not implemented there.
1223    fn alter_statement(&mut self, inner: u32) -> Result<Statement> {
1224        let stmt = self.first(self.find(inner, "AlterOptions"));
1225        match self.name(stmt) {
1226            "AlterTableStmt" => return self.alter_table(stmt),
1227            "AlterViewStmt" => {
1228                let to = self.identifier(self.find(self.find(stmt, "RenameAlter"), "Identifier"));
1229                let alter = crate::ast::Alter {
1230                    name: self.name_parts(self.find(stmt, "BaseTableName")),
1231                    quiet: self.find(stmt, "IfExists") != NONE,
1232                    view: true,
1233                    action: AlterAction::Rename { to },
1234                };
1235                return Ok(self.alter_entry(alter));
1236            }
1237            "AlterSchemaStmt" => {
1238                return Err(Error::not_implemented("Altering schemas is not yet supported"));
1239            }
1240            "AlterSequenceStmt" => {}
1241            _ => return self.unsupported(inner),
1242        }
1243        let set = self.first(self.find(stmt, "AlterSequenceOptions"));
1244        if self.name(set) != "SetSequenceOption" {
1245            return self.unsupported(inner);
1246        }
1247        let written: Vec<u32> =
1248            self.kids(set).filter(|&kid| self.name(kid) == "SequenceOption").collect();
1249        let mut owner = None;
1250        for option in written {
1251            let option = self.first(option);
1252            if self.name(option) != "SeqOwnedBy" {
1253                continue;
1254            }
1255            if owner.is_some() {
1256                return Err(Error::parser("Owned by value should be passed at most once"));
1257            }
1258            owner = Some(self.name_parts(self.find(option, "QualifiedName")));
1259        }
1260        let Some(owner) = owner else {
1261            return Err(Error::not_implemented("ALTER SEQUENCE option not yet supported"));
1262        };
1263        let sequence = crate::ast::Sequence {
1264            name: self.name_parts(self.find(stmt, "QualifiedSequenceName")),
1265            drop: false,
1266            quiet: self.find(stmt, "IfExists") != NONE,
1267            or_replace: false,
1268            temporary: false,
1269            cascade: false,
1270            options: rudb_common::sequence::Options::default(),
1271            owner,
1272        };
1273        Ok(self.sequence_statement(sequence))
1274    }
1275
1276    /// `AlterTableStmt <- 'TABLE' IfExists? BaseTableName List(AlterTableOptions)`, with the
1277    /// pin's refusals of the options it does not take, in the order it makes them.
1278    fn alter_table(&mut self, stmt: u32) -> Result<Statement> {
1279        let mut options = Vec::new();
1280        self.named_nodes(stmt, "AlterTableOptions", &mut options);
1281        if options.len() > 1 {
1282            return Err(Error::parser("Only one ALTER command per statement is supported"));
1283        }
1284        let option = self.first(options[0]);
1285        let nested = |this: &Self, node: u32| {
1286            let mut dots = Vec::new();
1287            this.named_nodes(node, "IdentifierDot", &mut dots);
1288            !dots.is_empty()
1289        };
1290        let column = |this: &mut Self, node: u32| {
1291            let name = this.find(node, "NestedColumnName");
1292            this.identifier(this.find(name, "ColumnName"))
1293        };
1294        let action = match self.name(option) {
1295            "RenameAlter" => {
1296                AlterAction::Rename { to: self.identifier(self.find(option, "Identifier")) }
1297            }
1298            "RenameColumn" if !nested(self, option) => {
1299                let at = column(self, option);
1300                AlterAction::RenameColumn {
1301                    column: at,
1302                    to: self.identifier(self.find(option, "Identifier")),
1303                }
1304            }
1305            "AddColumn" => self.add_column(option)?,
1306            "DropColumn" if !nested(self, option) => AlterAction::DropColumn {
1307                column: column(self, option),
1308                quiet: self.find(option, "IfExists") != NONE,
1309            },
1310            "AlterColumn" if !nested(self, option) => {
1311                let at = column(self, option);
1312                let entry = self.first(self.find(option, "AlterColumnEntry"));
1313                self.alter_column(at, entry)?
1314            }
1315            "DropConstraint" => {
1316                return Err(Error::not_implemented("No support for that ALTER TABLE option yet!"));
1317            }
1318            "SetPartitionedBy" | "ResetPartitionedBy" => {
1319                return Err(Error::not_implemented(
1320                    "SET PARTITIONED BY is not supported for DuckDB tables",
1321                ));
1322            }
1323            "SetSortedBy" | "ResetSortedBy" => {
1324                return Err(Error::not_implemented(
1325                    "SET SORTED BY is not supported for DuckDB tables",
1326                ));
1327            }
1328            "SetOptions" => {
1329                return Err(Error::not_implemented(
1330                    "SET (<options>) is not supported for DuckDB tables",
1331                ));
1332            }
1333            "ResetOptions" => {
1334                return Err(Error::not_implemented(
1335                    "RESET (<options>) is not supported for DuckDB tables",
1336                ));
1337            }
1338            _ => return self.unsupported(option),
1339        };
1340        let alter = crate::ast::Alter {
1341            name: self.name_parts(self.find(stmt, "BaseTableName")),
1342            quiet: self.find(stmt, "IfExists") != NONE,
1343            view: false,
1344            action,
1345        };
1346        Ok(self.alter_entry(alter))
1347    }
1348
1349    /// `AddColumn <- 'ADD' 'COLUMN'? IfNotExists? AddColumnEntry`.
1350    ///
1351    /// The pin keeps the type, `NOT NULL` and `DEFAULT` of the definition and drops every other
1352    /// constraint on it without a word, so this does too.
1353    fn add_column(&mut self, option: u32) -> Result<AlterAction> {
1354        let entry = self.find(option, "AddColumnEntry");
1355        let generated = self.find(entry, "GeneratedColumn");
1356        if self.find(entry, "Type") == NONE && generated == NONE {
1357            return Err(Error::parser("Column definition requires a type or generated expression"));
1358        }
1359        if generated != NONE {
1360            return Err(Error::parser(
1361                "Adding generated columns after table creation is not supported yet",
1362            ));
1363        }
1364        let mut defaults = 0;
1365        let mut kept = Vec::new();
1366        for kid in self.kids(entry) {
1367            if self.name(kid) != "ColumnConstraint" {
1368                continue;
1369            }
1370            // The pin keeps these quietly and drops them, and the tests in its tree, written for
1371            // the release after it, refuse them. The tests are what this follows.
1372            let refused = match self.name(self.first(kid)) {
1373                "DefaultValue" => {
1374                    defaults += 1;
1375                    None
1376                }
1377                "NotNullConstraint" => None,
1378                "PrimaryKeyConstraint" => Some("PRIMARY KEY"),
1379                "CheckConstraint" => Some("CHECK"),
1380                "ForeignKeyConstraint" => Some("FOREIGN KEY"),
1381                _ => continue,
1382            };
1383            if let Some(kind) = refused {
1384                return Err(Error::parser(format!(
1385                    "Adding columns with {kind} constraints is not supported yet"
1386                )));
1387            }
1388            kept.push(kid);
1389        }
1390        if defaults > 1 {
1391            return Err(Error::parser("Cannot define a default value twice"));
1392        }
1393        let dotted = self.find(entry, "DottedIdentifier");
1394        let mut parts = Vec::new();
1395        self.leaves(dotted, &mut parts);
1396        if parts.iter().any(|&leaf| self.text(leaf) == ".") {
1397            return self.unsupported(entry);
1398        }
1399        let name = self.identifier(dotted);
1400        let type_node = self.find(entry, "Type");
1401        let text = self.text(type_node).to_string();
1402        let ty = self.intern(&text);
1403        let mut not_null = false;
1404        let mut default = NONE;
1405        for kid in kept {
1406            let constraint = self.first(kid);
1407            if self.name(constraint) == "DefaultValue" {
1408                default = self.expr(self.find(constraint, "ColumnDefaultExpr"))?;
1409            } else {
1410                not_null = self.name(self.first(constraint)) == "NotNullColumnConstraint";
1411            }
1412        }
1413        let quiet = self.find(option, "IfNotExists") != NONE;
1414        if quiet && not_null {
1415            return Err(Error::not_implemented(
1416                "Adding a NOT NULL column with IF NOT EXISTS is not supported",
1417            ));
1418        }
1419        Ok(AlterAction::AddColumn { column: ColumnDef { name, ty, not_null, default }, quiet })
1420    }
1421
1422    /// `AlterColumnEntry <- AddOrDropDefault / ChangeNullability / AlterType`.
1423    fn alter_column(&mut self, column: StrRef, entry: u32) -> Result<AlterAction> {
1424        Ok(match self.name(entry) {
1425            "AddOrDropDefault" => {
1426                let inner = self.first(entry);
1427                let default = if self.name(inner) == "AddDefault" {
1428                    self.expr(self.find(inner, "Expression"))?
1429                } else {
1430                    NONE
1431                };
1432                AlterAction::Default { column, default }
1433            }
1434            "ChangeNullability" => {
1435                let which = self.first(self.find(entry, "DropOrSet"));
1436                AlterAction::NotNull { column, set: self.name(which) == "SetNullability" }
1437            }
1438            "AlterType" => {
1439                let type_node = self.find(entry, "Type");
1440                let using = self.find(entry, "UsingExpression");
1441                if type_node == NONE && using == NONE {
1442                    return Err(Error::parser(
1443                        "Omitting the type is only possible in combination with USING",
1444                    ));
1445                }
1446                let ty = if type_node == NONE {
1447                    NONE
1448                } else {
1449                    let text = self.text(type_node).to_string();
1450                    self.intern(&text)
1451                };
1452                let using =
1453                    if using == NONE { NONE } else { self.expr(self.find(using, "Expression"))? };
1454                AlterAction::Type { column, ty, using }
1455            }
1456            _ => return self.unsupported(entry),
1457        })
1458    }
1459
1460    fn alter_entry(&mut self, alter: crate::ast::Alter) -> Statement {
1461        let index = self.ast.alters.len() as u32;
1462        self.ast.alters.push(alter);
1463        Statement::Alter(index)
1464    }
1465
1466    fn type_statement(&mut self, made: crate::ast::TypeDef) -> Statement {
1467        let index = self.ast.types.len() as u32;
1468        self.ast.types.push(made);
1469        Statement::Type(index)
1470    }
1471
1472    fn sequence_statement(&mut self, sequence: crate::ast::Sequence) -> Statement {
1473        let index = self.ast.sequences.len() as u32;
1474        self.ast.sequences.push(sequence);
1475        Statement::Sequence(index)
1476    }
1477
1478    /// `CreateTableStmt <- 'TABLE' IfNotExists? QualifiedName CreateTableDefinition`.
1479    fn create_table_statement(
1480        &mut self,
1481        inner: u32,
1482        or_replace: bool,
1483        temporary: bool,
1484    ) -> Result<Statement> {
1485        let name = self.name_parts(self.find(inner, "QualifiedName"));
1486        let if_not_exists = self.find(inner, "IfNotExists") != NONE;
1487        let definition = self.find(inner, "CreateTableDefinition");
1488        let body = self.first(definition);
1489        let mut keys = Vec::new();
1490        let mut primary = NONE;
1491        let mut checks = Vec::new();
1492        let mut foreign = Vec::new();
1493        let mut order = Vec::new();
1494        let (columns, query) = match self.name(body) {
1495            "CreateColumnList" => {
1496                let constraints = (&mut keys, &mut primary, &mut checks, &mut foreign, &mut order);
1497                (self.column_list(body, name, constraints)?, NONE)
1498            }
1499            "CreateTableAs" => self.create_table_as(body)?,
1500            _ => return self.unsupported(body),
1501        };
1502        let keys = self.name_list_slice(keys);
1503        let checks = self.expr_slice(checks);
1504        let foreign_tables = self.name_list_slice(foreign.iter().map(|f: &Foreign| f.1).collect());
1505        let foreign_referenced =
1506            self.name_list_slice(foreign.iter().map(|f: &Foreign| f.2).collect());
1507        let foreign = self.name_list_slice(foreign.iter().map(|f: &Foreign| f.0).collect());
1508        let start = self.ast.constraints.len() as u32;
1509        self.ast.constraints.extend(order);
1510        let order = Slice { start, len: self.ast.constraints.len() as u32 - start };
1511        let index = self.ast.create_tables.len() as u32;
1512        self.ast.create_tables.push(CreateTable {
1513            name,
1514            columns,
1515            query,
1516            if_not_exists,
1517            or_replace,
1518            temporary,
1519            keys,
1520            primary,
1521            checks,
1522            foreign,
1523            foreign_tables,
1524            foreign_referenced,
1525            order,
1526        });
1527        Ok(Statement::CreateTable(index))
1528    }
1529
1530    /// `CreateViewStmt <- CreateSecure? CreateRecursive? 'VIEW' IfNotExists? QualifiedName
1531    /// InsertColumnList? WithList? 'AS' SelectStatementInternal`.
1532    ///
1533    /// The body is transformed here as well as kept as text. Transforming it is what makes a view
1534    /// whose body does not parse a parse error at creation, which is where it belongs, and the text
1535    /// is what the catalog keeps so that the body can be bound again at every reference.
1536    fn create_view_statement(
1537        &mut self,
1538        inner: u32,
1539        or_replace: bool,
1540        temporary: bool,
1541    ) -> Result<Statement> {
1542        for kid in self.kids(inner) {
1543            // `SECURE` is a column and row policy, `RECURSIVE` is a different shape of view
1544            // entirely, and `WITH` carries options. Dropping any of the three silently would make a
1545            // view that is not the view that was asked for.
1546            if matches!(self.name(kid), "CreateSecure" | "CreateRecursive" | "WithList") {
1547                return self.unsupported(kid);
1548            }
1549        }
1550        let name = self.name_parts(self.find(inner, "QualifiedName"));
1551        let if_not_exists = self.find(inner, "IfNotExists") != NONE;
1552        let list = self.find(inner, "InsertColumnList");
1553        let columns = if list == NONE {
1554            Slice::default()
1555        } else {
1556            let mut parts = Vec::new();
1557            for kid in self.kids(self.find(list, "ColumnList")) {
1558                parts.push(self.identifier(kid));
1559            }
1560            self.part_slice(parts)
1561        };
1562        let body = self.find(inner, "SelectStatementInternal");
1563        let sql = self.text(body).to_string();
1564        let sql = self.intern(&sql);
1565        let query = self.query(body)?;
1566        let index = self.ast.create_views.len() as u32;
1567        self.ast.create_views.push(CreateView {
1568            name,
1569            columns,
1570            query,
1571            sql,
1572            if_not_exists,
1573            or_replace,
1574            temporary,
1575        });
1576        Ok(Statement::CreateView(index))
1577    }
1578
1579    /// `CreateColumnList <- Parens(CreateTableColumnList?) PartitionSortedOptions? WithList?`.
1580    fn column_list(
1581        &mut self,
1582        node: u32,
1583        table: Slice,
1584        (keys, primary, checks, foreign, order): Constraints<'_>,
1585    ) -> Result<Slice> {
1586        for kid in self.kids(node) {
1587            if matches!(self.name(kid), "PartitionOptions" | "SortedOptions" | "WithList") {
1588                return self.unsupported(kid);
1589            }
1590        }
1591        let list = self.find(node, "CreateTableColumnList");
1592        if list == NONE {
1593            // `CREATE TABLE t ()` parses. It is a table of no columns, and the catalog is entitled
1594            // to refuse it, but that is not this layer's refusal to make.
1595            return Ok(Slice::default());
1596        }
1597        let mut defs = Vec::new();
1598        for element in self.kids(list) {
1599            let inner = self.first(element);
1600            if self.name(inner) == "CreateTableColumnDefinition" {
1601                let at = (defs.len() as u32, keys.len() as u32);
1602                let (def, marks) =
1603                    self.column_definition(self.first(inner), checks, foreign, (order, at))?;
1604                for is_primary in marks {
1605                    let names = self.part_slice(vec![def.name]);
1606                    self.add_key(table, names, is_primary, keys, primary)?;
1607                }
1608                defs.push(def);
1609                continue;
1610            }
1611            // A table level constraint. `FOREIGN KEY` is not enforced anywhere yet and silently
1612            // dropping one is a wrong answer waiting to happen, so it is refused.
1613            let mut found = Vec::new();
1614            self.named_nodes(inner, "TopCheckConstraint", &mut found);
1615            if let Some(&check) = found.first() {
1616                order.push(Constraint::Check(checks.len() as u32));
1617                checks.push(self.check(check)?);
1618                continue;
1619            }
1620            self.named_nodes(inner, "TopForeignKeyConstraint", &mut found);
1621            if let Some(&constraint) = found.first() {
1622                let mut ids = Vec::new();
1623                self.named_nodes(self.find(constraint, "ColumnIdList"), "ColId", &mut ids);
1624                let names: Vec<StrRef> = ids
1625                    .into_iter()
1626                    .map(|id| {
1627                        let text = self.fold_identifier(self.text(id));
1628                        self.intern(&text)
1629                    })
1630                    .collect();
1631                let count = names.len();
1632                let names = self.part_slice(names);
1633                let references = self.find(constraint, "ForeignKeyConstraint");
1634                order.push(Constraint::Foreign(foreign.len() as u32));
1635                foreign.push(self.foreign_key(references, names, count)?);
1636                continue;
1637            }
1638            self.named_nodes(inner, "TopPrimaryKeyConstraint", &mut found);
1639            let is_primary = !found.is_empty();
1640            if !is_primary {
1641                self.named_nodes(inner, "TopUniqueConstraint", &mut found);
1642            }
1643            let Some(&constraint) = found.first() else {
1644                return self.unsupported(inner);
1645            };
1646            let mut found = Vec::new();
1647            self.named_nodes(self.find(constraint, "ColumnIdList"), "ColId", &mut found);
1648            let mut names: Vec<StrRef> = Vec::with_capacity(found.len());
1649            for id in found {
1650                let text = self.fold_identifier(self.text(id));
1651                if names.iter().any(|&held| self.ast.string(held).eq_ignore_ascii_case(&text)) {
1652                    return Err(Error::parser(format!(
1653                        "column \"\"{text}\"\" appears twice in primary key constraint"
1654                    )));
1655                }
1656                names.push(self.intern(&text));
1657            }
1658            let names = self.part_slice(names);
1659            order.push(Constraint::Key(keys.len() as u32));
1660            self.add_key(table, names, is_primary, keys, primary)?;
1661        }
1662        Ok(self.column_def_slice(defs))
1663    }
1664
1665    /// `CheckConstraint <- 'CHECK' Parens(Expression)`, refused the way the pin refuses a subquery in
1666    /// one.
1667    fn check(&mut self, node: u32) -> Result<ExprRef> {
1668        let mut found = Vec::new();
1669        self.named_nodes(node, "SubqueryExpression", &mut found);
1670        if !found.is_empty() {
1671            return Err(Error::parser("subqueries prohibited in CHECK constraints"));
1672        }
1673        let mut found = Vec::new();
1674        self.named_nodes(node, "Expression", &mut found);
1675        let Some(&expr) = found.first() else {
1676            return self.unsupported(node);
1677        };
1678        self.expr(expr)
1679    }
1680
1681    /// `ForeignKeyConstraint <- 'REFERENCES' BaseTableName Parens(ColumnList)? KeyActions`, for a
1682    /// key over these columns of the table being made, refused the way the pin refuses an action
1683    /// other than the default or a column count that does not match.
1684    fn foreign_key(&mut self, node: u32, columns: Slice, count: usize) -> Result<Foreign> {
1685        let mut found = Vec::new();
1686        for action in ["CascadeKeyAction", "SetNullKeyAction", "SetDefaultKeyAction"] {
1687            self.named_nodes(self.find(node, "KeyActions"), action, &mut found);
1688        }
1689        if !found.is_empty() {
1690            return Err(Error::parser(
1691                "FOREIGN KEY constraints cannot use CASCADE, SET NULL or SET DEFAULT",
1692            ));
1693        }
1694        let table = self.name_parts(self.find(node, "BaseTableName"));
1695        let mut lists = Vec::new();
1696        self.named_nodes(node, "ColumnList", &mut lists);
1697        let mut ids = Vec::new();
1698        if let Some(&list) = lists.first() {
1699            self.named_nodes(list, "ColId", &mut ids);
1700        }
1701        if !ids.is_empty() && ids.len() != count {
1702            return Err(Error::parser(
1703                "The number of referencing and referenced columns for foreign keys must be the same",
1704            ));
1705        }
1706        let names: Vec<StrRef> = ids
1707            .into_iter()
1708            .map(|id| {
1709                let text = self.fold_identifier(self.text(id));
1710                self.intern(&text)
1711            })
1712            .collect();
1713        let referenced = self.part_slice(names);
1714        Ok((columns, table, referenced))
1715    }
1716
1717    /// Every node under this one, itself included, with this rule name, in the order written.
1718    fn named_nodes(&self, node: u32, rule: &str, out: &mut Vec<u32>) {
1719        if node == NONE {
1720            return;
1721        }
1722        if self.name(node) == rule {
1723            out.push(node);
1724            return;
1725        }
1726        for kid in self.kids(node) {
1727            self.named_nodes(kid, rule, out);
1728        }
1729    }
1730
1731    /// One more key of a table, refused the way the pin refuses a second primary key.
1732    fn add_key(
1733        &mut self,
1734        table: Slice,
1735        names: Slice,
1736        is_primary: bool,
1737        keys: &mut Vec<Slice>,
1738        primary: &mut u32,
1739    ) -> Result<()> {
1740        if is_primary {
1741            if *primary != NONE {
1742                let table = self.ast.name(table).last().unwrap_or_default().to_string();
1743                return Err(Error::parser(format!(
1744                    "table \"{table}\" has more than one primary key"
1745                )));
1746            }
1747            *primary = keys.len() as u32;
1748        }
1749        keys.push(names);
1750        Ok(())
1751    }
1752
1753    /// `ColumnDefinition <- DottedIdentifier Type? GeneratedColumn? ConstraintNameClause?
1754    /// ColumnConstraint*`.
1755    /// A column and the keys written on it, `true` for a primary key and `false` for a unique one.
1756    fn column_definition(
1757        &mut self,
1758        node: u32,
1759        checks: &mut Vec<ExprRef>,
1760        foreign: &mut Vec<Foreign>,
1761        (order, (column, key_base)): (&mut Vec<Constraint>, (u32, u32)),
1762    ) -> Result<(ColumnDef, Vec<bool>)> {
1763        let name = self.identifier(self.find(node, "DottedIdentifier"));
1764        let type_node = self.find(node, "Type");
1765        let ty = if type_node == NONE {
1766            NONE
1767        } else {
1768            let text = self.text(type_node).to_string();
1769            self.intern(&text)
1770        };
1771        if self.find(node, "GeneratedColumn") != NONE {
1772            return self.unsupported(self.find(node, "GeneratedColumn"));
1773        }
1774        let mut not_null = false;
1775        let mut default = NONE;
1776        let mut keys = Vec::new();
1777        for kid in self.kids(node) {
1778            if self.name(kid) != "ColumnConstraint" {
1779                continue;
1780            }
1781            let constraint = self.first(kid);
1782            match self.name(constraint) {
1783                "NotNullConstraint" => {
1784                    not_null = self.name(self.first(constraint)) == "NotNullColumnConstraint";
1785                    order.retain(|&held| held != Constraint::NotNull(column));
1786                    if not_null {
1787                        order.push(Constraint::NotNull(column));
1788                    }
1789                }
1790                // The key goes in once the column is made, at the place counted here.
1791                "PrimaryKeyConstraint" | "UniqueConstraint" => {
1792                    order.push(Constraint::Key(key_base + keys.len() as u32));
1793                    keys.push(self.name(constraint) == "PrimaryKeyConstraint");
1794                }
1795                "DefaultValue" => {
1796                    default = self.expr(self.find(constraint, "ColumnDefaultExpr"))?;
1797                }
1798                "CheckConstraint" => {
1799                    order.push(Constraint::Check(checks.len() as u32));
1800                    checks.push(self.check(constraint)?);
1801                }
1802                "ForeignKeyConstraint" => {
1803                    let names = self.part_slice(vec![name]);
1804                    order.push(Constraint::Foreign(foreign.len() as u32));
1805                    foreign.push(self.foreign_key(constraint, names, 1)?);
1806                }
1807                _ => return self.unsupported(constraint),
1808            }
1809        }
1810        Ok((ColumnDef { name, ty, not_null, default }, keys))
1811    }
1812
1813    /// `CreateTableAs <- IdentifierList? PartitionSortedOptions? WithList? 'AS' Statement
1814    /// WithData?`.
1815    ///
1816    /// The names in the `IdentifierList` become column definitions with no type, because the types
1817    /// are the query's and only the names are the syntax's to say.
1818    fn create_table_as(&mut self, node: u32) -> Result<(Slice, QueryRef)> {
1819        for kid in self.kids(node) {
1820            if matches!(
1821                self.name(kid),
1822                "PartitionOptions" | "SortedOptions" | "WithList" | "WithData"
1823            ) {
1824                return self.unsupported(kid);
1825            }
1826        }
1827        let names = self.find(node, "IdentifierList");
1828        let columns = if names == NONE {
1829            Slice::default()
1830        } else {
1831            let mut defs = Vec::new();
1832            for kid in self.kids(names) {
1833                let name = self.identifier(kid);
1834                defs.push(ColumnDef { name, ty: NONE, not_null: false, default: NONE });
1835            }
1836            self.column_def_slice(defs)
1837        };
1838        let statement = self.find(node, "Statement");
1839        let inner = self.first(statement);
1840        if self.name(inner) != "SelectStatement" {
1841            return self.unsupported(inner);
1842        }
1843        let query = self.query(self.first(inner))?;
1844        Ok((columns, query))
1845    }
1846
1847    /// `DropStatement <- 'DROP' DropEntries DropBehavior?`.
1848    ///
1849    /// `DropTable <- TableOrView IfExists? List(BaseTableName)`, and `TableOrView` covers `VIEW`
1850    /// and `MATERIALIZED VIEW` as well as `TABLE`, so it is checked rather than assumed. The first
1851    /// two are done and a materialized view is not a thing this database has.
1852    ///
1853    /// `CASCADE` on a table or a view changes nothing, because the pin keeps no dependency between
1854    /// a view and the tables it reads, and a foreign key holds a table in place with or without it.
1855    /// `DropSchema <- 'SCHEMA' IfExists? List(QualifiedName)` is the other rule that is done, where
1856    /// `CASCADE` does mean something, and the pin takes one schema at a time.
1857    fn drop_statement(&mut self, node: u32) -> Result<Statement> {
1858        let behavior = self.find(node, "DropBehavior");
1859        let cascade = behavior != NONE && self.name(self.first(behavior)) == "CascadeDropBehavior";
1860        let entries = self.find(node, "DropEntries");
1861        let inner = self.first(entries);
1862        if self.name(inner) == "DropSchema" {
1863            let names: Vec<u32> =
1864                self.kids(inner).filter(|&kid| self.name(kid) == "QualifiedName").collect();
1865            let [name] = names[..] else {
1866                return Err(Error::not_implemented("Can only drop one object at a time"));
1867            };
1868            let schema = crate::ast::Schema {
1869                name: self.name_parts(name),
1870                drop: true,
1871                quiet: self.find(inner, "IfExists") != NONE,
1872                or_replace: false,
1873                temporary: false,
1874                cascade,
1875            };
1876            return Ok(self.schema_statement(schema));
1877        }
1878        if self.name(inner) == "DropSequence" {
1879            let names: Vec<u32> =
1880                self.kids(inner).filter(|&kid| self.name(kid) == "QualifiedSequenceName").collect();
1881            let [name] = names[..] else {
1882                return Err(Error::not_implemented("Can only drop one object at a time"));
1883            };
1884            let sequence = crate::ast::Sequence {
1885                name: self.name_parts(name),
1886                drop: true,
1887                quiet: self.find(inner, "IfExists") != NONE,
1888                or_replace: false,
1889                temporary: false,
1890                cascade,
1891                options: rudb_common::sequence::Options::default(),
1892                owner: Slice::default(),
1893            };
1894            return Ok(self.sequence_statement(sequence));
1895        }
1896        if self.name(inner) == "DropType" {
1897            let names: Vec<u32> =
1898                self.kids(inner).filter(|&kid| self.name(kid) == "QualifiedTypeName").collect();
1899            let [name] = names[..] else {
1900                return Err(Error::not_implemented("Can only drop one object at a time"));
1901            };
1902            let made = crate::ast::TypeDef {
1903                name: self.name_parts(name),
1904                drop: true,
1905                quiet: self.find(inner, "IfExists") != NONE,
1906                or_replace: false,
1907                temporary: false,
1908                cascade,
1909                ty: NONE,
1910            };
1911            return Ok(self.type_statement(made));
1912        }
1913        if self.name(inner) == "DropIndex" {
1914            let names: Vec<u32> =
1915                self.kids(inner).filter(|&kid| self.name(kid) == "QualifiedIndexName").collect();
1916            let [name] = names[..] else {
1917                return Err(Error::not_implemented("Can only drop one object at a time"));
1918            };
1919            let index = Index {
1920                name: self.name_parts(name),
1921                table: Slice::default(),
1922                drop: true,
1923                quiet: self.find(inner, "IfExists") != NONE,
1924                unique: false,
1925                or_replace: false,
1926                using: NONE,
1927                elements: Slice::default(),
1928            };
1929            return Ok(self.index_statement(index));
1930        }
1931        if self.name(inner) != "DropTable" {
1932            return self.unsupported(inner);
1933        }
1934        let kind = self.find(inner, "TableOrView");
1935        let view = match self.name(self.first(kind)) {
1936            "CommentTable" => false,
1937            "CommentView" => true,
1938            _ => return self.unsupported(kind),
1939        };
1940        let if_exists = self.find(inner, "IfExists") != NONE;
1941        let mut names = Vec::new();
1942        for kid in self.kids(inner) {
1943            if self.name(kid) == "BaseTableName" {
1944                names.push(self.name_parts(kid));
1945            }
1946        }
1947        let names = self.name_list_slice(names);
1948        let index = self.ast.drop_tables.len() as u32;
1949        self.ast.drop_tables.push(DropTable { names, if_exists, view });
1950        Ok(Statement::DropTable(index))
1951    }
1952
1953    fn schema_statement(&mut self, schema: crate::ast::Schema) -> Statement {
1954        let index = self.ast.schemas.len() as u32;
1955        self.ast.schemas.push(schema);
1956        Statement::Schema(index)
1957    }
1958
1959    /// `InsertStatement <- ... InsertTarget InsertColumnList? InsertValues ...`.
1960    ///
1961    /// `RETURNING` is held as its own query, see [`Self::returning`].
1962    ///
1963    /// `BY NAME`, `BY POSITION` and `DEFAULT VALUES` are each a refusal, because every one of them
1964    /// changes what the statement means and none of them changes it in a way anything downstream
1965    /// would notice if it were dropped.
1966    fn insert_statement(&mut self, node: u32) -> Result<Statement> {
1967        for kid in self.kids(node) {
1968            if matches!(
1969                self.name(kid),
1970                "InsertTarget"
1971                    | "InsertColumnList"
1972                    | "InsertValues"
1973                    | "WithClause"
1974                    | "ReturningClause"
1975                    | "OrAction"
1976                    | "OnConflictClause"
1977            ) {
1978                continue;
1979            }
1980            return self.unsupported(kid);
1981        }
1982        let target = self.find(node, "InsertTarget");
1983        let name = self.name_parts(self.find(target, "BaseTableName"));
1984        let alias = self.find(target, "InsertAlias");
1985        let alias = if alias == NONE { NONE } else { self.identifier(self.first(alias)) };
1986        let list = self.find(node, "InsertColumnList");
1987        let columns = if list == NONE {
1988            Slice::default()
1989        } else {
1990            let mut parts = Vec::new();
1991            for kid in self.kids(self.find(list, "ColumnList")) {
1992                parts.push(self.identifier(kid));
1993            }
1994            self.part_slice(parts)
1995        };
1996        let values = self.find(node, "InsertValues");
1997        let inner = self.first(values);
1998        let source = match self.name(inner) {
1999            "SelectInsertValues" => self.query(self.find(inner, "SelectStatementInternal"))?,
2000            "DefaultValues" if list == NONE => NONE,
2001            "DefaultValues" => {
2002                return Err(Error::parser(
2003                    "You can not provide both a column list and DEFAULT VALUES, please remove one \
2004                     of the two",
2005                ));
2006            }
2007            _ => return self.unsupported(inner),
2008        };
2009        let returning = self.returning(node, name, alias)?;
2010        let conflict = self.conflict(node, name, alias)?;
2011        let index = self.ast.inserts.len() as u32;
2012        self.ast.inserts.push(Insert { name, columns, source, returning, conflict, copy: false });
2013        Ok(Statement::Insert(index))
2014    }
2015
2016    /// `CopyStatement <- 'COPY' CopyVariations`, of which `COPY t FROM 'file'` is done.
2017    ///
2018    /// It becomes `INSERT INTO t SELECT * FROM read_csv('file', ...)` with the options turned into
2019    /// the named parameters `read_csv` takes, which is close to what DuckDB does with it and means
2020    /// the load goes down the same road as every other load from a CSV file, split across threads
2021    /// and all. The one thing the rewrite leaves out is that the file is read as the table's types,
2022    /// and [`Insert::copy`] is how the binder hears about that. The answer is the one an `INSERT`
2023    /// gives, a `Count` of the rows written, which is what the pin answers a `COPY` with too.
2024    ///
2025    /// A `.parquet` file, or `FORMAT parquet`, becomes a `read_parquet` instead, since that reader
2026    /// is here and the rewrite is the same. Everything that writes a file, `COPY t TO` and `COPY
2027    /// (query) TO`, go to [`Self::copy_to`]. `COPY FROM DATABASE` is refused.
2028    fn copy_statement(&mut self, node: u32) -> Result<Statement> {
2029        let select = self.descendant(node, "CopySelect");
2030        if select != NONE {
2031            let query = self.query(self.descendant(select, "SelectStatementInternal"))?;
2032            return self.copy_to(select, query);
2033        }
2034        let table = self.descendant(node, "CopyTable");
2035        if table == NONE {
2036            return self.unsupported(self.first(node));
2037        }
2038        let name = self.name_parts(self.find(table, "BaseTableName"));
2039        let list = self.find(table, "InsertColumnList");
2040        let columns = if list == NONE {
2041            Slice::default()
2042        } else {
2043            let mut parts = Vec::new();
2044            for kid in self.kids(self.find(list, "ColumnList")) {
2045                parts.push(self.identifier(kid));
2046            }
2047            self.part_slice(parts)
2048        };
2049        let direction = self.first(self.find(table, "FromOrTo"));
2050        if self.name(direction) != "CopyFrom" {
2051            let source =
2052                self.push_source(Source::Table { name, alias: NONE, columns: Slice::default() });
2053            let query = if columns.len == 0 {
2054                self.star_over(source)
2055            } else {
2056                let mut targets = Vec::new();
2057                for index in columns.start..columns.start + columns.len {
2058                    let part = self.ast.parts[index as usize];
2059                    let name = self.part_slice(vec![part]);
2060                    let expr = self.push(Expr::Column { name });
2061                    targets.push(Target { expr, alias: NONE });
2062                }
2063                let targets = self.target_slice(targets);
2064                let start = self.ast.source_lists.len() as u32;
2065                self.ast.source_lists.push(source);
2066                let from = Slice { start, len: 1 };
2067                let select = self.push_select(Select { targets, from, ..Select::empty() });
2068                self.push_query(Query::bare(QueryBody::Select(select)))
2069            };
2070            return self.copy_to(table, query);
2071        }
2072        let path = self.copy_file_name(table)?;
2073        let (format, options) = self.copy_options(self.find(table, "CopyOptions"))?;
2074        let format = format.unwrap_or_else(|| {
2075            let lowered = path.to_ascii_lowercase();
2076            if lowered.ends_with(".parquet") { "parquet".to_string() } else { "csv".to_string() }
2077        });
2078        let reader = match format.as_str() {
2079            "csv" => "read_csv",
2080            "parquet" if options.is_empty() => "read_parquet",
2081            "parquet" => {
2082                return Err(Error::not_implemented(
2083                    "COPY FROM a Parquet file with options other than FORMAT is not supported yet",
2084                ));
2085            }
2086            other => {
2087                return Err(Error::not_implemented(format!(
2088                    "COPY FROM with FORMAT {other} is not supported yet"
2089                )));
2090            }
2091        };
2092        let text = self.intern(&path);
2093        let path = self.push(Expr::Literal { kind: LiteralKind::String, text });
2094        let mut args = vec![Target { expr: path, alias: NONE }];
2095        for (parameter, expr) in options {
2096            let alias = self.intern(parameter);
2097            args.push(Target { expr, alias });
2098        }
2099        let args = self.target_slice(args);
2100        let function = self.intern(reader);
2101        let function = self.part_slice(vec![function]);
2102        let source = self.push_source(Source::Function {
2103            name: function,
2104            args,
2105            alias: NONE,
2106            columns: Slice::default(),
2107            pragma: false,
2108        });
2109        let source = self.star_over(source);
2110        let index = self.ast.inserts.len() as u32;
2111        self.ast.inserts.push(Insert {
2112            name,
2113            columns,
2114            source,
2115            returning: None,
2116            conflict: None,
2117            copy: true,
2118        });
2119        Ok(Statement::Insert(index))
2120    }
2121
2122    /// `... TO CopyFileName CopyOptions?`, the file and the options kept as written.
2123    ///
2124    /// The options are not checked here, because which names exist depends on the format and the
2125    /// format can be written anywhere in the list or not at all. A string value is kept as the
2126    /// string it spells and anything else as its text, which is enough for every option `COPY TO`
2127    /// takes: each is a word, a number, a string, or a list of columns.
2128    fn copy_to(&mut self, node: u32, query: QueryRef) -> Result<Statement> {
2129        let path = self.copy_file_name(node)?;
2130        let mut options = Vec::new();
2131        let list = self.find(node, "CopyOptions");
2132        if list != NONE {
2133            let mut generic = Vec::new();
2134            self.named_nodes(list, "CopyGenericOption", &mut generic);
2135            for option in generic {
2136                let inner = self.first(option);
2137                if self.name(inner) != "GenericCopyOption" {
2138                    return self.unsupported(inner);
2139                }
2140                let name = self.text(self.find(inner, "CopyOptionName")).to_ascii_lowercase();
2141                let value = self.find(inner, "GenericCopyOptionValue");
2142                let value = if value == NONE { None } else { Some(self.copy_option_text(value)?) };
2143                options.push((name, value));
2144            }
2145            let mut specialized = Vec::new();
2146            self.named_nodes(list, "SpecializedOption", &mut specialized);
2147            for option in specialized {
2148                let mut inner = self.first(option);
2149                if self.name(inner) == "SingleOption" {
2150                    inner = self.first(inner);
2151                }
2152                let name = match self.name(inner) {
2153                    "CsvOption" => {
2154                        options.push(("format".to_string(), Some("csv".to_string())));
2155                        continue;
2156                    }
2157                    "HeaderOption" => {
2158                        options.push(("header".to_string(), None));
2159                        continue;
2160                    }
2161                    "ForceQuoteOption" => {
2162                        let columns = self.text(self.find(inner, "StarSymbolColumnList"));
2163                        options.push(("force_quote".to_string(), Some(columns.to_string())));
2164                        continue;
2165                    }
2166                    "NullAsOption" => "null",
2167                    "DelimiterAsOption" => "delimiter",
2168                    "QuoteAsOption" => "quote",
2169                    "EscapeAsOption" => "escape",
2170                    _ => return self.unsupported(inner),
2171                };
2172                let value = self.string_value(self.find(inner, "StringLiteral"))?;
2173                options.push((name.to_string(), Some(value)));
2174            }
2175        }
2176        let index = self.ast.copies.len() as u32;
2177        self.ast.copies.push(CopyTo { query, path, options });
2178        Ok(Statement::CopyTo(index))
2179    }
2180
2181    /// `CopyFileName`, as the name of the file.
2182    fn copy_file_name(&self, node: u32) -> Result<String> {
2183        let file = self.first(self.find(node, "CopyFileName"));
2184        match self.name(file) {
2185            "CopyFileNameStringLiteral" => self.string_value(self.find(file, "StringLiteral")),
2186            "CopyFileNameIdentifier" => Ok(self.text(file).to_string()),
2187            _ => self.unsupported(file),
2188        }
2189    }
2190
2191    /// The value of one generic `COPY` option: the string a string literal spells, and the text of
2192    /// anything else.
2193    fn copy_option_text(&self, value: u32) -> Result<String> {
2194        let text = self.text(value).trim();
2195        let literal = self.descendant(value, "StringLiteral");
2196        if literal != NONE && self.text(literal).trim() == text {
2197            return self.string_value(literal);
2198        }
2199        Ok(text.to_string())
2200    }
2201
2202    /// `CopyOptions <- 'WITH'? CopyOptionList`, as the format it named, if it named one, and the
2203    /// rest as `read_csv` parameters with their values.
2204    ///
2205    /// Both spellings are read. The generic list, `(FORMAT csv, HEADER false, NULL '')`, is the one
2206    /// DuckDB documents and the one the Join Order Benchmark loads with. The specialized one,
2207    /// `WITH DELIMITER '|' NULL '' CSV HEADER`, is PostgreSQL's older form and the grammar keeps it,
2208    /// so the options that mean the same thing in both are read from both. An option written with
2209    /// no value is a true one, which is what `HEADER` on its own means in either.
2210    ///
2211    /// An option DuckDB takes and this does not is refused by name rather than dropped, because
2212    /// every one of them changes which rows come out. A name DuckDB does not take either gets the
2213    /// first line of DuckDB's own refusal.
2214    fn copy_options(&mut self, node: u32) -> Result<(Option<String>, CopyOptions)> {
2215        let mut format = None;
2216        let mut options = Vec::new();
2217        if node == NONE {
2218            return Ok((format, options));
2219        }
2220        let mut generic = Vec::new();
2221        self.named_nodes(node, "CopyGenericOption", &mut generic);
2222        for option in generic {
2223            let inner = self.first(option);
2224            if self.name(inner) != "GenericCopyOption" {
2225                return self.unsupported(inner);
2226            }
2227            let name = self.text(self.find(inner, "CopyOptionName")).to_ascii_lowercase();
2228            let value = self.find(inner, "GenericCopyOptionValue");
2229            if value != NONE && self.name(self.first(value)) != "GenericCopyOptionExpression" {
2230                return self.unsupported(value);
2231            }
2232            if name == "format" {
2233                // `FORMAT csv` writes the format as a bare word, which would read as a column,
2234                // so it is taken as the text it was written with.
2235                if value == NONE {
2236                    return self.unsupported(option);
2237                }
2238                let written = self.text(value).trim();
2239                let written = written.trim_matches('\'').to_ascii_lowercase();
2240                format = Some(written);
2241                continue;
2242            }
2243            let parameter = copy_parameter(&name)?;
2244            let expr = if value == NONE {
2245                self.push(Expr::Literal { kind: LiteralKind::True, text: NONE })
2246            } else {
2247                self.expr(self.descendant(value, "Expression"))?
2248            };
2249            options.push((parameter, expr));
2250        }
2251        let mut specialized = Vec::new();
2252        self.named_nodes(node, "SpecializedOption", &mut specialized);
2253        for option in specialized {
2254            let mut inner = self.first(option);
2255            if self.name(inner) == "SingleOption" {
2256                inner = self.first(inner);
2257            }
2258            let parameter = match self.name(inner) {
2259                "CsvOption" => {
2260                    format = Some("csv".to_string());
2261                    continue;
2262                }
2263                "HeaderOption" => {
2264                    let yes = self.push(Expr::Literal { kind: LiteralKind::True, text: NONE });
2265                    options.push(("header", yes));
2266                    continue;
2267                }
2268                "NullAsOption" => "nullstr",
2269                "DelimiterAsOption" => "delim",
2270                "QuoteAsOption" => "quote",
2271                "EscapeAsOption" => "escape",
2272                _ => return self.unsupported(inner),
2273            };
2274            let expr = self.string_literal(self.find(inner, "StringLiteral"))?;
2275            options.push((parameter, expr));
2276        }
2277        Ok((format, options))
2278    }
2279
2280    /// `OrAction <- InsertOrReplace / InsertOrIgnore` and `OnConflictClause <- 'ON' 'CONFLICT'
2281    /// OnConflictTarget? OnConflictAction`, or `None` when the statement has neither.
2282    fn conflict(&mut self, node: u32, name: Slice, alias: StrRef) -> Result<Option<Conflict>> {
2283        let or = self.find(node, "OrAction");
2284        if or != NONE {
2285            let action = match self.name(self.first(or)) {
2286                "InsertOrReplace" => ConflictAction::Replace,
2287                _ => ConflictAction::Nothing,
2288            };
2289            return Ok(Some(Conflict { target: Slice::default(), action }));
2290        }
2291        let clause = self.find(node, "OnConflictClause");
2292        if clause == NONE {
2293            return Ok(None);
2294        }
2295        let mut target = Slice::default();
2296        let written = self.find(clause, "OnConflictTarget");
2297        if written != NONE {
2298            let inner = self.first(written);
2299            if self.name(inner) != "OnConflictExpressionTarget" {
2300                return self.unsupported(inner);
2301            }
2302            if self.find(inner, "WhereClause") != NONE {
2303                return Err(Error::binder(
2304                    "ON CONFLICT WHERE clause is only supported in DO UPDATE SET ... WHERE ...\nThe \
2305                     WHERE clause after the conflict columns is used for partial indexes which \
2306                     are not supported.",
2307                ));
2308            }
2309            let mut found = Vec::new();
2310            self.named_nodes(self.find(inner, "ColumnIdList"), "ColId", &mut found);
2311            let names = found
2312                .into_iter()
2313                .map(|id| {
2314                    let text = self.fold_identifier(self.text(id));
2315                    self.intern(&text)
2316                })
2317                .collect();
2318            target = self.part_slice(names);
2319        }
2320        let action = self.first(self.find(clause, "OnConflictAction"));
2321        if self.name(action) == "OnConflictNothing" {
2322            return Ok(Some(Conflict { target, action: ConflictAction::Nothing }));
2323        }
2324        let sets = self.set_clause(self.find(action, "UpdateSetClause"))?;
2325        let filter = self.find(action, "WhereClause");
2326        let condition = if filter == NONE {
2327            self.push(Expr::Literal { kind: LiteralKind::True, text: NONE })
2328        } else {
2329            self.expr(self.find(filter, "Expression"))?
2330        };
2331        let mut targets = Vec::with_capacity(sets.len() + 1);
2332        let mut columns = Vec::with_capacity(sets.len());
2333        for (column, value) in sets {
2334            columns.push(column);
2335            targets.push(Target { expr: value, alias: NONE });
2336        }
2337        targets.push(Target { expr: condition, alias: NONE });
2338        let targets = self.target_slice(targets);
2339        let left = self.push_source(Source::Table { name, alias, columns: Slice::default() });
2340        let excluded = self.intern("excluded");
2341        let right =
2342            self.push_source(Source::Table { name, alias: excluded, columns: Slice::default() });
2343        let joined = self.push_source(Source::Join {
2344            left,
2345            right,
2346            kind: JoinKind::Positional,
2347            natural: false,
2348            on: NONE,
2349            using: Slice::default(),
2350        });
2351        let start = self.ast.source_lists.len() as u32;
2352        self.ast.source_lists.push(joined);
2353        let from = Slice { start, len: 1 };
2354        let select = self.push_select(Select { targets, from, ..Select::empty() });
2355        let query = self.push_query(Query::bare(QueryBody::Select(select)));
2356        let columns = self.part_slice(columns);
2357        Ok(Some(Conflict { target, action: ConflictAction::Update { columns, query } }))
2358    }
2359
2360    /// `ReturningClause <- 'RETURNING' TargetList`, as `SELECT list FROM table [AS alias]`, or
2361    /// `None` when the statement has none.
2362    fn returning(&mut self, node: u32, name: Slice, alias: StrRef) -> Result<Option<QueryRef>> {
2363        let clause = self.find(node, "ReturningClause");
2364        if clause == NONE {
2365            return Ok(None);
2366        }
2367        let mut targets = Vec::new();
2368        for kid in self.kids(self.find(clause, "TargetList")).collect::<Vec<_>>() {
2369            targets.push(self.target(kid)?);
2370        }
2371        let targets = self.target_slice(targets);
2372        let from = self.written_table(name, alias);
2373        let select = self.push_select(Select { targets, from, ..Select::empty() });
2374        Ok(Some(self.push_query(Query::bare(QueryBody::Select(select)))))
2375    }
2376
2377    /// A `FROM` of the one table a writing statement names.
2378    fn written_table(&mut self, name: Slice, alias: StrRef) -> Slice {
2379        let source = self.push_source(Source::Table { name, alias, columns: Slice::default() });
2380        let start = self.ast.source_lists.len() as u32;
2381        self.ast.source_lists.push(source);
2382        Slice { start, len: 1 }
2383    }
2384
2385    /// An `INSERT`, `UPDATE` or `DELETE`, with the definitions of a `WITH` ahead of it in scope.
2386    ///
2387    /// A definition is inlined where it is named unless it was written `MATERIALIZED`, which is
2388    /// what a query nested in another gets too, and one that is held is carried by the source and
2389    /// by the `RETURNING` query both, since each is bound on its own.
2390    fn write_statement(&mut self, node: u32) -> Result<Statement> {
2391        let mark = self.ctes.len();
2392        let once = self.definitions(node, self.find(node, "WithClause"))?;
2393        let statement = match self.name(node) {
2394            "InsertStatement" => self.insert_statement(node),
2395            "UpdateStatement" => self.update_statement(node),
2396            _ => self.delete_statement(node),
2397        };
2398        self.ctes.truncate(mark);
2399        let statement = statement?;
2400        if let (
2401            false,
2402            Statement::Insert(index) | Statement::Update(index) | Statement::Delete(index),
2403        ) = (once.is_empty(), &statement)
2404        {
2405            let insert = self.ast.inserts[*index as usize];
2406            let update = match insert.conflict.map(|conflict| conflict.action) {
2407                Some(ConflictAction::Update { query, .. }) => Some(query),
2408                _ => None,
2409            };
2410            for query in std::iter::once(insert.source).chain(insert.returning).chain(update) {
2411                // Outermost first, so the statement's own come ahead of any the query wrote.
2412                let own = self.ast.queries[query as usize].ctes;
2413                let mut all = once.clone();
2414                all.extend_from_slice(self.ast.cte_list(own));
2415                let slice = self.cte_slice(all);
2416                self.ast.queries[query as usize].ctes = slice;
2417            }
2418        }
2419        Ok(statement)
2420    }
2421
2422    /// `UpdateStatement <- WithClause? 'UPDATE' UpdateTarget UpdateSetClause FromClause?
2423    /// WhereClause? ReturningClause?`.
2424    ///
2425    /// A qualified name after `SET` is the pin's own refusal.
2426    fn update_statement(&mut self, node: u32) -> Result<Statement> {
2427        let target = self.first(self.find(node, "UpdateTarget"));
2428        let name = self.name_parts(self.find(target, "BaseTableName"));
2429        let alias = self.find(target, "UpdateAlias");
2430        let alias = if alias == NONE { NONE } else { self.identifier(alias) };
2431        let sets = self.set_clause(self.find(node, "UpdateSetClause"))?;
2432        self.changed_rows(node, name, alias, sets, false)
2433    }
2434
2435    /// `UpdateSetClause`, as the columns it sets and the value each one gets.
2436    fn set_clause(&mut self, node: u32) -> Result<Vec<(StrRef, ExprRef)>> {
2437        let set = self.first(node);
2438        if self.name(set) == "UpdateSetTuple" {
2439            return self.set_tuple(set);
2440        }
2441        let mut sets = Vec::new();
2442        for element in self.kids(set).collect::<Vec<_>>() {
2443            let column = self.find(element, "UpdateSetColumnTarget");
2444            let dotted = self.find(column, "DotIdentifier");
2445            if dotted != NONE {
2446                return Err(Error::parser("Qualified column names in UPDATE .. SET not supported"));
2447            }
2448            let written = self.identifier(self.find(column, "ColumnName"));
2449            let value = self.expr(self.find(element, "Expression"))?;
2450            sets.push((written, value));
2451        }
2452        Ok(sets)
2453    }
2454
2455    /// `UpdateSetTuple <- Parens(List(ColumnName)) '=' Expression`.
2456    ///
2457    /// A row on the right, `(1, 'x')` or `ROW(1, 'x')`, hands one value to each column and has to
2458    /// have as many as there are columns. Anything else is handed to every column whole, so
2459    /// `(a, b) = 3` sets both to 3, which is how the pin reads it.
2460    fn set_tuple(&mut self, set: u32) -> Result<Vec<(StrRef, ExprRef)>> {
2461        let mut names = Vec::new();
2462        let mut pending: Vec<u32> = self.kids(set).collect();
2463        pending.reverse();
2464        while let Some(node) = pending.pop() {
2465            if self.name(node) == "ColumnName" {
2466                names.push(self.identifier(node));
2467            } else if self.name(node) != "Expression" {
2468                let kids: Vec<u32> = self.kids(node).collect();
2469                pending.extend(kids.into_iter().rev());
2470            }
2471        }
2472        let value = self.expr(self.find(set, "Expression"))?;
2473        let items = match self.ast.exprs[value as usize] {
2474            Expr::Row { items } => Some(items),
2475            Expr::Function { name, args, .. }
2476                if name.len == 1 && self.ast.name_text(name).eq_ignore_ascii_case("row") =>
2477            {
2478                Some(args)
2479            }
2480            _ => None,
2481        };
2482        let Some(items) = items else {
2483            return Ok(names.into_iter().map(|name| (name, value)).collect());
2484        };
2485        let items = self.ast.expr_list(items).to_vec();
2486        if items.len() != names.len() {
2487            return Err(Error::parser(format!(
2488                "Could not perform assignment, expected {} values, got {}",
2489                names.len(),
2490                items.len()
2491            )));
2492        }
2493        Ok(names.into_iter().zip(items).collect())
2494    }
2495
2496    /// `DeleteStatement <- WithClause? 'DELETE' 'FROM' TargetOptAlias DeleteUsingClause?
2497    /// WhereClause? ReturningClause?`.
2498    fn delete_statement(&mut self, node: u32) -> Result<Statement> {
2499        let target = self.find(node, "TargetOptAlias");
2500        let name = self.name_parts(self.find(target, "BaseTableName"));
2501        let alias = self.find(target, "ColId");
2502        let alias = if alias == NONE { NONE } else { self.identifier(alias) };
2503        self.changed_rows(node, name, alias, Vec::new(), true)
2504    }
2505
2506    /// The source an `UPDATE` or a `DELETE` is held with, which is `SELECT *, condition, values...
2507    /// FROM table`. With no `WHERE` the condition is `TRUE`, since every row is the one meant.
2508    ///
2509    /// `UPDATE ... FROM` and `DELETE ... USING` are the same thing with the condition and the values
2510    /// read from a lateral join instead, `SELECT t.*, m.hit, m.values... FROM table AS t LEFT JOIN
2511    /// (SELECT true AS hit, values... FROM sources WHERE condition LIMIT 1) AS m ON true`. The
2512    /// `LIMIT 1` is what makes a table row that several source rows match change once, to the
2513    /// values of one of them, which is what the pin does. A row nothing matches has a null for the
2514    /// flag and is left alone.
2515    fn changed_rows(
2516        &mut self,
2517        node: u32,
2518        name: Slice,
2519        alias: StrRef,
2520        sets: Vec<(StrRef, ExprRef)>,
2521        delete: bool,
2522    ) -> Result<Statement> {
2523        let returning = self.returning(node, name, alias)?;
2524        let filter = self.find(node, "WhereClause");
2525        let using = match self.find(node, "FromClause") {
2526            NONE => self.find(node, "DeleteUsingClause"),
2527            clause => clause,
2528        };
2529        if using != NONE {
2530            return self.changed_rows_using(name, alias, filter, using, sets, returning, delete);
2531        }
2532        let hit = if filter == NONE {
2533            self.push(Expr::Literal { kind: LiteralKind::True, text: NONE })
2534        } else {
2535            self.expr(self.first(filter))?
2536        };
2537        let star =
2538            self.push(Expr::Star { qualifier: Slice::default(), replacements: Slice::default() });
2539        let mut targets =
2540            vec![Target { expr: star, alias: NONE }, Target { expr: hit, alias: NONE }];
2541        let mut columns = Vec::with_capacity(sets.len());
2542        for (column, value) in sets {
2543            columns.push(column);
2544            targets.push(Target { expr: value, alias: NONE });
2545        }
2546        let targets = self.target_slice(targets);
2547        let from = self.written_table(name, alias);
2548        let select = self.push_select(Select { targets, from, ..Select::empty() });
2549        let source = self.push_query(Query::bare(QueryBody::Select(select)));
2550        let columns = self.part_slice(columns);
2551        Ok(self.changed_statement(name, columns, source, returning, delete))
2552    }
2553
2554    /// The lateral form of [`Self::changed_rows`], for a statement with a `FROM` or a `USING`.
2555    #[allow(clippy::too_many_arguments)]
2556    fn changed_rows_using(
2557        &mut self,
2558        name: Slice,
2559        alias: StrRef,
2560        filter: u32,
2561        using: u32,
2562        sets: Vec<(StrRef, ExprRef)>,
2563        returning: Option<QueryRef>,
2564        delete: bool,
2565    ) -> Result<Statement> {
2566        let hit = self.intern("__rudb_hit");
2567        let matched = self.intern("__rudb_matched");
2568        let alias = if alias == NONE {
2569            self.ast.parts[(name.start + name.len - 1) as usize]
2570        } else {
2571            alias
2572        };
2573        let yes = self.push(Expr::Literal { kind: LiteralKind::True, text: NONE });
2574        let mut inner = vec![Target { expr: yes, alias: hit }];
2575        let mut outer_names = vec![hit];
2576        let mut columns = Vec::with_capacity(sets.len());
2577        for (at, (column, value)) in sets.into_iter().enumerate() {
2578            columns.push(column);
2579            let named = self.intern(&format!("__rudb_value_{at}"));
2580            inner.push(Target { expr: value, alias: named });
2581            outer_names.push(named);
2582        }
2583        let inner = self.target_slice(inner);
2584        let from = self.sources(using)?;
2585        let filter = if filter == NONE { NONE } else { self.expr(self.first(filter))? };
2586        let select = self.push_select(Select { targets: inner, from, filter, ..Select::empty() });
2587        let one = self.intern("1");
2588        let limit = self.push(Expr::Literal { kind: LiteralKind::Number, text: one });
2589        let query = self.push_query(Query { limit, ..Query::bare(QueryBody::Select(select)) });
2590        let right =
2591            self.push_source(Source::Subquery { query, alias: matched, columns: Slice::default() });
2592        let left = self.push_source(Source::Table { name, alias, columns: Slice::default() });
2593        let on = self.push(Expr::Literal { kind: LiteralKind::True, text: NONE });
2594        let join = self.push_source(Source::Join {
2595            left,
2596            right,
2597            kind: JoinKind::Left,
2598            natural: false,
2599            on,
2600            using: Slice::default(),
2601        });
2602        let start = self.ast.source_lists.len() as u32;
2603        self.ast.source_lists.push(join);
2604        let from = Slice { start, len: 1 };
2605        let qualifier = self.part_slice(vec![alias]);
2606        let star = self.push(Expr::Star { qualifier, replacements: Slice::default() });
2607        let mut targets = vec![Target { expr: star, alias: NONE }];
2608        for named in outer_names {
2609            let name = self.part_slice(vec![matched, named]);
2610            let column = self.push(Expr::Column { name });
2611            targets.push(Target { expr: column, alias: NONE });
2612        }
2613        let targets = self.target_slice(targets);
2614        let select = self.push_select(Select { targets, from, ..Select::empty() });
2615        let source = self.push_query(Query::bare(QueryBody::Select(select)));
2616        let columns = self.part_slice(columns);
2617        Ok(self.changed_statement(name, columns, source, returning, delete))
2618    }
2619
2620    fn changed_statement(
2621        &mut self,
2622        name: Slice,
2623        columns: Slice,
2624        source: QueryRef,
2625        returning: Option<QueryRef>,
2626        delete: bool,
2627    ) -> Statement {
2628        let index = self.ast.inserts.len() as u32;
2629        self.ast.inserts.push(Insert {
2630            name,
2631            columns,
2632            source,
2633            returning,
2634            conflict: None,
2635            copy: false,
2636        });
2637        if delete { Statement::Delete(index) } else { Statement::Update(index) }
2638    }
2639
2640    /// `SelectStatementInternal <- WithClause? SelectSetOpChain ResultModifiers?`.
2641    fn query(&mut self, node: u32) -> Result<QueryRef> {
2642        let span = self.span(node);
2643        let outer = std::mem::replace(&mut self.current_span, span);
2644        // Every query in a statement is reached through here, including the one a `WITH`
2645        // definition is and the one a subquery is, so the count is how deeply nested the query
2646        // being read is and one means the statement's own. [`Self::worth_holding`] is the only
2647        // reader of it.
2648        self.query_depth += 1;
2649        let result = self.query_inner(node);
2650        self.query_depth -= 1;
2651        self.current_span = outer;
2652        result
2653    }
2654
2655    fn query_inner(&mut self, node: u32) -> Result<QueryRef> {
2656        let mark = self.ctes.len();
2657        let with = self.find(node, "WithClause");
2658        let once = self.definitions(node, with)?;
2659        let chain = self.find(node, "SelectSetOpChain");
2660        if chain == NONE {
2661            return self.unsupported(node);
2662        }
2663        let query = self.set_op_chain(chain)?;
2664        let modifiers = self.find(node, "ResultModifiers");
2665        if modifiers != NONE {
2666            self.result_modifiers(query, modifiers)?;
2667        }
2668        if !once.is_empty() {
2669            let slice = self.cte_slice(once);
2670            self.ast.queries[query as usize].ctes = slice;
2671        }
2672        self.ctes.truncate(mark);
2673        Ok(query)
2674    }
2675
2676    /// The definitions of a `WITH`, put in scope for what follows, with the ones held once
2677    /// returned so the query they belong to can carry them. `NONE` for no clause is no definitions.
2678    /// The caller truncates `ctes` back to where it was once the query is read.
2679    fn definitions(&mut self, node: u32, with: u32) -> Result<Vec<u32>> {
2680        let mut once = Vec::new();
2681        if with == NONE {
2682            return Ok(once);
2683        }
2684        if self.find(with, "Recursive") != NONE {
2685            return self.unsupported(self.find(with, "Recursive"));
2686        }
2687        let written: Vec<u32> =
2688            self.kids(with).filter(|&kid| self.name(kid) == "WithStatement").collect();
2689        for (at, &statement) in written.iter().enumerate() {
2690            // `MATERIALIZED` says the definition runs once and every reference reads the rows
2691            // it produced and `NOT MATERIALIZED` says the query goes into each place the name
2692            // is used. Neither word was written for most definitions, and what the plain form
2693            // means is a decision rather than a default: the pinned build holds the rows of a
2694            // plain definition that is named more than once and puts one named once into the
2695            // place it is named, so that is what happens here. It is settled at the parse
2696            // rather than left to the optimizer because the pin settles it there too, which is
2697            // visible in its `EXPLAIN`.
2698            //
2699            // Holding rather than inlining is also what makes a definition holding a volatile
2700            // call answer the way the pin answers it. `WITH c AS (SELECT random() AS r) SELECT
2701            // a.r, b.r FROM c a, c b` gives the same number twice on the pin, which is what a
2702            // definition run once gives, and two numbers is what inlining gives. The function
2703            // table has no `random`, no `nextval` and no `now` in it yet, so nothing reaches
2704            // that today, but the rule is now the one that will be right when something does.
2705            let word = self.find(statement, "Materialized");
2706            let asked = word != NONE && !self.text(word).eq_ignore_ascii_case("NOT MATERIALIZED");
2707            let refused = word != NONE && !asked;
2708            let name = self.identifier(self.first(statement));
2709            let materialized =
2710                asked || (!refused && self.worth_holding(node, &written[..=at], name));
2711            let list = self.find(statement, "InsertColumnList");
2712            let columns = if list == NONE {
2713                Slice::default()
2714            } else {
2715                let mut names = Vec::new();
2716                for kid in self.kids(self.find(list, "ColumnList")) {
2717                    names.push(self.identifier(kid));
2718                }
2719                self.part_slice(names)
2720            };
2721            let body = self.find(statement, "CTEBody");
2722            let select = self.first(body);
2723            if self.name(select) != "CTESelectBody" {
2724                return self.unsupported(body);
2725            }
2726            let query = self.query(self.first(select))?;
2727            if materialized {
2728                let index = self.ast.ctes.len() as u32;
2729                self.ast.ctes.push(Cte { name, query, columns });
2730                once.push(index);
2731                self.ctes.push((name, Held::Once(index), columns));
2732            } else {
2733                self.ctes.push((name, Held::Inline(query), columns));
2734            }
2735        }
2736        Ok(once)
2737    }
2738
2739    /// Whether a plain `WITH` definition is one to hold the rows of rather than to inline.
2740    ///
2741    /// Two things have to hold. The name has to be read more than once, because a definition read
2742    /// once is cheaper inlined: it becomes part of the query that reads it and the filters and the
2743    /// columns that query asks for reach the scan underneath, where holding the rows stops them at
2744    /// the definition. Read twice it is the other way round, and q15 of TPC-H is the query that
2745    /// says so, since its definition groups a quarter of lineitem and the query names it twice.
2746    ///
2747    /// And the definition has to be the statement's own rather than one written inside a subquery,
2748    /// which is what the depth is for. A definition written inside a subquery can name a column of
2749    /// the query around it, and rows held once for the whole statement cannot answer per outer
2750    /// row, so inlining is the only thing that is certainly the same query. A nested definition
2751    /// with nothing correlated in it would be worth holding too, and telling those apart is a
2752    /// question about resolved columns that this pass does not have and the binder does.
2753    ///
2754    /// `held` is this definition and the ones written before it. A name read inside one of those is
2755    /// not a read of this one: either it is this definition's own subtree, where the name means
2756    /// whatever it meant outside the clause, or it is an earlier definition, which was transformed
2757    /// before this name existed.
2758    fn worth_holding(&self, query: u32, held: &[u32], name: StrRef) -> bool {
2759        if self.query_depth != 1 {
2760            return false;
2761        }
2762        let name = self.ast.string(name);
2763        // A definition of the same name further in takes the name over for the part of the query
2764        // under it, and which reads belong to which is a question about scopes that a count of
2765        // spellings cannot ask. Inlining is what every definition got until now, so it is what a
2766        // query that asks the harder question gets.
2767        if self.redefines(query, name, held) {
2768            return false;
2769        }
2770        let mut seen = 0;
2771        self.counts_reads(query, name, held, &mut seen);
2772        seen > 1
2773    }
2774
2775    /// Counts the bare table names under `at` that spell `name`, skipping the subtrees in `held`.
2776    fn counts_reads(&self, at: u32, name: &str, held: &[u32], seen: &mut usize) {
2777        if held.contains(&at) {
2778            return;
2779        }
2780        if self.name(at) == "BaseTableName"
2781            && self.bare_name(at).is_some_and(|read| read.eq_ignore_ascii_case(name))
2782        {
2783            *seen += 1;
2784        }
2785        for kid in self.kids(at) {
2786            self.counts_reads(kid, name, held, seen);
2787        }
2788    }
2789
2790    /// Whether any `WITH` definition under `at` outside `held` is written with this name.
2791    fn redefines(&self, at: u32, name: &str, held: &[u32]) -> bool {
2792        if held.contains(&at) {
2793            return false;
2794        }
2795        if self.name(at) == "WithStatement"
2796            && self
2797                .bare_name(self.first(at))
2798                .is_some_and(|written| written.eq_ignore_ascii_case(name))
2799        {
2800            return true;
2801        }
2802        self.kids(at).any(|kid| self.redefines(kid, name, held))
2803    }
2804
2805    /// `SelectSetOpChain <- IntersectChain SelectSetOpChainTail*`, left associative.
2806    fn set_op_chain(&mut self, node: u32) -> Result<QueryRef> {
2807        let mut kids = self.kids(node);
2808        let head = kids.next().unwrap_or(NONE);
2809        let mut left = self.intersect_chain(head)?;
2810        for tail in kids {
2811            // `SelectSetOpChainTail <- SetopClause IntersectChain`.
2812            let clause = self.first(tail);
2813            let (op, quantifier, by_name) = self.setop_clause(clause)?;
2814            let right = self.intersect_chain(self.nth(tail, 1))?;
2815            left = self.push_query(Query::bare(QueryBody::SetOp {
2816                op,
2817                quantifier,
2818                by_name,
2819                left,
2820                right,
2821            }));
2822        }
2823        Ok(left)
2824    }
2825
2826    /// `IntersectChain <- SelectAtom IntersectChainTail*`, which binds tighter than union.
2827    fn intersect_chain(&mut self, node: u32) -> Result<QueryRef> {
2828        let mut kids = self.kids(node);
2829        let head = kids.next().unwrap_or(NONE);
2830        let mut left = self.select_atom(head)?;
2831        for tail in kids {
2832            // `IntersectChainTail <- SetIntersectClause SelectAtom`.
2833            let clause = self.first(tail);
2834            let quantifier = self.quantifier(self.find(clause, "DistinctOrAll"));
2835            let right = self.select_atom(self.nth(tail, 1))?;
2836            left = self.push_query(Query::bare(QueryBody::SetOp {
2837                op: SetOp::Intersect,
2838                quantifier,
2839                by_name: false,
2840                left,
2841                right,
2842            }));
2843        }
2844        Ok(left)
2845    }
2846
2847    /// `SetopClause <- SetopType DistinctOrAll? ByName?`.
2848    fn setop_clause(&mut self, node: u32) -> Result<(SetOp, Quantifier, bool)> {
2849        let kind = self.find(node, "SetopType");
2850        let op = match self.name(self.first(kind)) {
2851            "SetopUnion" => SetOp::Union,
2852            "SetopExcept" => SetOp::Except,
2853            _ => return self.unsupported(kind),
2854        };
2855        let quantifier = self.quantifier(self.find(node, "DistinctOrAll"));
2856        let by_name = self.find(node, "ByName") != NONE;
2857        // `BY NAME` only goes with `UNION`. The grammar takes it after `EXCEPT` as well, since the
2858        // two share a clause, so the pairing is checked here and refused the way the pin refuses
2859        // it. `INTERSECT BY NAME` never reaches this, because intersection has a clause of its own
2860        // with no `ByName` in it, and is a syntax error there just as it is there.
2861        if by_name && op == SetOp::Except {
2862            return Err(Error::parser("Invalid combination of EXCEPT and BY NAME"));
2863        }
2864        Ok((op, quantifier, by_name))
2865    }
2866
2867    /// `DistinctOrAll <- DistinctKeyword / AllKeyword`, absent included.
2868    fn quantifier(&self, node: u32) -> Quantifier {
2869        if node == NONE {
2870            return Quantifier::Unstated;
2871        }
2872        match self.name(self.first(node)) {
2873            "DistinctKeyword" => Quantifier::Distinct,
2874            "AllKeyword" => Quantifier::All,
2875            _ => Quantifier::Unstated,
2876        }
2877    }
2878
2879    /// `SelectAtom <- SelectParens / SelectStatementType`.
2880    fn select_atom(&mut self, node: u32) -> Result<QueryRef> {
2881        let inner = self.first(node);
2882        match self.name(inner) {
2883            // `SelectParens <- Parens(SelectStatementInternal)`, so the parens buy a query that
2884            // carries its own order by and limit and nothing else.
2885            "SelectParens" => self.query(self.first(inner)),
2886            "SelectStatementType" => {
2887                let kind = self.first(inner);
2888                match self.name(kind) {
2889                    "OptionalParensSimpleSelect" => {
2890                        let select = self.simple_select(self.unwrap_parens(kind))?;
2891                        Ok(self.push_query(Query::bare(QueryBody::Select(select))))
2892                    }
2893                    "ValuesClause" => {
2894                        let rows = self.values_clause(kind)?;
2895                        Ok(self.push_query(Query::bare(QueryBody::Values(rows))))
2896                    }
2897                    "DescribeStatement" => self.describe_statement(kind),
2898                    _ => self.unsupported(kind),
2899                }
2900            }
2901            _ => self.unsupported(inner),
2902        }
2903    }
2904
2905    /// `DescribeStatement <- ShowTables / ShowDeprecatedSelect / DescribeSelect / ShowAllTables /
2906    /// ShowByName / DescribeByName`.
2907    ///
2908    /// Three of the six are done. The two that describe a relation are, and so is `SHOW ALL`, which
2909    /// lists every table and view rather than describing one. The three that are not are `SHOW
2910    /// TABLES FROM <name>`, which wants a schema this cannot name yet, `SHOW <query>`, which upstream
2911    /// documents as deprecated, and the special forms `SCHEMAS` and `VARIABLES`, which answer from
2912    /// places rudb has not built.
2913    ///
2914    /// `SUMMARIZE` shares `DescribeByName` and `DescribeSelect` with `DESCRIBE` and is refused
2915    /// here, because it returns twelve columns of statistics rather than six of schema and reading
2916    /// it as a describe would answer a different question than the one that was asked.
2917    fn describe_statement(&mut self, node: u32) -> Result<QueryRef> {
2918        let inner = self.first(node);
2919        match self.name(inner) {
2920            "DescribeSelect" => {
2921                self.describe_and_not_summarize(inner)?;
2922                let query = self.query(self.find(inner, "SelectStatementInternal"))?;
2923                Ok(self.push_query(Query::bare(QueryBody::Describe(query))))
2924            }
2925            "DescribeByName" => {
2926                self.describe_and_not_summarize(inner)?;
2927                let target = self.find(inner, "DescribeTarget");
2928                if target == NONE {
2929                    return self.unsupported(inner);
2930                }
2931                let name = self.name_parts(target);
2932                if let Some(query) = self.special_form(name) {
2933                    return Ok(query);
2934                }
2935                let source = self.describe_target(target)?;
2936                let query = self.star_over(source);
2937                Ok(self.push_query(Query::bare(QueryBody::Describe(query))))
2938            }
2939            "ShowAllTables" => Ok(self.pragma_query("pragma_show_tables_expanded")),
2940            "ShowByName" => {
2941                let target = self.find(inner, "ShowTarget");
2942                if target == NONE {
2943                    return self.unsupported(inner);
2944                }
2945                let name = self.name_parts(target);
2946                if let Some(query) = self.special_form(name) {
2947                    return Ok(query);
2948                }
2949                let source = self.push_source(Source::Table {
2950                    name,
2951                    alias: NONE,
2952                    columns: Slice::default(),
2953                });
2954                let relation = self.star_over(source);
2955                Ok(self.push_query(Query::bare(QueryBody::Show { name, relation })))
2956            }
2957            _ => self.unsupported(inner),
2958        }
2959    }
2960
2961    /// The names `SHOW` and `DESCRIBE` answer from the catalog instead of looking up.
2962    ///
2963    /// The pin reads these before the name reaches the catalog, so `SHOW tables` lists the tables
2964    /// even when a table is named `tables`, and `DESCRIBE tables` does the same rather than
2965    /// describing that table. A qualified name is never one of these, because `DESCRIBE main.tables`
2966    /// is the table and the pin describes it.
2967    fn special_form(&mut self, name: Slice) -> Option<QueryRef> {
2968        if name.len != 1 {
2969            return None;
2970        }
2971        let written = self.ast.name_text(name);
2972        let pragma = match written.to_ascii_lowercase().as_str() {
2973            "tables" => "pragma_show_tables",
2974            "databases" => "pragma_show_databases",
2975            _ => return None,
2976        };
2977        Some(self.pragma_query(pragma))
2978    }
2979
2980    /// `SELECT * FROM <name>()`, which is what a special form turns into.
2981    ///
2982    /// Marked as a pragma call because that is the half of the catalog these three live in, and a
2983    /// name in that half is not a name a `FROM` clause can reach.
2984    fn pragma_query(&mut self, pragma: &str) -> QueryRef {
2985        let part = self.intern(pragma);
2986        let name = self.part_slice(vec![part]);
2987        let args = self.target_slice(Vec::new());
2988        let source = self.push_source(Source::Function {
2989            name,
2990            args,
2991            alias: NONE,
2992            columns: Slice::default(),
2993            pragma: true,
2994        });
2995        self.star_over(source)
2996    }
2997
2998    /// `DescribeOrSummarize <- DescribeRule / Summarize`, where only the first is done.
2999    fn describe_and_not_summarize(&mut self, node: u32) -> Result<()> {
3000        let word = self.find(node, "DescribeOrSummarize");
3001        if word == NONE || self.name(self.first(word)) != "DescribeRule" {
3002            return self.unsupported(if word == NONE { node } else { word });
3003        }
3004        Ok(())
3005    }
3006
3007    /// `DescribeTarget <- DescribeBaseTableName / DescribeStringLiteral`, as a source to read from.
3008    ///
3009    /// Both become a `FROM` item and not a lookup of their own, because the string form is the
3010    /// replacement scan and the binder already knows how to turn `'hits.parquet'` into a reader.
3011    /// A name that is a table, a view, a file or nothing at all then gets one answer from one place.
3012    fn describe_target(&mut self, node: u32) -> Result<SourceRef> {
3013        let inner = self.first(node);
3014        let name = match self.name(inner) {
3015            "DescribeBaseTableName" => self.name_parts(self.find(inner, "BaseTableName")),
3016            "DescribeStringLiteral" => {
3017                let text = self.string_value(self.find(inner, "StringLiteral"))?;
3018                let part = self.intern(&text);
3019                self.part_slice(vec![part])
3020            }
3021            _ => return self.unsupported(inner),
3022        };
3023        Ok(self.push_source(Source::Table { name, alias: NONE, columns: Slice::default() }))
3024    }
3025
3026    /// `SELECT * FROM <source>`, which is what `DESCRIBE t` means.
3027    fn star_over(&mut self, source: SourceRef) -> QueryRef {
3028        let star =
3029            self.push(Expr::Star { qualifier: Slice::default(), replacements: Slice::default() });
3030        let targets = self.target_slice(vec![Target { expr: star, alias: NONE }]);
3031        let start = self.ast.source_lists.len() as u32;
3032        self.ast.source_lists.push(source);
3033        let from = Slice { start, len: 1 };
3034        let select = self.push_select(Select { targets, from, ..Select::empty() });
3035        self.push_query(Query::bare(QueryBody::Select(select)))
3036    }
3037
3038    /// `ValuesClause <- 'VALUES' List(ValuesExpressions)`, each of which is `Parens(List(Expression))`.
3039    ///
3040    /// The rows are not checked against each other for width here. Two rows of different widths
3041    /// parse, and saying so is the binder's job, because the message wants to name the column count
3042    /// it expected and the parser does not know it for `INSERT` where the table decides.
3043    fn values_clause(&mut self, node: u32) -> Result<Slice> {
3044        let mut rows = Vec::new();
3045        for kid in self.kids(node) {
3046            if self.name(kid) != "ValuesExpressions" {
3047                continue;
3048            }
3049            let mut items = Vec::new();
3050            for expr in self.kids(kid) {
3051                items.push(self.expr(expr)?);
3052            }
3053            let slice = self.expr_slice(items);
3054            rows.push(slice);
3055        }
3056        let start = self.ast.rows.len() as u32;
3057        self.ast.rows.extend(rows);
3058        Ok(Slice { start, len: self.ast.rows.len() as u32 - start })
3059    }
3060
3061    /// `OptionalParensSimpleSelect <- SimpleSelectParens / SimpleSelect`, down to the select.
3062    fn unwrap_parens(&self, node: u32) -> u32 {
3063        let mut node = self.first(node);
3064        while self.name(node) == "SimpleSelectParens" {
3065            node = self.first(node);
3066        }
3067        node
3068    }
3069
3070    /// `ResultModifiers <- OrderByClause? LimitOffset?`.
3071    fn result_modifiers(&mut self, query: QueryRef, node: u32) -> Result<()> {
3072        let order = self.find(node, "OrderByClause");
3073        if order != NONE {
3074            let (items, all) = self.order_by(order)?;
3075            self.ast.queries[query as usize].order_by = self.order_slice(items);
3076            self.ast.queries[query as usize].order_by_all = all;
3077        }
3078        let limit = self.find(node, "LimitOffset");
3079        if limit != NONE {
3080            self.limit_offset(query, self.first(limit))?;
3081        }
3082        Ok(())
3083    }
3084
3085    /// The four spellings of a limit and an offset, in either order and either one alone.
3086    fn limit_offset(&mut self, query: QueryRef, node: u32) -> Result<()> {
3087        match self.name(node) {
3088            "LimitOffsetClause" | "OffsetLimitClause" => {
3089                let limit = self.find(node, "LimitClause");
3090                if limit != NONE {
3091                    self.limit(query, limit)?;
3092                }
3093                let offset = self.find(node, "OffsetClause");
3094                if offset != NONE {
3095                    self.offset(query, offset)?;
3096                }
3097                Ok(())
3098            }
3099            _ => self.unsupported(node),
3100        }
3101    }
3102
3103    /// `LimitClause <- 'LIMIT' LimitValue`.
3104    fn limit(&mut self, query: QueryRef, node: u32) -> Result<()> {
3105        let value = self.first(node);
3106        let inner = self.first(value);
3107        match self.name(inner) {
3108            // `LIMIT ALL` is no limit at all, which is what an absent limit already means.
3109            "LimitAll" => Ok(()),
3110            // `LimitExpression <- Expression '%'?`. The percent sign is a terminal so it leaves no
3111            // node behind, and the only thing that says it was written is the text of the rule that
3112            // matched it.
3113            "LimitExpression" => {
3114                let expr = self.expr(self.first(inner))?;
3115                self.ast.queries[query as usize].limit = expr;
3116                self.ast.queries[query as usize].limit_percent = self.text(inner).ends_with('%');
3117                Ok(())
3118            }
3119            "LimitLiteralPercent" => {
3120                let expr = self.expr(self.first(inner))?;
3121                self.ast.queries[query as usize].limit = expr;
3122                self.ast.queries[query as usize].limit_percent = true;
3123                Ok(())
3124            }
3125            _ => self.unsupported(inner),
3126        }
3127    }
3128
3129    /// `OffsetClause <- 'OFFSET' OffsetValue`, where `OffsetValue <- Expression RowOrRows?`.
3130    fn offset(&mut self, query: QueryRef, node: u32) -> Result<()> {
3131        let value = self.first(node);
3132        let expr = self.expr(self.first(value))?;
3133        self.ast.queries[query as usize].offset = expr;
3134        Ok(())
3135    }
3136
3137    /// `SimpleSelect <- SelectFrom WhereClause? GroupByClause? HavingClause? WindowClause?
3138    /// QualifyClause? SampleClause?`.
3139    fn simple_select(&mut self, node: u32) -> Result<SelectRef> {
3140        for name in ["QualifyClause", "SampleClause"] {
3141            let clause = self.find(node, name);
3142            if clause != NONE {
3143                return self.unsupported(clause);
3144            }
3145        }
3146        // The named windows go in before anything that could use one is walked, which is every
3147        // other clause of the block, including the target list that the grammar puts first.
3148        let mark = self.named_windows.len();
3149        let windows = self.find(node, "WindowClause");
3150        if windows != NONE {
3151            self.window_clause(windows)?;
3152        }
3153        let mut select = Select::empty();
3154        self.select_from(&mut select, self.first(node))?;
3155        let filter = self.find(node, "WhereClause");
3156        if filter != NONE {
3157            select.filter = self.expr(self.first(filter))?;
3158        }
3159        let group = self.find(node, "GroupByClause");
3160        if group != NONE {
3161            self.group_by(&mut select, self.first(group))?;
3162        }
3163        let having = self.find(node, "HavingClause");
3164        if having != NONE {
3165            select.having = self.expr(self.first(having))?;
3166        }
3167        self.named_windows.truncate(mark);
3168        Ok(self.push_select(select))
3169    }
3170
3171    /// `SelectFrom <- SelectFromClause / FromSelectClause`, which is `SELECT ... FROM ...` and
3172    /// DuckDB's `FROM ... SELECT ...` written the other way round.
3173    fn select_from(&mut self, select: &mut Select, node: u32) -> Result<()> {
3174        let clause = self.first(node);
3175        let targets = self.find(clause, "SelectClause");
3176        let from = self.find(clause, "FromClause");
3177        if from != NONE {
3178            select.from = self.sources(from)?;
3179        }
3180        if targets == NONE {
3181            // `FROM t` on its own. DuckDB reads it as `SELECT * FROM t`, and inventing the star
3182            // here rather than in the binder keeps the binder from having to know the shape of the
3183            // clause that was missing.
3184            let star = self
3185                .push(Expr::Star { qualifier: Slice::default(), replacements: Slice::default() });
3186            let start = self.ast.targets.len() as u32;
3187            self.ast.targets.push(Target { expr: star, alias: NONE });
3188            select.targets = Slice { start, len: 1 };
3189            return Ok(());
3190        }
3191        self.select_clause(select, targets)
3192    }
3193
3194    /// `SelectClause <- 'SELECT' DistinctClause? TargetList?`.
3195    fn select_clause(&mut self, select: &mut Select, node: u32) -> Result<()> {
3196        let distinct = self.find(node, "DistinctClause");
3197        if distinct != NONE {
3198            let inner = self.first(distinct);
3199            select.distinct = match self.name(inner) {
3200                // `SELECT ALL` is the default spelled out.
3201                "DistinctAll" => Distinct::No,
3202                "DistinctOn" => {
3203                    let on = self.find(inner, "DistinctOnTargets");
3204                    if on == NONE {
3205                        Distinct::Yes
3206                    } else {
3207                        let mut items = Vec::new();
3208                        for kid in self.kids(on) {
3209                            items.push(self.expr(kid)?);
3210                        }
3211                        Distinct::On(self.expr_slice(items))
3212                    }
3213                }
3214                _ => return self.unsupported(inner),
3215            };
3216        }
3217        let list = self.find(node, "TargetList");
3218        if list == NONE {
3219            return Ok(());
3220        }
3221        let mut targets = Vec::new();
3222        for kid in self.kids(list) {
3223            targets.push(self.target(kid)?);
3224        }
3225        select.targets = self.target_slice(targets);
3226        Ok(())
3227    }
3228
3229    /// `AliasedExpression <- ColIdExpression / ExpressionAsCollabel / ExpressionOptIdentifier`.
3230    fn target(&mut self, node: u32) -> Result<Target> {
3231        let inner = self.first(node);
3232        match self.name(inner) {
3233            // `ColIdExpression <- ColId ':' Expression`, the alias written first.
3234            "ColIdExpression" => {
3235                let alias = self.identifier(self.first(inner));
3236                let expr = self.expr(self.nth(inner, 1))?;
3237                Ok(Target { expr, alias })
3238            }
3239            "ExpressionAsCollabel" => {
3240                let expr = self.expr(self.first(inner))?;
3241                let alias = self.identifier(self.nth(inner, 1));
3242                Ok(Target { expr, alias })
3243            }
3244            "ExpressionOptIdentifier" => {
3245                let expr = self.expr(self.first(inner))?;
3246                let alias =
3247                    if self.count(inner) > 1 { self.identifier(self.nth(inner, 1)) } else { NONE };
3248                Ok(Target { expr, alias })
3249            }
3250            _ => self.unsupported(inner),
3251        }
3252    }
3253
3254    /// `GroupByClause <- 'GROUP' 'BY' GroupByExpressions`.
3255    fn group_by(&mut self, select: &mut Select, node: u32) -> Result<()> {
3256        let inner = self.first(node);
3257        match self.name(inner) {
3258            "GroupByAll" => {
3259                select.group_by_all = true;
3260                Ok(())
3261            }
3262            "GroupByList" => {
3263                let mut items = Vec::new();
3264                for kid in self.kids(inner) {
3265                    // `GroupByExpression <- EmptyGroupingItem / CubeOrRollupClause /
3266                    // GroupingSetsClause / GroupByBaseExpression`.
3267                    let expression = self.first(kid);
3268                    if self.name(expression) != "GroupByBaseExpression" {
3269                        return self.unsupported(expression);
3270                    }
3271                    items.push(self.expr(self.first(expression))?);
3272                }
3273                select.group_by = self.expr_slice(items);
3274                Ok(())
3275            }
3276            _ => self.unsupported(inner),
3277        }
3278    }
3279
3280    /// `OrderByClause <- 'ORDER' 'BY' OrderByExpressions`, where `OrderByExpressions <- OrderByAll
3281    /// / OrderByExpressionList`.
3282    fn order_by(&mut self, node: u32) -> Result<(Vec<OrderItem>, bool)> {
3283        let inner = self.first(self.first(node));
3284        match self.name(inner) {
3285            "OrderByAll" => {
3286                let (order, nulls) = self.sort_options(inner);
3287                Ok((vec![OrderItem { expr: NONE, order, nulls }], true))
3288            }
3289            "OrderByExpressionList" => {
3290                let mut items = Vec::new();
3291                for kid in self.kids(inner) {
3292                    // `OrderByExpression <- Expression DescOrAsc? NullsFirstOrLast?`.
3293                    let expr = self.expr(self.first(kid))?;
3294                    let (order, nulls) = self.sort_options(kid);
3295                    items.push(OrderItem { expr, order, nulls });
3296                }
3297                Ok((items, false))
3298            }
3299            _ => self.unsupported(inner),
3300        }
3301    }
3302
3303    /// The direction and the null placement of one sort key, either of which may be unwritten.
3304    fn sort_options(&self, node: u32) -> (Order, Nulls) {
3305        let direction = self.find(node, "DescOrAsc");
3306        let order = if direction == NONE {
3307            Order::Unstated
3308        } else if self.name(self.first(direction)) == "DescendingOrder" {
3309            Order::Descending
3310        } else {
3311            Order::Ascending
3312        };
3313        let placement = self.find(node, "NullsFirstOrLast");
3314        let nulls = if placement == NONE {
3315            Nulls::Unstated
3316        } else if self.name(self.first(placement)) == "NullsFirst" {
3317            Nulls::First
3318        } else {
3319            Nulls::Last
3320        };
3321        (order, nulls)
3322    }
3323
3324    // From clauses.
3325
3326    /// `FromClause <- 'FROM' List(TableRef)`.
3327    fn sources(&mut self, node: u32) -> Result<Slice> {
3328        let mut items = Vec::new();
3329        for kid in self.kids(node) {
3330            items.push(self.table_ref(kid)?);
3331        }
3332        let start = self.ast.source_lists.len() as u32;
3333        self.ast.source_lists.extend(items);
3334        Ok(Slice { start, len: self.ast.source_lists.len() as u32 - start })
3335    }
3336
3337    /// `TableRef <- InnerTableRef JoinOrPivot*`, left associative like the set operators.
3338    fn table_ref(&mut self, node: u32) -> Result<SourceRef> {
3339        let mut kids = self.kids(node);
3340        let head = kids.next().unwrap_or(NONE);
3341        let mut left = self.inner_table_ref(head)?;
3342        for tail in kids {
3343            let clause = self.first(tail);
3344            if self.name(clause) != "JoinClause" {
3345                return self.unsupported(clause);
3346            }
3347            left = self.join(left, self.first(clause))?;
3348        }
3349        Ok(left)
3350    }
3351
3352    /// `InnerTableRef <- ValuesRef / TableFunction / TableSubquery / BaseTableRef / ParensTableRef`.
3353    fn inner_table_ref(&mut self, node: u32) -> Result<SourceRef> {
3354        let inner = if self.name(node) == "InnerTableRef" { self.first(node) } else { node };
3355        match self.name(inner) {
3356            "BaseTableRef" => {
3357                if self.find(inner, "TableAliasColon") != NONE {
3358                    return self.unsupported(inner);
3359                }
3360                for name in ["AtClause", "SampleClause"] {
3361                    let clause = self.find(inner, name);
3362                    if clause != NONE {
3363                        return self.unsupported(clause);
3364                    }
3365                }
3366                let name = self.name_parts(self.find(inner, "BaseTableName"));
3367                let (alias, columns) = self.table_alias(self.find(inner, "TableAlias"));
3368                if name.len == 1 {
3369                    let part = self.ast.parts[name.start as usize];
3370                    if let Some(&(_, held, declared)) =
3371                        self.ctes.iter().rev().find(|&&(cte, _, _)| {
3372                            self.ast.string(cte).eq_ignore_ascii_case(self.ast.string(part))
3373                        })
3374                    {
3375                        match held {
3376                            Held::Inline(query) => {
3377                                let alias = if alias == NONE { part } else { alias };
3378                                let columns = if columns.is_empty() { declared } else { columns };
3379                                return Ok(self.push_source(Source::Subquery {
3380                                    query,
3381                                    alias,
3382                                    columns,
3383                                }));
3384                            }
3385                            // The alias is left as it was written, which for a bare name is
3386                            // nothing at all, because the definition already has the name and a
3387                            // reference that invented one would print itself as `c AS c`.
3388                            Held::Once(cte) => {
3389                                return Ok(self.push_source(Source::Cte { cte, alias, columns }));
3390                            }
3391                        }
3392                    }
3393                }
3394                Ok(self.push_source(Source::Table { name, alias, columns }))
3395            }
3396            // `LATERAL` is read and dropped. A FROM entry here already sees the entries written to
3397            // its left, which is what the word asks for, so writing it changes nothing and the
3398            // pinned build resolves the same query with and without it.
3399            "TableSubquery" => {
3400                if self.find(inner, "TableAliasColon") != NONE {
3401                    return self.unsupported(inner);
3402                }
3403                // `SubqueryReference <- Parens(SelectStatementInternal)`.
3404                let reference = self.find(inner, "SubqueryReference");
3405                let query = self.query(self.first(reference))?;
3406                let (alias, columns) = self.table_alias(self.find(inner, "TableAlias"));
3407                Ok(self.push_source(Source::Subquery { query, alias, columns }))
3408            }
3409            // `TableFunction <- TableFunctionLateralOpt / TableFunctionAliasColon`, and
3410            // `TableFunctionLateralOpt <- Lateral? QualifiedTableFunction TableFunctionArguments
3411            // WithOrdinality? TableAlias?`. The colon form is its own work and `WITH ORDINALITY`
3412            // adds a column, so both are turned away rather than dropped. `LATERAL` is read and
3413            // dropped, for the reason given above `TableSubquery`.
3414            "TableFunction" => {
3415                let form = self.first(inner);
3416                for name in ["TableAliasColon", "WithOrdinality", "SampleClause"] {
3417                    let clause = self.find(form, name);
3418                    if clause != NONE {
3419                        return self.unsupported(clause);
3420                    }
3421                }
3422                let name = self.name_parts(self.find(form, "QualifiedTableFunction"));
3423                let mut args = Vec::new();
3424                // `TableFunctionArguments <- Parens(List(FunctionArgument)?)`, so a call with no
3425                // arguments has the wrapper and no list under it.
3426                let list = self.find(form, "TableFunctionArguments");
3427                for kid in self.kids(list) {
3428                    args.push(self.table_argument(kid)?);
3429                }
3430                let args = self.target_slice(args);
3431                let (alias, columns) = self.table_alias(self.find(form, "TableAlias"));
3432                Ok(self.push_source(Source::Function { name, args, alias, columns, pragma: false }))
3433            }
3434            "ValuesRef" => {
3435                if self.find(inner, "TableAliasColon") != NONE {
3436                    return self.unsupported(inner);
3437                }
3438                let rows = self.values_clause(self.find(inner, "ValuesClause"))?;
3439                let (alias, columns) = self.table_alias(self.find(inner, "TableAlias"));
3440                Ok(self.push_source(Source::Values { rows, alias, columns }))
3441            }
3442            "ParensTableRef" => {
3443                if self.find(inner, "TableAliasColon") != NONE
3444                    || self.find(inner, "SampleClause") != NONE
3445                    || self.find(inner, "TableAlias") != NONE
3446                {
3447                    return self.unsupported(inner);
3448                }
3449                self.table_ref(self.find(inner, "TableRef"))
3450            }
3451            _ => self.unsupported(inner),
3452        }
3453    }
3454
3455    /// `TableAlias <- TableAliasAs / TableAliasWithoutAs`, either with a column alias list.
3456    fn table_alias(&mut self, node: u32) -> (StrRef, Slice) {
3457        if node == NONE {
3458            return (NONE, Slice::default());
3459        }
3460        let inner = self.first(node);
3461        let alias = self.identifier(self.first(inner));
3462        let list = self.find(inner, "ColumnAliases");
3463        if list == NONE {
3464            return (alias, Slice::default());
3465        }
3466        let mut columns = Vec::new();
3467        for kid in self.kids(list) {
3468            let name = self.identifier(kid);
3469            columns.push(name);
3470        }
3471        (alias, self.part_slice(columns))
3472    }
3473
3474    /// `JoinClause <- JoinByClause / RegularJoinClause / JoinWithoutOnClause / NearestJoinClause`.
3475    fn join(&mut self, left: SourceRef, node: u32) -> Result<SourceRef> {
3476        match self.name(node) {
3477            // `RegularJoinClause <- Asof? JoinType? 'JOIN' TableRef JoinQualifier`.
3478            "RegularJoinClause" => {
3479                if self.find(node, "Asof") != NONE {
3480                    return self.unsupported(node);
3481                }
3482                let kind = self.join_type(self.find(node, "JoinType"));
3483                let right = self.table_ref(self.find(node, "TableRef"))?;
3484                let (on, using) = self.join_qualifier(self.find(node, "JoinQualifier"))?;
3485                Ok(self.push_source(Source::Join { left, right, kind, natural: false, on, using }))
3486            }
3487            // `JoinWithoutOnClause <- JoinPrefix 'JOIN' InnerTableRef`, which is cross, natural and
3488            // positional. Those three are exactly the joins that carry no condition.
3489            "JoinWithoutOnClause" => {
3490                let prefix = self.first(self.find(node, "JoinPrefix"));
3491                let (kind, natural) = match self.name(prefix) {
3492                    "CrossJoinPrefix" => (JoinKind::Cross, false),
3493                    "PositionalJoinPrefix" => (JoinKind::Positional, false),
3494                    "NaturalJoinPrefix" => (self.join_type(self.find(prefix, "JoinType")), true),
3495                    _ => return self.unsupported(prefix),
3496                };
3497                let right = self.inner_table_ref(self.find(node, "InnerTableRef"))?;
3498                Ok(self.push_source(Source::Join {
3499                    left,
3500                    right,
3501                    kind,
3502                    natural,
3503                    on: NONE,
3504                    using: Slice::default(),
3505                }))
3506            }
3507            _ => self.unsupported(node),
3508        }
3509    }
3510
3511    /// `JoinType <- FullJoin / LeftJoin / RightJoin / SemiJoin / AntiJoin / InnerJoin`, absent
3512    /// meaning inner, which is what SQL has always meant by a bare `JOIN`.
3513    fn join_type(&self, node: u32) -> JoinKind {
3514        if node == NONE {
3515            return JoinKind::Inner;
3516        }
3517        match self.name(self.first(node)) {
3518            "FullJoin" => JoinKind::Full,
3519            "LeftJoin" => JoinKind::Left,
3520            "RightJoin" => JoinKind::Right,
3521            "SemiJoin" => JoinKind::Semi,
3522            "AntiJoin" => JoinKind::Anti,
3523            _ => JoinKind::Inner,
3524        }
3525    }
3526
3527    /// `JoinQualifier <- OnClause / UsingClause`.
3528    fn join_qualifier(&mut self, node: u32) -> Result<(ExprRef, Slice)> {
3529        let inner = self.first(node);
3530        match self.name(inner) {
3531            "OnClause" => Ok((self.expr(self.first(inner))?, Slice::default())),
3532            "UsingClause" => {
3533                let mut columns = Vec::new();
3534                for kid in self.kids(inner) {
3535                    let name = self.identifier(kid);
3536                    columns.push(name);
3537                }
3538                Ok((NONE, self.part_slice(columns)))
3539            }
3540            _ => self.unsupported(inner),
3541        }
3542    }
3543
3544    // Expressions.
3545
3546    /// One expression, from wherever in the precedence chain it starts.
3547    ///
3548    /// The loop is the whole design. A rule that says something gets an arm, a rule with exactly
3549    /// one child that said nothing is stepped through, and anything else is an error naming itself.
3550    /// The chain rules never get an arm for their one child case, which is why adding a precedence
3551    /// level upstream costs nothing here.
3552    ///
3553    /// Said nothing means covered no text of its own. A keyword is not a child of the node that
3554    /// spells it, so `TRIM(x)` is a rule with one child and that child is `x`, and stepping through
3555    /// on the child count alone threw the `TRIM` away and answered the untrimmed string. Comparing
3556    /// the two spans is what tells the two cases apart: a precedence rule with one child covers
3557    /// exactly what its child covers, and a rule that wrote a keyword or a bracket covers more.
3558    /// That is the rule rather than a list of the names it happened to be wrong about, because the
3559    /// grammar has eleven hundred rules and the ones with a keyword and one child are not enumerable
3560    /// by reading the ones that are wrong today.
3561    fn expr(&mut self, node: u32) -> Result<ExprRef> {
3562        let span = self.span(node);
3563        let outer = std::mem::replace(&mut self.current_span, span);
3564        let result = self.expr_inner(node);
3565        self.current_span = outer;
3566        result
3567    }
3568
3569    fn expr_inner(&mut self, node: u32) -> Result<ExprRef> {
3570        let mut node = node;
3571        loop {
3572            let count = self.count(node);
3573            let name = self.name(node);
3574            match name {
3575                "LogicalOrExpression" | "ColDefOrExpr" if count > 1 => {
3576                    return self.logical(node, BinaryOp::Or);
3577                }
3578                "LogicalAndExpression" | "ColDefAndExpr" if count > 1 => {
3579                    return self.logical(node, BinaryOp::And);
3580                }
3581                "DefaultExpression" => return Ok(self.push(Expr::Default)),
3582                "LogicalNotExpression" if count > 1 => return self.logical_not(node),
3583                "IsExpression" if count > 1 => return self.is_expression(node),
3584                "BetweenInLikeExpression" if count > 1 => return self.between_in_like(node),
3585                "PrefixExpression" if count > 1 => return self.prefix(node),
3586                "BaseExpression" if count > 1 => return self.indirection(node),
3587                "LambdaArrowExpression"
3588                | "IsDistinctFromExpression"
3589                | "ComparisonExpression"
3590                | "OtherOperatorExpression"
3591                | "BitwiseExpression"
3592                | "AdditiveExpression"
3593                | "MultiplicativeExpression"
3594                | "ExponentiationExpression"
3595                | "CollateExpression"
3596                | "AtTimeZoneExpression"
3597                    if count > 1 =>
3598                {
3599                    return self.tail_chain(node);
3600                }
3601                "ColumnReference" => {
3602                    let name = self.name_parts(node);
3603                    return Ok(self.push(Expr::Column { name }));
3604                }
3605                "StarExpression" => return self.star(node),
3606                "NumberLiteral" => {
3607                    let text = self.text(node).to_string();
3608                    let text = self.intern(&text);
3609                    return Ok(self.push(Expr::Literal { kind: LiteralKind::Number, text }));
3610                }
3611                "StringLiteral" => return self.string_literal(node),
3612                "NullLiteral" | "TrueLiteral" | "FalseLiteral" => {
3613                    let kind = match name {
3614                        "NullLiteral" => LiteralKind::Null,
3615                        "TrueLiteral" => LiteralKind::True,
3616                        _ => LiteralKind::False,
3617                    };
3618                    return Ok(self.push(Expr::Literal { kind, text: NONE }));
3619                }
3620                "FunctionExpression" => return self.function(node),
3621                "CoalesceExpression" => return self.coalesce(node),
3622                "NullIfExpression" => return self.null_if(node),
3623                "TryExpression" => return self.try_expression(node),
3624                "LambdaExpression" => return self.lambda(node),
3625                "SubstringExpression" => return self.substring(node),
3626                "PositionExpression" => return self.position(node),
3627                "TrimExpression" => return self.trim(node),
3628                "OverlayExpression" => return self.overlay(node),
3629                "ExtractExpression" => return self.extract(node),
3630                "CastExpression" => return self.cast(node),
3631                "TypeLiteral" => return self.typed_literal(node),
3632                "IntervalLiteral" => return self.interval_literal(node),
3633                "CaseExpression" => return self.case(node),
3634                "ParenthesisExpression" => return self.row(node),
3635                "RowExpression" => return self.row_expression(node),
3636                // `ParensExpression <- Parens(Expression)` covers more text than its child and
3637                // still says nothing about the value, because the brackets are grouping. It is the
3638                // one rule of that shape, which is why it is an arm rather than a second rule in
3639                // the step below. `ParenthesisExpression` is not this: it holds a list, and a list
3640                // of more than one is a row.
3641                "ParensExpression" if count == 1 => node = self.first(node),
3642                "BoundedListExpression" => return self.list(node),
3643                "ArrayParensSelect" => {
3644                    let query = self.query(self.descendant(node, "SelectStatementInternal"))?;
3645                    return Ok(self.push(Expr::Subquery { query, array: true }));
3646                }
3647                "ArrayBoundedListExpression" => {
3648                    let inner = self.find(node, "BoundedListExpression");
3649                    let list = self.list(inner)?;
3650                    if self.text(node).len() != self.text(inner).len() {
3651                        self.ast.array_lists.push(list);
3652                    }
3653                    return Ok(list);
3654                }
3655                "StructExpression" => return self.structure(node),
3656                "MapExpression" => return self.map(node),
3657                "QuestionMarkNumberedParameter"
3658                | "AnonymousParameter"
3659                | "NumberedParameter"
3660                | "ColLabelParameter" => return self.parameter(node),
3661                "SubqueryExpression" => return self.subquery(node),
3662                _ if count == 1 && self.text(self.first(node)) == self.text(node) => {
3663                    node = self.first(node);
3664                }
3665                _ => return self.unsupported(node),
3666            }
3667        }
3668    }
3669
3670    /// `X <- Y XTail*` where `XTail <- Operator Y`, the shape ten precedence levels share.
3671    fn tail_chain(&mut self, node: u32) -> Result<ExprRef> {
3672        let mut kids = self.kids(node);
3673        let head = kids.next().unwrap_or(NONE);
3674        let mut left = self.expr(head)?;
3675        for tail in kids {
3676            // `SingleArrowPair <- '->' LogicalOrExpression` has no operator node, since the arrow is
3677            // a bare token, so the one child is the operand. It is the old lambda spelling or the
3678            // JSON operator, and the binder is where the two are told apart.
3679            if self.name(tail) == "SingleArrowPair" {
3680                let right = self.expr(self.first(tail))?;
3681                left = self.push(Expr::Binary { op: BinaryOp::Arrow, left, right });
3682                continue;
3683            }
3684            let operator = self.first(tail);
3685            // `ComparisonExpressionTail <- ComparisonOperator NotExpression? BetweenInLikeExpression`
3686            // is the one tail with an optional middle, so the operand is the last child and not the
3687            // second one. Taking the last is right for every tail and wrong for none.
3688            let operand = self.kids(tail).last().unwrap_or(NONE);
3689            if self.count(tail) > 2 {
3690                return self.unsupported(tail);
3691            }
3692            if self.contains(operator, "AnyAllParsedOperator") {
3693                let any_op = self.descendant(operator, "AnyOp");
3694                let op = self.binary_op(any_op)?;
3695                let reference = self.descendant(operand, "SubqueryReference");
3696                if reference == NONE {
3697                    return self.unsupported(operand);
3698                }
3699                let query = self.query(self.first(reference))?;
3700                let all = self.contains(operator, "SubqueryAll");
3701                left = self.push(Expr::QuantifiedSubquery { operand: left, op, query, all });
3702                continue;
3703            }
3704            let op = self.binary_op(operator)?;
3705            let right = self.expr(operand)?;
3706            left = self.push(Expr::Binary { op, left, right });
3707        }
3708        Ok(left)
3709    }
3710
3711    /// Which infix operator a tail's operator node is.
3712    fn binary_op(&mut self, node: u32) -> Result<BinaryOp> {
3713        // The operator rules nest: `ComparisonOperator` over `OperatorGreaterThan` over the symbol
3714        // itself. Every one of them covers the same tokens, so the text is the same at every level
3715        // and reading it once at the top is enough. The name is not, which is why the bottom of the
3716        // chain is walked to as well: `OtherOperator` says nothing and `OperatorLiteral` says
3717        // everything, and they are three levels apart.
3718        let mut leaf = node;
3719        while self.count(leaf) == 1 {
3720            leaf = self.first(leaf);
3721        }
3722        let text = self.text(node);
3723        let upper = text.to_ascii_uppercase();
3724        let op = match upper.as_str() {
3725            "OR" => BinaryOp::Or,
3726            "AND" => BinaryOp::And,
3727            "=" | "==" => BinaryOp::Eq,
3728            "!=" | "<>" => BinaryOp::NotEq,
3729            "<" => BinaryOp::Lt,
3730            ">" => BinaryOp::Gt,
3731            "<=" => BinaryOp::LtEq,
3732            ">=" => BinaryOp::GtEq,
3733            "+" => BinaryOp::Add,
3734            "-" => BinaryOp::Subtract,
3735            "*" => BinaryOp::Multiply,
3736            "/" => BinaryOp::Divide,
3737            "//" => BinaryOp::IntegerDivide,
3738            "%" => BinaryOp::Modulo,
3739            "**" => BinaryOp::Power,
3740            "^" => BinaryOp::Caret,
3741            "&" => BinaryOp::BitAnd,
3742            "|" => BinaryOp::BitOr,
3743            "<<" => BinaryOp::ShiftLeft,
3744            ">>" => BinaryOp::ShiftRight,
3745            "||" => BinaryOp::Concat,
3746            "COLLATE" => BinaryOp::Collate,
3747            "->" => BinaryOp::Arrow,
3748            "->>" => BinaryOp::LongArrow,
3749            "@>" => BinaryOp::Contains,
3750            "<@" => BinaryOp::ContainedBy,
3751            "&&" => BinaryOp::Overlaps,
3752            "^@" => BinaryOp::StartsWith,
3753            "<<=" => BinaryOp::InetContainedByOrEq,
3754            ">>=" => BinaryOp::InetContainsOrEq,
3755            _ if self.name(leaf) == "AtTimeZoneOperator" => BinaryOp::AtTimeZone,
3756            // `IsDistinctFromOp <- 'IS' 'NOT'? 'DISTINCT' 'FROM'`, told apart by the middle word,
3757            // which is not in the tree because keywords are terminals.
3758            _ if self.name(leaf) == "IsDistinctFromOp" => {
3759                if upper.split_whitespace().any(|word| word == "NOT") {
3760                    BinaryOp::IsNotDistinctFrom
3761                } else {
3762                    BinaryOp::IsDistinctFrom
3763                }
3764            }
3765            // `OperatorLiteral` is the open end of the operator set. Its body in the grammar text
3766            // says `Identifier`, but it is one of the 24 rules whose body the matcher does not
3767            // walk and the matcher it is overridden to is the bare operator one, so what it
3768            // actually accepts is any run of operator characters that is not already a token.
3769            // `a <=> b` is such a run, DuckDB resolves it as a two argument function of that name,
3770            // and rejecting it here would reject SQL DuckDB accepts.
3771            _ if self.name(leaf) == "OperatorLiteral" => {
3772                let interned = self.intern(text);
3773                BinaryOp::Named(interned)
3774            }
3775            _ => return self.unsupported(node),
3776        };
3777        Ok(op)
3778    }
3779
3780    /// `LogicalOrExpression <- LogicalAndExpression LogicalOrExpressionTail*`, and the `AND` twin.
3781    ///
3782    /// Separate from the other tails because the tail here is `'OR' LogicalAndExpression` with the
3783    /// keyword as a terminal, so there is no operator node to read and the operator is the rule.
3784    fn logical(&mut self, node: u32, op: BinaryOp) -> Result<ExprRef> {
3785        let mut kids = self.kids(node);
3786        let head = kids.next().unwrap_or(NONE);
3787        let mut left = self.expr(head)?;
3788        for tail in kids {
3789            let right = self.expr(self.first(tail))?;
3790            left = self.push(Expr::Binary { op, left, right });
3791        }
3792        Ok(left)
3793    }
3794
3795    /// `LogicalNotExpression <- NotExpression? IsExpression`, where `NotExpression <- NotKeyword+`.
3796    ///
3797    /// The plus matters. `NOT NOT x` is two nodes in the parse tree and two negations in the AST,
3798    /// and folding them here would be an optimizer decision taken in the parser.
3799    fn logical_not(&mut self, node: u32) -> Result<ExprRef> {
3800        let negations = self.count(self.first(node));
3801        let mut expr = self.expr(self.nth(node, 1))?;
3802        for _ in 0..negations {
3803            expr = self.push(Expr::Unary { op: UnaryOp::Not, operand: expr });
3804        }
3805        Ok(expr)
3806    }
3807
3808    /// `IsExpression <- IsDistinctFromExpression IsTest*`, the postfix null and boolean tests.
3809    fn is_expression(&mut self, node: u32) -> Result<ExprRef> {
3810        let mut kids = self.kids(node);
3811        let head = kids.next().unwrap_or(NONE);
3812        let mut expr = self.expr(head)?;
3813        for test in kids {
3814            let inner = self.first(test);
3815            let negated = self.text(inner).to_ascii_uppercase().contains("NOT");
3816            let op = match self.name(inner) {
3817                "NotNull" => UnaryOp::IsNotNull,
3818                "IsNull" => UnaryOp::IsNull,
3819                // `IsLiteral <- 'IS' 'NOT'? IsLiteralValue`, and the value rule is one more level
3820                // down again because it is a choice of four and not four alternatives inlined.
3821                "IsLiteral" => match self.name(self.first(self.first(inner))) {
3822                    "NullLiteral" if negated => UnaryOp::IsNotNull,
3823                    "NullLiteral" => UnaryOp::IsNull,
3824                    "TrueLiteral" if negated => UnaryOp::IsNotTrue,
3825                    "TrueLiteral" => UnaryOp::IsTrue,
3826                    "FalseLiteral" if negated => UnaryOp::IsNotFalse,
3827                    "FalseLiteral" => UnaryOp::IsFalse,
3828                    "UnknownLiteral" if negated => UnaryOp::IsNotUnknown,
3829                    "UnknownLiteral" => UnaryOp::IsUnknown,
3830                    _ => return self.unsupported(inner),
3831                },
3832                _ => return self.unsupported(inner),
3833            };
3834            expr = self.push(Expr::Unary { op, operand: expr });
3835        }
3836        Ok(expr)
3837    }
3838
3839    /// `BetweenInLikeExpression <- OtherOperatorExpression BetweenInLikeOp?`.
3840    fn between_in_like(&mut self, node: u32) -> Result<ExprRef> {
3841        let operand = self.expr(self.first(node))?;
3842        // `BetweenInLikeOp <- 'NOT'? BetweenInLikeOpExpression`. The `NOT` is a terminal, so what
3843        // says it was written is that the op node covers a token the inner node does not.
3844        let op = self.nth(node, 1);
3845        let negated = self.text(op).to_ascii_uppercase().starts_with("NOT");
3846        let inner = self.first(self.first(op));
3847        match self.name(inner) {
3848            // `BetweenClause <- 'BETWEEN' x 'AND' y`.
3849            "BetweenClause" => {
3850                let low = self.expr(self.first(inner))?;
3851                let high = self.expr(self.nth(inner, 1))?;
3852                Ok(self.push(Expr::Between { operand, low, high, negated }))
3853            }
3854            // `InClause <- 'IN' InExpression`.
3855            "InClause" => {
3856                let expression = self.first(self.first(inner));
3857                match self.name(expression) {
3858                    "InExpressionList" => {
3859                        let mut items = Vec::new();
3860                        for kid in self.kids(expression) {
3861                            items.push(self.expr(kid)?);
3862                        }
3863                        let list = self.expr_slice(items);
3864                        Ok(self.push(Expr::In { operand, list, negated }))
3865                    }
3866                    "InSelectStatement" => {
3867                        let query = self.query(self.first(expression))?;
3868                        Ok(self.push(Expr::InSubquery { operand, query, negated }))
3869                    }
3870                    _ => self.unsupported(expression),
3871                }
3872            }
3873            // `LikeClause <- LikeVariations x EscapeClause?`.
3874            "LikeClause" => {
3875                if self.find(inner, "EscapeClause") != NONE {
3876                    return self.unsupported(inner);
3877                }
3878                let variation = self.name(self.first(self.first(inner)));
3879                let op = match (variation, negated) {
3880                    ("LikeToken", false) | ("NotLikeOp", true) => BinaryOp::Like,
3881                    ("LikeToken", true) | ("NotLikeOp", false) => BinaryOp::NotLike,
3882                    ("ILikeToken", false) | ("NotILikeOp", true) => BinaryOp::ILike,
3883                    ("ILikeToken", true) | ("NotILikeOp", false) => BinaryOp::NotILike,
3884                    // Glob and the bare regex match have no negated spelling of their own in
3885                    // `LikeVariations`, so a `NOT` in front of either stays an explicit negation.
3886                    ("GlobToken", _) => BinaryOp::Glob,
3887                    ("RegexMatchToken", _) => BinaryOp::Regex,
3888                    ("SimilarToToken", false) => BinaryOp::SimilarTo,
3889                    ("SimilarToToken", true) => BinaryOp::NotSimilarTo,
3890                    ("NotSimilarToOp", false) => BinaryOp::NotRegex,
3891                    ("NotSimilarToOp", true) => BinaryOp::Regex,
3892                    ("RegexInsensitiveMatchToken", false)
3893                    | ("NotRegexInsensitiveMatchOp", true) => BinaryOp::RegexInsensitive,
3894                    ("RegexInsensitiveMatchToken", true)
3895                    | ("NotRegexInsensitiveMatchOp", false) => BinaryOp::NotRegexInsensitive,
3896                    _ => return self.unsupported(inner),
3897                };
3898                let right = self.expr(self.nth(inner, 1))?;
3899                let expr = self.push(Expr::Binary { op, left: operand, right });
3900                // The like family folds its negation into the operator because it has a spelling
3901                // for the negated form. Glob and regex do not, so theirs stays where it was.
3902                if negated && matches!(op, BinaryOp::Glob | BinaryOp::Regex) {
3903                    return Ok(self.push(Expr::Unary { op: UnaryOp::Not, operand: expr }));
3904                }
3905                Ok(expr)
3906            }
3907            _ => self.unsupported(inner),
3908        }
3909    }
3910
3911    /// `PrefixExpression <- PrefixOperator* BaseExpression`, applied right to left.
3912    fn prefix(&mut self, node: u32) -> Result<ExprRef> {
3913        let kids: Vec<u32> = self.kids(node).collect();
3914        let mut expr = self.expr(kids[kids.len() - 1])?;
3915        for &operator in kids[..kids.len() - 1].iter().rev() {
3916            let op = match self.name(self.first(operator)) {
3917                "MinusPrefixOperator" => UnaryOp::Negate,
3918                "PlusPrefixOperator" => UnaryOp::Plus,
3919                "TildePrefixOperator" => UnaryOp::BitNot,
3920                _ => return self.unsupported(operator),
3921            };
3922            expr = self.push(Expr::Unary { op, operand: expr });
3923        }
3924        Ok(expr)
3925    }
3926
3927    /// `BaseExpression <- SingleExpression IndirectionList?`, the postfix chain.
3928    fn indirection(&mut self, node: u32) -> Result<ExprRef> {
3929        let mut expr = self.expr(self.first(node))?;
3930        for step in self.kids(self.nth(node, 1)) {
3931            let inner = self.first(step);
3932            expr = match self.name(inner) {
3933                // `CastOperator <- '::' Type`.
3934                "CastOperator" => {
3935                    let text = self.text(self.first(inner)).to_string();
3936                    let ty = self.intern(&text);
3937                    self.push(Expr::Cast { operand: expr, ty, try_cast: false })
3938                }
3939                "DotOperator" => {
3940                    let dot = self.first(inner);
3941                    match self.name(dot) {
3942                        // `DotColumnOperator <- '.' ColLabel`, which DuckDB resolves as a call of
3943                        // `struct_extract`. Writing it as that call rather than as its own node
3944                        // keeps the binder from needing a rule for a thing that is already a
3945                        // function.
3946                        "DotColumnOperator" => {
3947                            let field = self.identifier(self.first(dot));
3948                            let text = self.ast.string(field).to_string();
3949                            let literal = self.intern(&text);
3950                            let key = self
3951                                .push(Expr::Literal { kind: LiteralKind::String, text: literal });
3952                            let name = self.function_name("struct_extract");
3953                            let args = self.expr_slice(vec![expr, key]);
3954                            self.push(Expr::Function { name, args, distinct: false, filter: NONE })
3955                        }
3956                        // `DotMethodOperator <- '.' MethodExpression`, where `x.f(a)` is `f(x, a)`.
3957                        "DotMethodOperator" => {
3958                            let method = self.first(dot);
3959                            let text = self.text(self.first(method)).to_string();
3960                            let text = unquote(&text);
3961                            let name = self.function_name(&text);
3962                            let mut args = vec![expr];
3963                            let list = self.find(method, "MethodExpressionArguments");
3964                            if list != NONE {
3965                                let inner = self.first(list);
3966                                let arguments = self.find(inner, "MethodFunctionArguments");
3967                                if arguments != NONE {
3968                                    for kid in self.kids(arguments) {
3969                                        let (named, arg) = self.argument(kid)?;
3970                                        if named != NONE {
3971                                            return self.unsupported(kid);
3972                                        }
3973                                        args.push(arg);
3974                                    }
3975                                }
3976                            }
3977                            let args = self.expr_slice(args);
3978                            self.push(Expr::Function { name, args, distinct: false, filter: NONE })
3979                        }
3980                        _ => return self.unsupported(dot),
3981                    }
3982                }
3983                // `SliceExpression <- '[' SliceBound ']'` over
3984                // `SliceBound <- Expression? EndSliceBound? StepSliceBound?`, so a subscript is one
3985                // index when neither colon is there and a range when either of them is. Both become
3986                // a call, the same two calls DuckDB's own transformer writes.
3987                "SliceExpression" => self.subscript(inner, expr)?,
3988                // `PostfixOperator <- '!'`.
3989                "PostfixOperator" => {
3990                    self.push(Expr::Unary { op: UnaryOp::Factorial, operand: expr })
3991                }
3992                _ => return self.unsupported(inner),
3993            };
3994        }
3995        Ok(expr)
3996    }
3997
3998    /// `SliceExpression <- '[' SliceBound ']'`, which is `array_extract` or `array_slice`.
3999    ///
4000    /// The three parts of the bound are all optional and any of the eight combinations parses, so
4001    /// which call this is comes from which parts are there rather than from how many children the
4002    /// bound has. One expression and no colon is an index. Anything with a colon in it is a range,
4003    /// and a range the query did not write both ends of gets the ends DuckDB's transformer gives it:
4004    /// a missing begin is 1 and a missing end is -1, which is the last element, so `x[:]` is the
4005    /// whole of `x` and `array_slice(x, 1, -1)` answers the same thing.
4006    ///
4007    /// `EndSliceMinus` is the `-` in `x[1:-]`, which upstream reads as a range with no end rather
4008    /// than as a subtraction of nothing, and it answers `x[1:]`. So it is the missing end too.
4009    ///
4010    /// The step is the odd one. `x[1:2:]` is a step that is written and empty, and what upstream
4011    /// does with it is pass a list where the step goes, which then fails to bind because the fourth
4012    /// parameter is a BIGINT. The empty list here is that, measured off the pinned binary: it says
4013    /// `array_slice(INTEGER[], INTEGER_LITERAL, INTEGER_LITERAL, INTEGER[])` has no match, and the
4014    /// fourth type in that sentence is the list. Writing a 1 there instead would answer a row where
4015    /// the reference refuses.
4016    fn subscript(&mut self, node: u32, target: ExprRef) -> Result<ExprRef> {
4017        let bound = self.first(node);
4018        let (mut begin, mut end, mut step) = (NONE, NONE, NONE);
4019        for kid in self.kids(bound) {
4020            match self.name(kid) {
4021                "EndSliceBound" => end = kid,
4022                "StepSliceBound" => step = kid,
4023                _ => begin = kid,
4024            }
4025        }
4026        if end == NONE && step == NONE {
4027            if begin == NONE {
4028                return Err(Error::parser("Empty subscript '[]' is not allowed"));
4029            }
4030            let index = self.expr(begin)?;
4031            let name = self.function_name("array_extract");
4032            let args = self.expr_slice(vec![target, index]);
4033            return Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }));
4034        }
4035        let first = if begin == NONE { self.literal_number("1") } else { self.expr(begin)? };
4036        // `EndSliceBound <- ':' EndSliceValue?` and `EndSliceValue <- Expression / EndSliceMinus`,
4037        // so the end is written only when the value is there and is not the lone hyphen.
4038        let value = if end == NONE { NONE } else { self.find(end, "EndSliceValue") };
4039        let written = if value == NONE { NONE } else { self.first(value) };
4040        let last = if written == NONE || self.name(written) == "EndSliceMinus" {
4041            self.literal_number("-1")
4042        } else {
4043            self.expr(written)?
4044        };
4045        let mut args = vec![target, first, last];
4046        if step != NONE {
4047            let by = self.first(step);
4048            args.push(if by == NONE {
4049                self.push(Expr::List { items: Slice::default() })
4050            } else {
4051                self.expr(by)?
4052            });
4053        }
4054        let name = self.function_name("array_slice");
4055        let args = self.expr_slice(args);
4056        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4057    }
4058
4059    /// A number literal the transformer writes rather than reads, for a bound a range left out.
4060    fn literal_number(&mut self, digits: &str) -> ExprRef {
4061        let text = self.intern(digits);
4062        self.push(Expr::Literal { kind: LiteralKind::Number, text })
4063    }
4064
4065    /// A one part function name, for the calls the transformer invents rather than reads.
4066    fn function_name(&mut self, name: &str) -> Slice {
4067        let interned = self.intern(name);
4068        self.part_slice(vec![interned])
4069    }
4070
4071    /// `StarExpression <- StarQualifierList? '*' ExcludeList? ReplaceList? RenameList?`.
4072    fn star(&mut self, node: u32) -> Result<ExprRef> {
4073        for name in ["ExcludeList", "RenameList"] {
4074            let list = self.find(node, name);
4075            if list != NONE {
4076                return self.unsupported(list);
4077            }
4078        }
4079        let replace = self.find(node, "ReplaceList");
4080        let replacements =
4081            if replace == NONE { Slice::default() } else { self.replacements(replace)? };
4082        let qualifier = self.find(node, "StarQualifierList");
4083        let qualifier =
4084            if qualifier == NONE { Slice::default() } else { self.name_parts(qualifier) };
4085        Ok(self.push(Expr::Star { qualifier, replacements }))
4086    }
4087
4088    /// `ReplaceList <- 'REPLACE' ReplaceEntries`, where an entry is `Expression 'AS'
4089    /// ColumnReference` and the entries are one bare entry or a parenthesized list of them.
4090    ///
4091    /// The duplicate check is here rather than in the binder because that is where DuckDB does it:
4092    /// naming the same column twice is a Parser Error there, and it is one of the few things about
4093    /// a star that can be decided without knowing what the star stands for.
4094    fn replacements(&mut self, node: u32) -> Result<Slice> {
4095        // `ReplaceEntries <- ReplaceEntrySingle / ReplaceEntryList` and both of those hold the
4096        // entries as their own children, so the same walk reads either shape.
4097        let entries = self.first(self.first(node));
4098        let listed: Vec<u32> =
4099            self.kids(entries).filter(|&kid| self.name(kid) == "ReplaceEntry").collect();
4100        let mut replacements = Vec::with_capacity(listed.len());
4101        for entry in listed {
4102            let expr = self.expr(self.first(entry))?;
4103            let alias = self.identifier(self.nth(entry, 1));
4104            let written = self.ast.string(alias).to_string();
4105            if replacements
4106                .iter()
4107                .any(|held: &Target| self.ast.string(held.alias).eq_ignore_ascii_case(&written))
4108            {
4109                return Err(Error::parser(format!(
4110                    "Duplicate entry \"{written}\" in REPLACE list"
4111                )));
4112            }
4113            replacements.push(Target { expr, alias });
4114        }
4115        Ok(self.target_slice(replacements))
4116    }
4117
4118    /// `FunctionExpression <- FunctionIdentifier FunctionExpressionArguments WithinGroupClause?
4119    /// FilterClause? ExportClause? OverClause?`.
4120    fn function(&mut self, node: u32) -> Result<ExprRef> {
4121        let clause = self.find(node, "ExportClause");
4122        if clause != NONE {
4123            return self.unsupported(clause);
4124        }
4125        // `FilterClauseContents <- 'WHERE'? Expression`, so the word is optional and the predicate
4126        // is the last thing under it either way. Whether the call is allowed to carry one at all is
4127        // the binder's question, because it is a question about what the name resolves to.
4128        let clause = self.find(node, "FilterClause");
4129        let written =
4130            if clause == NONE { NONE } else { self.descendant(clause, "FilterClauseContents") };
4131        let filter = if written == NONE {
4132            NONE
4133        } else {
4134            let predicate = self.kids(written).last().unwrap_or(NONE);
4135            self.expr(predicate)?
4136        };
4137        let over = self.find(node, "OverClause");
4138        let mut name = self.name_parts(self.first(node));
4139        // `FunctionExpressionArguments <- Parens(FunctionExpressionArgumentList)` and
4140        // `FunctionExpressionArgumentList <- DistinctOrAll? FunctionArgumentList? OrderByClause?
4141        // IgnoreOrRespectNulls?`, so a call with no arguments still has both wrappers.
4142        let list = self.first(self.nth(node, 1));
4143        // An `ORDER BY` written inside the brackets is the order the call reads its rows in, which
4144        // is a different thing from the `ORDER BY` in an `OVER` and is written in a different place.
4145        // On a call without an `OVER` it is kept beside the call, for the binder to decide whether
4146        // the aggregate it names cares about the order.
4147        let inside = self.find(list, "OrderByClause");
4148        let mut inner = if inside == NONE {
4149            Slice { start: 0, len: 0 }
4150        } else {
4151            // `ORDER BY ALL` names the call's own arguments rather than a list of keys, and what the
4152            // reference binary does with it in here is not the ordinary reading of the words, so it
4153            // is turned down rather than guessed at.
4154            let (items, all) = self.order_by(inside)?;
4155            if all {
4156                return self.unsupported(inside);
4157            }
4158            self.order_slice(items)
4159        };
4160        // Either word is a window modifier and nothing else carries one, so an ordinary call that
4161        // writes one is turned down here, in the sentence the pin turns it down with.
4162        let nulls = self.find(list, "IgnoreOrRespectNulls");
4163        if nulls != NONE && over == NONE {
4164            return Err(Error::parser(
4165                "RESPECT/IGNORE NULLS is not supported for non-window functions",
4166            ));
4167        }
4168        let ignore_nulls = nulls != NONE && self.name(self.first(nulls)) == "IgnoreNulls";
4169        let distinct = self.quantifier(self.find(list, "DistinctOrAll")) == Quantifier::Distinct;
4170        let mut args = Vec::new();
4171        let mut names = Vec::new();
4172        let mut first_named = NONE;
4173        let arguments = self.find(list, "FunctionArgumentList");
4174        if arguments != NONE {
4175            for kid in self.kids(arguments) {
4176                let (name, arg) = self.argument(kid)?;
4177                if name == NONE && !names.is_empty() {
4178                    return Err(Error::binder(format!(
4179                        "Positional argument '{}' cannot follow named arguments in function call.",
4180                        self.text(kid)
4181                    )));
4182                }
4183                if name != NONE {
4184                    if names.is_empty() {
4185                        first_named = kid;
4186                    }
4187                    names.push(name);
4188                }
4189                args.push(arg);
4190            }
4191        }
4192        // `struct_pack(a := 1)` is the one call whose names are part of its value, and it is the
4193        // same struct `{'a': 1}` is, so it becomes that. `struct_pack()` is the empty struct and a
4194        // call with any positional argument stays a call, for the binder to turn down in the pin's
4195        // words. `struct_insert(s, b := 2)` and `struct_update` take the named arguments as the
4196        // fields to add or replace, so those are gathered into one struct handed over as the last
4197        // argument. A name on any other call is a parameter the binder does not have yet.
4198        let called = if name.len == 1 {
4199            self.ast.name(name).last().map(str::to_ascii_lowercase).unwrap_or_default()
4200        } else {
4201            String::new()
4202        };
4203        let within = self.find(node, "WithinGroupClause");
4204        if within != NONE {
4205            if over != NONE {
4206                return self.unsupported(within);
4207            }
4208            inner = self.within_group(within, &called, inside, args.len())?;
4209            if called.starts_with("percentile_") {
4210                name = self.function_name(&called.replace("percentile_", "quantile_"));
4211            }
4212        }
4213        let packs = called == "struct_pack";
4214        if packs && over == NONE && names.len() == args.len() {
4215            let names = self.part_slice(names);
4216            let values = self.expr_slice(args);
4217            return Ok(self.push(Expr::Struct { names, values }));
4218        }
4219        let merges = matches!(called.as_str(), "struct_insert" | "struct_update");
4220        let rewritten = packs || merges || called == "unnest" || called == "ifnull";
4221        if inside != NONE && over == NONE && rewritten {
4222            return self.unsupported(inside);
4223        }
4224        if merges && over == NONE && !names.is_empty() && names.len() + 1 == args.len() {
4225            let names = self.part_slice(names);
4226            let values = self.expr_slice(args.split_off(1));
4227            args.push(self.push(Expr::Struct { names, values }));
4228        } else if called == "unnest" && over == NONE && !names.is_empty() {
4229            // `unnest(l, recursive := true)` keeps its options beside the call, where the binder
4230            // looks for them, and the call itself is the positional arguments alone.
4231            let values = args.split_off(args.len() - names.len());
4232            let named: Vec<Target> =
4233                names.into_iter().zip(values).map(|(alias, expr)| Target { expr, alias }).collect();
4234            let named = self.target_slice(named);
4235            let args = self.expr_slice(args);
4236            let call = self.push(Expr::Function { name, args, distinct, filter });
4237            self.ast.named_args.push((call, named));
4238            return Ok(call);
4239        } else if !names.is_empty() && (!packs || names.len() == args.len()) {
4240            return self.unsupported(first_named);
4241        }
4242        // A call with an `OVER` on it is a window call and none of the rewrites below apply to it.
4243        // The reference binary agrees on the one case where that is visible: `ifnull(1) OVER ()`
4244        // keeps its name and its one argument and is turned down for not naming an aggregate,
4245        // where the same call without the `OVER` is a rewrite and an arity error.
4246        if over != NONE {
4247            let args = self.expr_slice(args);
4248            let spec = self.over(over)?;
4249            return Ok(self.push(Expr::Window {
4250                name,
4251                args,
4252                distinct,
4253                filter,
4254                ignore_nulls,
4255                order: inner,
4256                spec,
4257            }));
4258        }
4259        // `IFNULL` is an ordinary call in the grammar and is not one by the time DuckDB's parser is
4260        // done with it: `ifnull(NULL, 3)` comes back named `COALESCE(NULL, 3)` there, and so does
4261        // `main.ifnull(NULL, 3)`, so the qualifier goes with the rewrite. The count is checked here
4262        // because that is where upstream checks it, with the sentence below rather than the binder's
4263        // arity error, and it is checked before the two arguments are looked at.
4264        if self.ast.name(name).last().is_some_and(|part| part.eq_ignore_ascii_case("ifnull")) {
4265            if args.len() != 2 {
4266                return Err(Error::parser("Wrong number of arguments to IFNULL."));
4267            }
4268            let args = self.expr_slice(args);
4269            let name = self.function_name("coalesce");
4270            return Ok(self.push(Expr::Function { name, args, distinct, filter }));
4271        }
4272        let args = self.expr_slice(args);
4273        let call = self.push(Expr::Function { name, args, distinct, filter });
4274        if inner.len > 0 {
4275            self.ast.aggregate_orders.push((call, inner));
4276        }
4277        Ok(call)
4278    }
4279
4280    /// `WithinGroupClause <- 'WITHIN' 'GROUP' Parens(OrderByClause)`.
4281    ///
4282    /// The pin takes the clause on three names and writes it as the order of the call, so
4283    /// `percentile_cont(0.5) WITHIN GROUP (ORDER BY x)` is `quantile_cont(0.5 ORDER BY x)` and the
4284    /// binder reads the value from the key. The checks and their words are the pin's parser's.
4285    fn within_group(
4286        &mut self,
4287        node: u32,
4288        called: &str,
4289        inside: u32,
4290        written: usize,
4291    ) -> Result<Slice> {
4292        let wanted = match called {
4293            "percentile_cont" | "percentile_disc" => 1,
4294            "mode" => 0,
4295            _ => return Err(Error::parser(format!("Unknown ordered aggregate \"{called}\"."))),
4296        };
4297        if inside != NONE {
4298            return Err(Error::parser("Cannot use multiple ORDER BY statements with WITHIN GROUP"));
4299        }
4300        let clause = self.find(node, "OrderByClause");
4301        let (items, all) = self.order_by(clause)?;
4302        if all {
4303            return self.unsupported(clause);
4304        }
4305        if items.len() != 1 {
4306            return Err(Error::parser("Cannot use multiple ORDER BY clauses with WITHIN GROUP"));
4307        }
4308        if written != wanted {
4309            return Err(Error::parser(format!(
4310                "Wrong number of arguments for {}",
4311                called.to_ascii_uppercase()
4312            )));
4313        }
4314        Ok(self.order_slice(items))
4315    }
4316
4317    // Windows.
4318
4319    /// `WindowClause <- 'WINDOW' List(WindowDefinition)` and
4320    /// `WindowDefinition <- Identifier 'AS' WindowFrameDefinition`.
4321    ///
4322    /// The definitions are read in the order they were written and each one can see the ones before
4323    /// it, so `WINDOW w AS (ORDER BY i), v AS (w)` defines two windows that order the same way.
4324    fn window_clause(&mut self, node: u32) -> Result<()> {
4325        for kid in self.kids(node) {
4326            if self.name(kid) != "WindowDefinition" {
4327                continue;
4328            }
4329            let name = self.identifier(self.first(kid));
4330            let definition = self.find(kid, "WindowFrameDefinition");
4331            if definition == NONE {
4332                return self.unsupported(kid);
4333            }
4334            let (spec, framed) = self.window_definition(definition)?;
4335            let spec = self.push_window(spec);
4336            self.named_windows.push((name, spec, framed));
4337        }
4338        Ok(())
4339    }
4340
4341    /// `OverClause <- 'OVER' WindowFrame` and
4342    /// `WindowFrame <- ParensIdentifier / WindowFrameDefinition / IdentifierWindowFrame`.
4343    ///
4344    /// The first and the third spelling are a bare reference, written `OVER (w)` and `OVER w`, and
4345    /// both resolve to the window that name was given. A reference is resolved here rather than
4346    /// carried, because that is where the reference binary resolves it: a name nobody defined is a
4347    /// `Parser Error` there, and a view written with one comes back out of the catalog with the
4348    /// definition written in its place.
4349    fn over(&mut self, node: u32) -> Result<WindowRef> {
4350        let mut frame = self.first(node);
4351        if self.name(frame) == "WindowFrame" {
4352            frame = self.first(frame);
4353        }
4354        match self.name(frame) {
4355            "ParensIdentifier" | "IdentifierWindowFrame" => {
4356                let name = self.identifier(self.first(frame));
4357                let (spec, _) = self.named_window(name)?;
4358                Ok(spec)
4359            }
4360            "WindowFrameDefinition" => {
4361                let (spec, _) = self.window_definition(frame)?;
4362                Ok(self.push_window(spec))
4363            }
4364            _ => self.unsupported(frame),
4365        }
4366    }
4367
4368    /// The window a name stands for, and whether its definition wrote a frame clause.
4369    fn named_window(&self, name: StrRef) -> Result<(WindowRef, bool)> {
4370        let written = self.ast.string(name);
4371        let found = self
4372            .named_windows
4373            .iter()
4374            .rev()
4375            .find(|&&(defined, _, _)| self.ast.string(defined).eq_ignore_ascii_case(written));
4376        match found {
4377            Some(&(_, spec, framed)) => Ok((spec, framed)),
4378            // The doubled quotes are upstream's and not a slip here. It writes the name with the
4379            // quoting a printed identifier gets and then writes quotes around that as well, so a
4380            // window called `w` is reported as `""w""`.
4381            None => Err(Error::parser(format!("window \"\"{written}\"\" does not exist"))),
4382        }
4383    }
4384
4385    /// `WindowFrameDefinition <- WindowFrameNameContentsParens / WindowFrameContentsParens`,
4386    /// `WindowFrameNameContents <- BaseWindowName? WindowFrameContents` and
4387    /// `WindowFrameContents <- WindowPartition? OrderByClause? FrameClause?`.
4388    ///
4389    /// Returns the window and whether a frame clause was written, which the caller needs because a
4390    /// definition that wrote one cannot be used as the base of another.
4391    fn window_definition(&mut self, node: u32) -> Result<(WindowSpec, bool)> {
4392        let held = self.first(self.first(node));
4393        let (base, contents) = match self.name(held) {
4394            "WindowFrameNameContents" => {
4395                (self.find(held, "BaseWindowName"), self.find(held, "WindowFrameContents"))
4396            }
4397            "WindowFrameContents" => (NONE, held),
4398            _ => return self.unsupported(held),
4399        };
4400        if contents == NONE {
4401            return self.unsupported(node);
4402        }
4403        let partition = self.find(contents, "WindowPartition");
4404        let order = self.find(contents, "OrderByClause");
4405        let frame = self.find(contents, "FrameClause");
4406        let mut spec = WindowSpec::empty();
4407        if base != NONE {
4408            let name = self.identifier(self.first(base));
4409            let written = self.ast.string(name).to_string();
4410            let (found, framed) = self.named_window(name)?;
4411            // The three refusals are upstream's, in its words. What they have in common is that a
4412            // base window is copied and not merged, so anything the copy would have to combine with
4413            // something the base already said is turned down rather than guessed at.
4414            if framed {
4415                return Err(Error::parser(format!(
4416                    "cannot copy window \"{written}\" because it has a frame clause"
4417                )));
4418            }
4419            spec = self.ast.window(found);
4420            if partition != NONE && !spec.partition.is_empty() {
4421                return Err(Error::parser(format!(
4422                    "Cannot override PARTITION BY clause of window \"{written}\""
4423                )));
4424            }
4425            if order != NONE && !spec.order.is_empty() {
4426                return Err(Error::parser(format!(
4427                    "Cannot override ORDER BY clause of window \"{written}\""
4428                )));
4429            }
4430        }
4431        if partition != NONE {
4432            let mut items = Vec::new();
4433            for kid in self.kids(partition) {
4434                items.push(self.expr(kid)?);
4435            }
4436            spec.partition = self.expr_slice(items);
4437        }
4438        if order != NONE {
4439            let (items, all) = self.order_by(order)?;
4440            if all {
4441                return self.unsupported(order);
4442            }
4443            spec.order = self.order_slice(items);
4444        }
4445        if frame != NONE {
4446            self.frame_clause(&mut spec, frame)?;
4447        }
4448        Ok((spec, frame != NONE))
4449    }
4450
4451    /// `FrameClause <- Framing FrameExtent WindowExcludeClause?`.
4452    ///
4453    /// One normalisation happens here and it is the reference binary's. A frame that runs from the
4454    /// first row of the partition to the last says the same thing however it is measured, so
4455    /// `RANGE` and `GROUPS` become `ROWS` when both ends are unbounded. It matters because the
4456    /// printed form of a window is the column name a target with no alias gets, and upstream prints
4457    /// `ROWS` for all three spellings.
4458    fn frame_clause(&mut self, spec: &mut WindowSpec, node: u32) -> Result<()> {
4459        let framing = self.first(self.find(node, "Framing"));
4460        spec.unit = match self.name(framing) {
4461            "RowsFraming" => WindowUnit::Rows,
4462            "RangeFraming" => WindowUnit::Range,
4463            "GroupsFraming" => WindowUnit::Groups,
4464            _ => return self.unsupported(framing),
4465        };
4466        let extent = self.first(self.find(node, "FrameExtent"));
4467        match self.name(extent) {
4468            // `SingleFrameExtent <- FrameBound`, which names the start and leaves the end at the
4469            // current row.
4470            "SingleFrameExtent" => {
4471                spec.start = self.frame_bound(self.first(extent))?;
4472                spec.end = WindowBound::CurrentRow;
4473            }
4474            // `BetweenFrameExtent <- 'BETWEEN' FrameBound 'AND' FrameBound`.
4475            "BetweenFrameExtent" => {
4476                spec.start = self.frame_bound(self.first(extent))?;
4477                spec.end = self.frame_bound(self.nth(extent, 1))?;
4478            }
4479            _ => return self.unsupported(extent),
4480        }
4481        let exclude = self.find(node, "WindowExcludeClause");
4482        if exclude != NONE {
4483            let element = self.first(self.first(exclude));
4484            spec.exclude = match self.name(element) {
4485                "ExcludeCurrentRow" => WindowExclude::CurrentRow,
4486                "ExcludeGroup" => WindowExclude::Group,
4487                "ExcludeTies" => WindowExclude::Ties,
4488                "ExcludeNoOthers" => WindowExclude::NoOthers,
4489                _ => return self.unsupported(element),
4490            };
4491        }
4492        if spec.start == WindowBound::UnboundedPreceding
4493            && spec.end == WindowBound::UnboundedFollowing
4494        {
4495            spec.unit = WindowUnit::Rows;
4496        }
4497        Ok(())
4498    }
4499
4500    /// `FrameBound <- FrameUnbounded / FrameCurrentRow / FrameExpression`.
4501    fn frame_bound(&mut self, node: u32) -> Result<WindowBound> {
4502        let inner = if self.name(node) == "FrameBound" { self.first(node) } else { node };
4503        match self.name(inner) {
4504            "FrameCurrentRow" => Ok(WindowBound::CurrentRow),
4505            // `FrameUnbounded <- 'UNBOUNDED' PrecedingOrFollowing`.
4506            "FrameUnbounded" => {
4507                if self.preceding(self.first(inner)) {
4508                    Ok(WindowBound::UnboundedPreceding)
4509                } else {
4510                    Ok(WindowBound::UnboundedFollowing)
4511                }
4512            }
4513            // `FrameExpression <- Expression PrecedingOrFollowing`.
4514            "FrameExpression" => {
4515                let offset = self.expr(self.first(inner))?;
4516                if self.preceding(self.nth(inner, 1)) {
4517                    Ok(WindowBound::Preceding(offset))
4518                } else {
4519                    Ok(WindowBound::Following(offset))
4520                }
4521            }
4522            _ => self.unsupported(inner),
4523        }
4524    }
4525
4526    /// `PrecedingOrFollowing <- PrecedingFrame / FollowingFrame`, which of the two it was.
4527    fn preceding(&self, node: u32) -> bool {
4528        self.name(self.first(node)) == "PrecedingFrame"
4529    }
4530
4531    /// `CoalesceExpression <- 'COALESCE' Parens(List(Expression))`.
4532    ///
4533    /// A keyword is not a child and the two wrappers are transparent, so the children are the
4534    /// arguments. One of them is enough for the grammar and none of them is a syntax error, which is
4535    /// why there is no count checked here.
4536    ///
4537    /// The call is written with the canonical name rather than the one the query used, since there is
4538    /// nothing else to keep: the keyword is the name. Upstream prints the column in capitals whatever
4539    /// case was written, because `COALESCE` is an operator there and not a function name that its
4540    /// parser folded, and the binder is where that is decided here.
4541    fn coalesce(&mut self, node: u32) -> Result<ExprRef> {
4542        let mut args = Vec::new();
4543        for kid in self.kids(node) {
4544            args.push(self.expr(kid)?);
4545        }
4546        let args = self.expr_slice(args);
4547        let name = self.function_name("coalesce");
4548        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4549    }
4550
4551    /// `LambdaExpression <- 'LAMBDA' List(ColIdOrString) ':' Expression`.
4552    ///
4553    /// Every child but the last is a parameter, since the list and the keyword leave no node of
4554    /// their own behind, and the last one is the body. A parameter is a name and is read the way a
4555    /// column name is, so `lambda "x": x` is the parameter `x` and `lambda X: x` keeps its case for
4556    /// the column heading and still answers to `x`, which the binder matches without case.
4557    fn lambda(&mut self, node: u32) -> Result<ExprRef> {
4558        let kids: Vec<u32> = self.kids(node).collect();
4559        let Some((&body, params)) = kids.split_last() else {
4560            return self.unsupported(node);
4561        };
4562        if params.is_empty() {
4563            return self.unsupported(node);
4564        }
4565        let mut names = Vec::with_capacity(params.len());
4566        for &param in params {
4567            names.push(self.identifier(param));
4568        }
4569        let params = self.part_slice(names);
4570        let body = self.expr(body)?;
4571        Ok(self.push(Expr::Lambda { params, body }))
4572    }
4573
4574    /// `NullIfExpression <- 'NULLIF' Parens(NullIfArguments)` and
4575    /// `NullIfArguments <- Expression ',' Expression`.
4576    ///
4577    /// Exactly two arguments, because the rule says so: `nullif(1)` and `nullif(1, 2, 3)` are syntax
4578    /// errors upstream and are syntax errors here for the same reason, so there is no arity to check
4579    /// after the parse.
4580    ///
4581    /// It stays a function called `nullif` rather than becoming the `CASE` upstream's macro expands
4582    /// to, since the column it produces is named after the call and not after the expansion.
4583    /// `TryExpression <- 'TRY' Parens(Expression)`, kept as a call to `try` that the binder and the
4584    /// executor know is not a function. The pin prints it as `TRY(...)` and so does this.
4585    fn try_expression(&mut self, node: u32) -> Result<ExprRef> {
4586        let kids: Vec<u32> = self.kids(node).collect();
4587        let [only] = kids[..] else {
4588            return self.unsupported(node);
4589        };
4590        let inner = self.expr(only)?;
4591        let args = self.expr_slice(vec![inner]);
4592        let name = self.function_name("try");
4593        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4594    }
4595
4596    fn null_if(&mut self, node: u32) -> Result<ExprRef> {
4597        let arguments = self.find(node, "NullIfArguments");
4598        if arguments == NONE {
4599            return self.unsupported(node);
4600        }
4601        let mut args = Vec::new();
4602        for kid in self.kids(arguments) {
4603            args.push(self.expr(kid)?);
4604        }
4605        let args = self.expr_slice(args);
4606        let name = self.function_name("nullif");
4607        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4608    }
4609
4610    /// `SubstringExpression <- 'SUBSTRING' Parens(SubstringArguments)` and
4611    /// `SubstringArguments <- SubstringParameters / SubstringExpressionList`.
4612    ///
4613    /// Both spellings are the same call and DuckDB's parser writes both of them back out as one:
4614    /// `substring(s FROM a FOR b)` comes back as the column `"substring"(s, a, b)` there, and so does
4615    /// `substring(s, a, b)`. The `FOR` on its own is the one worth pointing at, since it is not the
4616    /// two argument call it looks like. `substring('abcdef' FOR 3)` is `"substring"('abcdef', 1, 3)`
4617    /// upstream, so the start is filled in with a literal 1 here rather than left out.
4618    fn substring(&mut self, node: u32) -> Result<ExprRef> {
4619        let shape = self.first(self.first(node));
4620        let mut args = Vec::new();
4621        match self.name(shape) {
4622            "SubstringExpressionList" => {
4623                for kid in self.kids(shape) {
4624                    args.push(self.expr(kid)?);
4625                }
4626            }
4627            "SubstringParameters" => {
4628                args.push(self.expr(self.first(shape))?);
4629                // `SubstringFromFor <- SubstringFromOptionalFor / SubstringFor`, and both of those
4630                // hold the bounds as `FromExpression` and `ForExpression`, so finding them by name
4631                // reads either shape and neither one has to be told apart from the other.
4632                let bounds = self.first(self.nth(shape, 1));
4633                let from = self.find(bounds, "FromExpression");
4634                let start =
4635                    if from == NONE { self.number("1") } else { self.expr(self.first(from))? };
4636                args.push(start);
4637                let count = self.find(bounds, "ForExpression");
4638                if count != NONE {
4639                    args.push(self.expr(self.first(count))?);
4640                }
4641            }
4642            _ => return self.unsupported(shape),
4643        }
4644        let args = self.expr_slice(args);
4645        let name = self.function_name("substring");
4646        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4647    }
4648
4649    /// `PositionExpression <- 'POSITION' Parens(PositionArguments)` and
4650    /// `PositionArguments <- OtherOperatorExpression 'IN' Expression`.
4651    ///
4652    /// The two arguments swap. `position('c' IN 'abcdef')` is `"position"('abcdef', 'c')` upstream,
4653    /// which is the same order `strpos` and `instr` are written in, so the haystack comes first in
4654    /// the call and second in the query.
4655    fn position(&mut self, node: u32) -> Result<ExprRef> {
4656        let arguments = self.first(node);
4657        if self.count(arguments) != 2 {
4658            return self.unsupported(arguments);
4659        }
4660        let needle = self.expr(self.first(arguments))?;
4661        let haystack = self.expr(self.nth(arguments, 1))?;
4662        let args = self.expr_slice(vec![haystack, needle]);
4663        let name = self.function_name("position");
4664        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4665    }
4666
4667    /// `TrimExpression <- 'TRIM' Parens(TrimArguments)` and
4668    /// `TrimArguments <- TrimDirection? TrimSource? List(Expression)`.
4669    ///
4670    /// The direction is not an argument, it is the function: `LEADING` is `ltrim` upstream and
4671    /// `TRAILING` is `rtrim`, while `BOTH` and the bare form are both `trim`. The characters to strip
4672    /// are the last argument whichever way they were written, so `trim(BOTH 'x' FROM 'xxaxx')` and
4673    /// `trim('xxaxx', 'x')` are the same call, which is why the source goes on the end of the list
4674    /// rather than in front of it.
4675    fn trim(&mut self, node: u32) -> Result<ExprRef> {
4676        let arguments = self.first(node);
4677        let direction = self.find(arguments, "TrimDirection");
4678        let name = match direction {
4679            NONE => "trim",
4680            held => match self.name(self.first(held)) {
4681                "TrimLeading" => "ltrim",
4682                "TrimTrailing" => "rtrim",
4683                _ => "trim",
4684            },
4685        };
4686        let mut args = Vec::new();
4687        for kid in self.kids(arguments) {
4688            if matches!(self.name(kid), "TrimDirection" | "TrimSource") {
4689                continue;
4690            }
4691            args.push(self.expr(kid)?);
4692        }
4693        // `TrimSource <- Expression? 'FROM'`, so `trim(LEADING FROM s)` has the node with nothing
4694        // under it and there is no second argument to add.
4695        let source = self.find(arguments, "TrimSource");
4696        if source != NONE && self.count(source) == 1 {
4697            args.push(self.expr(self.first(source))?);
4698        }
4699        let args = self.expr_slice(args);
4700        let name = self.function_name(name);
4701        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4702    }
4703
4704    /// `OverlayExpression <- 'OVERLAY' Parens(OverlayArguments)` and
4705    /// `OverlayArguments <- OverlayParameters / OverlayExpressionList`, where
4706    /// `OverlayParameters <- Expression 'PLACING' Expression FromExpression ForExpression?`.
4707    ///
4708    /// The arguments are already in the order the call takes them, so the keyword spelling is the
4709    /// list spelling with `PLACING`, `FROM` and `FOR` where the commas would be:
4710    /// `overlay('abcdef' PLACING 'X' FROM 2 FOR 1)` is `"overlay"('abcdef', 'X', 2, 1)` upstream.
4711    fn overlay(&mut self, node: u32) -> Result<ExprRef> {
4712        let shape = self.first(self.first(node));
4713        if !matches!(self.name(shape), "OverlayParameters" | "OverlayExpressionList") {
4714            return self.unsupported(shape);
4715        }
4716        let mut args = Vec::new();
4717        for kid in self.kids(shape) {
4718            let kid = match self.name(kid) {
4719                "FromExpression" | "ForExpression" => self.first(kid),
4720                _ => kid,
4721            };
4722            args.push(self.expr(kid)?);
4723        }
4724        let args = self.expr_slice(args);
4725        let name = self.function_name("overlay");
4726        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4727    }
4728
4729    /// A number literal the query did not write, for the one place a lowering has to supply one.
4730    fn number(&mut self, text: &str) -> ExprRef {
4731        let text = self.intern(text);
4732        self.push(Expr::Literal { kind: LiteralKind::Number, text })
4733    }
4734
4735    /// `ExtractExpression <- 'EXTRACT' Parens(ExtractArguments)` and
4736    /// `ExtractArguments <- ExtractArgument 'FROM' Expression`.
4737    ///
4738    /// `EXTRACT` is not a function in the grammar because its argument list is not an argument
4739    /// list, and it is a function everywhere after here because DuckDB's parser does the same
4740    /// rewrite: `EXTRACT(minute FROM t)` is `date_part('minute', t)` and there is no separate
4741    /// implementation of one of them. The part is a keyword, an identifier or a string in the
4742    /// grammar, and all three become the string, which is why this is a rewrite and not a node.
4743    fn extract(&mut self, node: u32) -> Result<ExprRef> {
4744        let arguments = self.find(node, "ExtractArguments");
4745        if arguments == NONE {
4746            return self.unsupported(node);
4747        }
4748        let argument = self.first(self.first(arguments));
4749        let part = match self.name(argument) {
4750            "ExtractStringArgument" => self.string_value(argument)?,
4751            // A keyword, which is one of the thirteen the grammar names and is written back as the
4752            // one spelling that keyword has. `EXTRACT(seconds FROM t)` and `EXTRACT(SECOND FROM t)`
4753            // are both `date_part('SECOND', t)`, which was measured, and it shows up in the column
4754            // name as well as in the deparse, since an unaliased column is named after the call.
4755            "ExtractDatePartArgument" => date_part(self.text(argument)),
4756            // An identifier, taken as written. Which specifier names are legal is not a question
4757            // about syntax, so the answer to it lives with the function.
4758            "ExtractIdentifierArgument" => self.text(argument).to_string(),
4759            _ => return self.unsupported(argument),
4760        };
4761        let text = self.intern(&part);
4762        let part = self.push(Expr::Literal { kind: LiteralKind::String, text });
4763        let operand = self.expr(self.nth(arguments, 1))?;
4764        let name = self.function_name("date_part");
4765        let args = self.expr_slice(vec![part, operand]);
4766        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4767    }
4768
4769    /// `FunctionArgument <- NamedFunctionArgument / PositionalFunctionArgument`, with the name the
4770    /// argument was given or `NONE` for a positional one.
4771    fn argument(&mut self, node: u32) -> Result<(u32, ExprRef)> {
4772        let inner = self.first(node);
4773        match self.name(inner) {
4774            "PositionalFunctionArgument" => Ok((NONE, self.expr(self.first(inner))?)),
4775            "NamedFunctionArgument" => {
4776                let named = self.first(inner);
4777                if self.count(named) != 3 {
4778                    return self.unsupported(named);
4779                }
4780                let name = self.identifier(self.first(named));
4781                Ok((name, self.expr(self.nth(named, 2))?))
4782            }
4783            _ => self.unsupported(inner),
4784        }
4785    }
4786
4787    /// One argument of a table function, which is the same rule plus the names.
4788    ///
4789    /// `NamedParameter <- TypeFuncName Type? NamedParameterAssignment Expression` and
4790    /// `NamedParameterAssignment <- ':=' / '=>'`, so those two spellings are what the grammar has.
4791    /// The binary accepts a third, `name = value`, which the grammar has no rule for because it
4792    /// parses as an equality and is picked apart afterwards. That is what happens here too: a
4793    /// positional argument that is a comparison between a bare name and something else is a named
4794    /// parameter, which is the reading upstream's own transformer gives it. `read_parquet(f,
4795    /// binary_as_string=True)` is the query that matters and it is the spelling the ClickBench
4796    /// entry uses.
4797    ///
4798    /// The name is not resolved here and neither is the value. Which parameters a function takes
4799    /// is the binder's question, and so is whether `binary_as_string=True` means anything to the
4800    /// function it was written on.
4801    fn table_argument(&mut self, node: u32) -> Result<Target> {
4802        let inner = self.first(node);
4803        if self.name(inner) == "NamedFunctionArgument" {
4804            let named = self.first(inner);
4805            if self.count(named) != 3 {
4806                // The optional `Type` between the name and the assignment, which is a macro
4807                // parameter's declaration and not a call.
4808                return self.unsupported(named);
4809            }
4810            let alias = self.identifier(self.first(named));
4811            let expr = self.expr(self.nth(named, 2))?;
4812            return Ok(Target { expr, alias });
4813        }
4814        let expr = self.expr(self.first(inner))?;
4815        if let Expr::Binary { op: BinaryOp::Eq, left, right } = self.ast.expr(expr)
4816            && let Expr::Column { name } = self.ast.expr(left)
4817            && name.len == 1
4818        {
4819            let alias = self.ast.parts[name.start as usize];
4820            return Ok(Target { expr: right, alias });
4821        }
4822        Ok(Target { expr, alias: NONE })
4823    }
4824
4825    /// `CastExpression <- CastOrTryCast Parens(CastArguments)`.
4826    fn cast(&mut self, node: u32) -> Result<ExprRef> {
4827        let try_cast = self.name(self.first(self.first(node))) == "TryCastKeyword";
4828        // `CastArguments <- Expression 'AS' Type`.
4829        let arguments = self.nth(node, 1);
4830        let operand = self.expr(self.first(arguments))?;
4831        let text = self.text(self.nth(arguments, 1)).to_string();
4832        let ty = self.intern(&text);
4833        Ok(self.push(Expr::Cast { operand, ty, try_cast }))
4834    }
4835
4836    /// `TypeLiteral <- Type StringLiteral`, which is the cast written the other way round.
4837    ///
4838    /// `DATE '1995-09-01'` and `CAST('1995-09-01' AS DATE)` are the same expression upstream, and
4839    /// the proof is the column name: the pinned binary answers both of them in a column called
4840    /// `CAST('1995-09-01' AS DATE)`. So this is the cast node and nothing else, which means every
4841    /// type the cast already takes is a typed literal for free and the two can never drift.
4842    ///
4843    /// The string is the literal the grammar matched rather than any expression, so there is no
4844    /// constant folding question here. `DATE x` does not parse in the first place.
4845    fn typed_literal(&mut self, node: u32) -> Result<ExprRef> {
4846        let text = self.text(self.first(node)).to_string();
4847        let ty = self.intern(&text);
4848        let operand = self.expr(self.nth(node, 1))?;
4849        Ok(self.push(Expr::Cast { operand, ty, try_cast: false }))
4850    }
4851
4852    /// `IntervalLiteral <- 'INTERVAL' IntervalParameter Interval?`, which is a function call.
4853    ///
4854    /// There is no interval node and there does not need to be one, because DuckDB's own
4855    /// transformer rewrites the literal into a call and the column name says so: `INTERVAL 1 DAY`
4856    /// comes back from the pinned binary in a column called
4857    /// `to_days(CAST(trunc(CAST(1 AS DOUBLE)) AS INTEGER))`. So the literal and a handwritten
4858    /// `to_days(1)` are the same expression from here on and the two cannot drift apart.
4859    ///
4860    /// Every unit goes through a DOUBLE on the way in, which is what makes `INTERVAL 1.5 DAY` one
4861    /// day rather than a day and a half: the truncation is in the rewrite and not in the function.
4862    /// The two units that can carry a fraction skip the truncation and stay a DOUBLE all the way,
4863    /// so `INTERVAL 2.7 SECOND` really is two and seven tenths of a second.
4864    ///
4865    /// A literal with no unit is the cast written the other way round, so `INTERVAL '1 day'` is
4866    /// `CAST('1 day' AS INTERVAL)`. That arm also catches a word the grammar does not read as a
4867    /// unit, since `INTERVAL 1 d` parses as this rule with no `Interval` child and a column alias
4868    /// after it, which is why upstream answers it with a cast error about an INTEGER.
4869    fn interval_literal(&mut self, node: u32) -> Result<ExprRef> {
4870        let parameter = self.find(node, "IntervalParameter");
4871        if parameter == NONE {
4872            return self.unsupported(node);
4873        }
4874        let operand = self.expr(self.first(parameter))?;
4875        let unit = self.find(node, "Interval");
4876        if unit == NONE {
4877            let ty = self.intern("INTERVAL");
4878            return Ok(self.push(Expr::Cast { operand, ty, try_cast: false }));
4879        }
4880        let spelling = self.name(self.first(unit));
4881        // The seven range forms parse and then refuse, in upstream's words, with the unit names
4882        // spelled the canonical way rather than the way they were written: `interval 1 days to
4883        // hours` is `DAY TO HOUR` there as well.
4884        if spelling == "IntervalToInterval" {
4885            let pair = self.name(self.first(self.first(unit)));
4886            return Err(Error::parser(format!("{} is not supported", worded(pair))));
4887        }
4888        let Some(&(_, function, width)) = UNITS.iter().find(|(rule, _, _)| *rule == spelling)
4889        else {
4890            return self.unsupported(unit);
4891        };
4892        let double = self.intern("DOUBLE");
4893        let mut count = self.push(Expr::Cast { operand, ty: double, try_cast: false });
4894        if let Some(width) = width {
4895            let name = self.function_name("trunc");
4896            let args = self.expr_slice(vec![count]);
4897            let whole = self.push(Expr::Function { name, args, distinct: false, filter: NONE });
4898            let ty = self.intern(width);
4899            count = self.push(Expr::Cast { operand: whole, ty, try_cast: false });
4900        }
4901        let name = self.function_name(function);
4902        let args = self.expr_slice(vec![count]);
4903        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
4904    }
4905
4906    /// `CaseExpression <- 'CASE' Expression? CaseWhenThen+ CaseElse? 'END'`.
4907    fn case(&mut self, node: u32) -> Result<ExprRef> {
4908        let mut operand = NONE;
4909        let mut arms = Vec::new();
4910        let mut otherwise = NONE;
4911        for kid in self.kids(node) {
4912            match self.name(kid) {
4913                // `CaseWhenThen <- 'WHEN' Expression 'THEN' Expression`.
4914                "CaseWhenThen" => {
4915                    let when = self.expr(self.first(kid))?;
4916                    let then = self.expr(self.nth(kid, 1))?;
4917                    arms.push(CaseArm { when, then });
4918                }
4919                // `CaseElse <- 'ELSE' Expression`.
4920                "CaseElse" => otherwise = self.expr(self.first(kid))?,
4921                // The bare `Expression` before the first `WHEN`, which makes it a simple case.
4922                _ => operand = self.expr(kid)?,
4923            }
4924        }
4925        let start = self.ast.case_arms.len() as u32;
4926        self.ast.case_arms.extend(arms);
4927        let arms = Slice { start, len: self.ast.case_arms.len() as u32 - start };
4928        Ok(self.push(Expr::Case { operand, arms, otherwise }))
4929    }
4930
4931    /// `ParenthesisExpression <- Parens(List(Expression)?)`, which is a row value.
4932    ///
4933    /// One item is not a row. `(a)` is `a` in every dialect and reading it as a one column row
4934    /// would change what `(a) = (b)` means.
4935    fn row(&mut self, node: u32) -> Result<ExprRef> {
4936        let mut items = Vec::new();
4937        for kid in self.kids(node) {
4938            items.push(self.expr(kid)?);
4939        }
4940        if items.len() == 1 {
4941            return Ok(items[0]);
4942        }
4943        let items = self.expr_slice(items);
4944        Ok(self.push(Expr::Row { items }))
4945    }
4946
4947    /// `RowExpression <- 'ROW' Parens(List(Expression)?)`, which is a row whatever its length, so
4948    /// `row(1)` is a row of one where `(1)` is the number.
4949    fn row_expression(&mut self, node: u32) -> Result<ExprRef> {
4950        let mut items = Vec::new();
4951        for kid in self.kids(node) {
4952            items.push(self.expr(kid)?);
4953        }
4954        let items = self.expr_slice(items);
4955        Ok(self.push(Expr::Row { items }))
4956    }
4957
4958    /// `Parameter <- '?' Number / '?' / '$' Number / '$' ColLabel`, a prepared statement parameter.
4959    ///
4960    /// The identifier is what follows the marker, so `?1` and `$1` are both the parameter named 1,
4961    /// and a bare `?` takes the next number by where it was written. That is what DuckDB does, which
4962    /// is why `? + $2` prints as `$1 + $2`: the counting is its own and does not skip a number
4963    /// because a later parameter claimed it.
4964    fn parameter(&mut self, node: u32) -> Result<ExprRef> {
4965        let written = self.text(node).trim();
4966        let written = written.trim_start_matches(['?', '$']).trim();
4967        let name = if written.is_empty() {
4968            self.anonymous += 1;
4969            self.anonymous.to_string()
4970        } else {
4971            written.to_string()
4972        };
4973        let name = self.intern(&name);
4974        Ok(self.push(Expr::Parameter { name }))
4975    }
4976
4977    /// `BoundedListExpression <- '[' List(Expression)? ']'`, which is a LIST value.
4978    ///
4979    /// One item is a list of one here, unlike the parenthesised form, because the brackets are what
4980    /// say list and there is nothing else `[a]` could mean.
4981    fn list(&mut self, node: u32) -> Result<ExprRef> {
4982        let mut items = Vec::new();
4983        for kid in self.kids(node) {
4984            items.push(self.expr(kid)?);
4985        }
4986        let items = self.expr_slice(items);
4987        Ok(self.push(Expr::List { items }))
4988    }
4989
4990    /// `MapExpression <- 'MAP' MapStructExpression`, `MapStructExpression <- '{'
4991    /// List(MapStructField)? '}'` and `MapStructField <- Expression ':' Expression`.
4992    ///
4993    /// `MAP {1: 'a'}` is `map([1], ['a'])` on the pin, down to the column heading, so it becomes that
4994    /// call with the keys in one list and the values in the other.
4995    fn map(&mut self, node: u32) -> Result<ExprRef> {
4996        let mut keys = Vec::new();
4997        let mut values = Vec::new();
4998        let fields = self.find(node, "MapStructExpression");
4999        if fields != NONE {
5000            for field in self.kids(fields).collect::<Vec<_>>() {
5001                let kids: Vec<u32> = self.kids(field).collect();
5002                let [key, value] = kids[..] else {
5003                    return self.unsupported(field);
5004                };
5005                keys.push(self.expr(key)?);
5006                values.push(self.expr(value)?);
5007            }
5008        }
5009        let keys = self.expr_slice(keys);
5010        let keys = self.push(Expr::List { items: keys });
5011        let values = self.expr_slice(values);
5012        let values = self.push(Expr::List { items: values });
5013        let args = self.expr_slice(vec![keys, values]);
5014        let name = self.function_name("map");
5015        Ok(self.push(Expr::Function { name, args, distinct: false, filter: NONE }))
5016    }
5017
5018    /// `StructExpression <- '{' List(StructField)? '}'` and
5019    /// `StructField <- ColIdOrString ':' Expression`.
5020    ///
5021    /// A field name is read the way a column name is, so `{a: 1}`, `{"a": 1}` and `{'a': 1}` are
5022    /// the same struct, and a name written twice is left for the binder to refuse in the pin's words.
5023    fn structure(&mut self, node: u32) -> Result<ExprRef> {
5024        let mut names = Vec::new();
5025        let mut values = Vec::new();
5026        for field in self.kids(node).collect::<Vec<_>>() {
5027            let kids: Vec<u32> = self.kids(field).collect();
5028            let [name, value] = kids[..] else {
5029                return self.unsupported(field);
5030            };
5031            names.push(self.identifier(name));
5032            values.push(self.expr(value)?);
5033        }
5034        let names = self.part_slice(names);
5035        let values = self.expr_slice(values);
5036        Ok(self.push(Expr::Struct { names, values }))
5037    }
5038
5039    /// `SubqueryExpression <- SubqueryNot? SubqueryExists? SubqueryReference`.
5040    fn subquery(&mut self, node: u32) -> Result<ExprRef> {
5041        let negated = self.find(node, "SubqueryNot") != NONE;
5042        let exists = self.find(node, "SubqueryExists") != NONE;
5043        let reference = self.find(node, "SubqueryReference");
5044        let query = self.query(self.first(reference))?;
5045        Ok(if exists {
5046            self.push(Expr::Exists { query, negated })
5047        } else if negated {
5048            return self.unsupported(node);
5049        } else {
5050            self.push(Expr::Subquery { query, array: false })
5051        })
5052    }
5053
5054    /// The value of a string literal, with the quotes gone and the escapes resolved.
5055    ///
5056    /// A literal can be several tokens. `'a' 'b'` on two lines is one literal that is `ab`, which is
5057    /// the SQL standard's rule and DuckDB's, so the node is decoded token by token rather than by
5058    /// taking its text and stripping the outside.
5059    fn string_value(&self, node: u32) -> Result<String> {
5060        let span = self.tree.node(node);
5061        let mut value = String::new();
5062        for token in &self.tokens[span.start as usize..span.end as usize] {
5063            if token.kind == Kind::String {
5064                value.push_str(&string_token(token.text(self.query))?);
5065            }
5066        }
5067        Ok(value)
5068    }
5069
5070    /// The token that opens a string literal, which is the whole of it when it has a prefix.
5071    ///
5072    /// Only the first token is asked, because a prefixed literal is one token: `E'a' 'b'` is a
5073    /// syntax error upstream rather than a concatenation, so there is no second prefix to disagree
5074    /// with this one.
5075    fn first_string(&self, node: u32) -> &'a str {
5076        let span = self.tree.node(node);
5077        self.tokens[span.start as usize..span.end as usize]
5078            .iter()
5079            .find(|token| token.kind == Kind::String)
5080            .map_or("", |token| token.text(self.query))
5081    }
5082
5083    /// A string literal as an expression, which is the value plus what the prefix makes of it.
5084    ///
5085    /// `N'abc'` is a cast of the string to VARCHAR upstream and not a plain string, and the column
5086    /// name is the proof: the pinned binary answers it in a column called `CAST('abc' AS VARCHAR)`.
5087    /// So it is written here as the cast it is, and then there is nothing left to keep in step.
5088    ///
5089    /// `x'4142'` is not a string at all, it is a BLOB, so it is the one prefix that becomes a
5090    /// different kind of literal rather than a string with something done to it.
5091    fn string_literal(&mut self, node: u32) -> Result<ExprRef> {
5092        let token = self.first_string(node);
5093        let prefix = match token.as_bytes() {
5094            [prefix, b'\'', ..] => *prefix,
5095            _ => 0,
5096        };
5097        if matches!(prefix, b'X' | b'x')
5098            && let Some(body) = token.get(1..).and_then(quoted_body)
5099        {
5100            let text = blob_text(body.as_bytes())?;
5101            let text = self.intern(&text);
5102            return Ok(self.push(Expr::Literal { kind: LiteralKind::Blob, text }));
5103        }
5104        let value = self.string_value(node)?;
5105        let text = self.intern(&value);
5106        let literal = self.push(Expr::Literal { kind: LiteralKind::String, text });
5107        if matches!(prefix, b'N' | b'n') {
5108            let ty = self.intern("VARCHAR");
5109            return Ok(self.push(Expr::Cast { operand: literal, ty, try_cast: false }));
5110        }
5111        Ok(literal)
5112    }
5113}
5114
5115/// The options of a `COPY` as the `read_csv` parameters they become, each with its value.
5116type CopyOptions = Vec<(&'static str, ExprRef)>;
5117
5118/// The `read_csv` parameter a `COPY` option is, by the name it was written with in lower case.
5119///
5120/// `DELIMITER` and `NULL` are the `COPY` names for what `read_csv` calls `delim` and `nullstr`, and
5121/// DuckDB takes the `read_csv` names in a `COPY` too, so both are here.
5122fn copy_parameter(name: &str) -> Result<&'static str> {
5123    Ok(match name {
5124        "header" => "header",
5125        "delimiter" | "delim" | "sep" => "delim",
5126        "quote" => "quote",
5127        "escape" => "escape",
5128        "null" | "nullstr" => "nullstr",
5129        "all_varchar" | "allow_quoted_nulls" | "auto_detect" | "columns" | "comment"
5130        | "compression" | "dateformat" | "date_format" | "decimal_separator" | "encoding"
5131        | "force_not_null" | "force_quote" | "ignore_errors" | "max_line_size" | "names"
5132        | "new_line" | "null_padding" | "sample_size" | "skip" | "strict_mode"
5133        | "timestampformat" | "timestamp_format" | "types" | "dtypes" => {
5134            return Err(Error::not_implemented(format!(
5135                "COPY FROM with the option {name} is not supported yet"
5136            )));
5137        }
5138        _ => {
5139            return Err(Error::not_implemented(format!("Unrecognized option \"{name}\" for csv")));
5140        }
5141    })
5142}
5143
5144/// Each unit an interval literal can be written in, as the grammar rule that spells it, the
5145/// function it becomes, and the width the count is truncated to on the way there.
5146///
5147/// A width of `None` is the pair that keeps what is after the point. Those two stay a DOUBLE and
5148/// never see `trunc`, which is the whole of the difference between `INTERVAL 2.7 SECOND` being two
5149/// and seven tenths of a second and `INTERVAL 1.5 DAY` being one day. Every entry, both spellings
5150/// of every keyword and the width of each one was read off the pinned binary's column names.
5151const UNITS: &[(&str, &str, Option<&str>)] = &[
5152    ("YearKeyword", "to_years", Some("INTEGER")),
5153    ("MonthKeyword", "to_months", Some("INTEGER")),
5154    ("QuarterKeyword", "to_quarters", Some("INTEGER")),
5155    ("DecadeKeyword", "to_decades", Some("INTEGER")),
5156    ("CenturyKeyword", "to_centuries", Some("INTEGER")),
5157    ("MillenniumKeyword", "to_millennia", Some("INTEGER")),
5158    ("DayKeyword", "to_days", Some("INTEGER")),
5159    ("WeekKeyword", "to_weeks", Some("INTEGER")),
5160    ("HourKeyword", "to_hours", Some("BIGINT")),
5161    ("MinuteKeyword", "to_minutes", Some("BIGINT")),
5162    ("MicrosecondKeyword", "to_microseconds", Some("BIGINT")),
5163    ("SecondKeyword", "to_seconds", None),
5164    ("MillisecondKeyword", "to_milliseconds", None),
5165];
5166
5167/// The one spelling a date part keyword is written back as, which is not always the singular.
5168///
5169/// Both spellings of each of the thirteen keywords land on one name, and the name is upper case and
5170/// is plural for the two smallest parts and singular for the rest. That is not a rule, it is a list,
5171/// and it was read off the pinned binary a keyword at a time: `EXTRACT(milliseconds FROM t)` and
5172/// `EXTRACT(millisecond FROM t)` are both `date_part('MILLISECONDS', t)` while `EXTRACT(seconds FROM
5173/// t)` is `date_part('SECOND', t)`.
5174///
5175/// A word that is not a keyword never reaches here, because the grammar tells the two apart, and it
5176/// keeps whatever case it was written in. `EXTRACT(epoch FROM t)` stays lower case, measured.
5177fn date_part(written: &str) -> String {
5178    const PARTS: &[(&str, &str)] = &[
5179        ("YEAR", "YEAR"),
5180        ("YEARS", "YEAR"),
5181        ("MONTH", "MONTH"),
5182        ("MONTHS", "MONTH"),
5183        ("DAY", "DAY"),
5184        ("DAYS", "DAY"),
5185        ("HOUR", "HOUR"),
5186        ("HOURS", "HOUR"),
5187        ("MINUTE", "MINUTE"),
5188        ("MINUTES", "MINUTE"),
5189        ("SECOND", "SECOND"),
5190        ("SECONDS", "SECOND"),
5191        ("MILLISECOND", "MILLISECONDS"),
5192        ("MILLISECONDS", "MILLISECONDS"),
5193        ("MICROSECOND", "MICROSECONDS"),
5194        ("MICROSECONDS", "MICROSECONDS"),
5195        ("WEEK", "WEEK"),
5196        ("WEEKS", "WEEK"),
5197        ("QUARTER", "QUARTER"),
5198        ("QUARTERS", "QUARTER"),
5199        ("DECADE", "DECADE"),
5200        ("DECADES", "DECADE"),
5201        ("CENTURY", "CENTURY"),
5202        ("CENTURIES", "CENTURY"),
5203        ("MILLENNIUM", "MILLENNIUM"),
5204        ("MILLENNIA", "MILLENNIUM"),
5205    ];
5206    PARTS
5207        .iter()
5208        .find(|(spelling, _)| spelling.eq_ignore_ascii_case(written))
5209        .map_or_else(|| written.to_string(), |(_, name)| (*name).to_string())
5210}
5211
5212/// A grammar rule name like `DayToHour` as the words upstream puts in the message for it.
5213fn worded(rule: &str) -> String {
5214    let mut out = String::new();
5215    for character in rule.chars() {
5216        if character.is_ascii_uppercase() && !out.is_empty() {
5217            out.push(' ');
5218        }
5219        out.push(character.to_ascii_uppercase());
5220    }
5221    out
5222}
5223
5224/// The value of one string token, with the quotes gone and whatever the prefix means resolved.
5225///
5226/// There is no fall through that keeps the source text. That arm is what answered `SELECT E'a'`
5227/// with the four characters `E'a'`, and a default that silently answers with the query is a default
5228/// that will do this again with the next spelling somebody adds, so a spelling this does not know
5229/// raises instead. Per #329.
5230fn string_token(text: &str) -> Result<String> {
5231    if let Some(body) = dollar_body(text) {
5232        return Ok(body.to_string());
5233    }
5234    if let Some(body) = quoted_body(text) {
5235        return Ok(body.replace("''", "'"));
5236    }
5237    let Some(body) = text.get(1..).and_then(quoted_body) else {
5238        return Ok(text.to_string());
5239    };
5240    match text.as_bytes()[0] {
5241        b'E' | b'e' => escaped(body),
5242        // `N'abc'` is the string and nothing else. The cast that makes the name is put on outside.
5243        b'N' | b'n' => Ok(body.replace("''", "'")),
5244        // Not a bit string, whatever the spelling suggests. Upstream answers `B'101'` with the four
5245        // characters `b101` as a VARCHAR, and `B''` with the one character `b`, which is measured
5246        // and not guessed. Nothing else is done with the body.
5247        b'B' | b'b' => Ok(format!("b{}", body.replace("''", "'"))),
5248        // `x'41'` is a BLOB and a BLOB is not a string, so the places that want a string out of a
5249        // literal, which are DESCRIBE and the part in EXTRACT, do not get one from this spelling.
5250        _ => Err(Error::not_implemented(format!("the string literal {text} is not supported yet"))),
5251    }
5252}
5253
5254/// The text a blob literal's body means, which is the text a blob prints as.
5255///
5256/// `x'4142'` is two bytes and the pinned binary calls the column `'AB'::BLOB`, so what is kept here
5257/// is the printed form and not the source. The cast that reads it back gives the bytes again, which
5258/// is what makes one text enough for both the value and the name, and it is `Value` that prints it
5259/// so the two spellings of a blob cannot drift apart.
5260///
5261/// Upstream writes `\xHH` for every pair without looking at the digits and lets the cast refuse the
5262/// ones that are not hex, which is why `x'4'` is a parser error and `x'zz'` is a conversion error
5263/// one step later. Doing the same thing gives both messages in the same words. The pairs are bytes
5264/// and not characters: `x'éé'` is four bytes and so two pairs, which is how upstream counts them.
5265fn blob_text(body: &[u8]) -> Result<String> {
5266    if !body.len().is_multiple_of(2) {
5267        return Err(Error::parser("Hex string literal must have an even number of hex digits"));
5268    }
5269    let digit = |byte: u8| (byte as char).to_digit(16).map(|digit| digit as u8);
5270    let bytes: Option<Vec<u8>> =
5271        body.chunks(2).map(|pair| Some(digit(pair[0])? * 16 + digit(pair[1])?)).collect();
5272    match bytes {
5273        Some(bytes) => Ok(Value::Blob(bytes).to_string()),
5274        None => {
5275            Ok(body.chunks(2).map(|pair| format!("\\x{}", String::from_utf8_lossy(pair))).collect())
5276        }
5277    }
5278}
5279
5280/// The body of a single quoted string, for the tokens that are one.
5281///
5282/// An unterminated token has nothing to take off the end and keeps every byte it was given, which
5283/// is why the closing quote has to be a quote that is not also the opening one.
5284fn quoted_body(text: &str) -> Option<&str> {
5285    text.strip_prefix('\'').filter(|rest| !rest.is_empty()).and_then(|rest| rest.strip_suffix('\''))
5286}
5287
5288/// The body of an `E'...'` literal, with the C style escapes resolved.
5289///
5290/// Every rule here was read off the pinned binary one at a time. The named escapes are `\n`, `\t`,
5291/// `\r`, `\b` and `\f`, and `\v` is not one of them. `\x` takes one or two hex digits and `\0`
5292/// through `\7` take one to three octal digits, both of which write a byte and not a character, so
5293/// `\xc3\xa9` is one `é` and `\377` is not a string at all. `\uHHHH` takes exactly four hex digits
5294/// and writes the character they name. Anything else, including a `\u` that is short or names a
5295/// surrogate half or a NUL, drops the backslash and keeps the character, so `\q` is `q` and `\u41`
5296/// is `u41`.
5297///
5298/// The result is bytes until the end because the escapes write bytes, and the two ways of writing
5299/// something that is not a string both raise the way upstream raises them.
5300fn escaped(body: &str) -> Result<String> {
5301    let bytes = body.as_bytes();
5302    let mut out = Vec::with_capacity(bytes.len());
5303    let mut at = 0;
5304    while at < bytes.len() {
5305        let byte = bytes[at];
5306        at += 1;
5307        if byte == b'\'' && bytes.get(at) == Some(&b'\'') {
5308            out.push(b'\'');
5309            at += 1;
5310            continue;
5311        }
5312        if byte != b'\\' || at == bytes.len() {
5313            out.push(byte);
5314            continue;
5315        }
5316        let escape = bytes[at];
5317        at += 1;
5318        match escape {
5319            b'n' => out.push(b'\n'),
5320            b't' => out.push(b'\t'),
5321            b'r' => out.push(b'\r'),
5322            b'b' => out.push(0x08),
5323            b'f' => out.push(0x0c),
5324            b'x' => match digits(bytes, &mut at, 16, 2) {
5325                Some(value) => out.push(value as u8),
5326                None => out.push(b'x'),
5327            },
5328            b'0'..=b'7' => {
5329                at -= 1;
5330                let value = digits(bytes, &mut at, 8, 3).unwrap_or(0);
5331                out.push(value as u8);
5332            }
5333            b'u' => match four_hex(bytes, at).and_then(char::from_u32).filter(|c| *c != '\0') {
5334                Some(c) => {
5335                    at += 4;
5336                    out.extend_from_slice(c.encode_utf8(&mut [0; 4]).as_bytes());
5337                }
5338                None => out.push(b'u'),
5339            },
5340            other => out.push(other),
5341        }
5342    }
5343    if out.contains(&0) {
5344        return Err(Error::parser("Null character not permitted in escape string literal"));
5345    }
5346    String::from_utf8(out).map_err(|error| {
5347        Error::parser(format!(
5348            "Invalid UTF-8 in escape string literal at byte offset {}: byte mismatch",
5349            error.utf8_error().valid_up_to()
5350        ))
5351    })
5352}
5353
5354/// Up to `most` digits in `radix` starting at `at`, moving `at` past the ones that were taken.
5355///
5356/// `None` means there were none at all, which is the case where the escape was not an escape:
5357/// `\x` on its own is the letter `x` upstream and not a zero byte.
5358fn digits(bytes: &[u8], at: &mut usize, radix: u32, most: usize) -> Option<u32> {
5359    let mut value = None;
5360    for _ in 0..most {
5361        let Some(digit) = bytes.get(*at).and_then(|byte| (*byte as char).to_digit(radix)) else {
5362            break;
5363        };
5364        value = Some(value.unwrap_or(0) * radix + digit);
5365        *at += 1;
5366    }
5367    value
5368}
5369
5370/// The four hex digits of a `\uHHHH`, which has to be all four of them or it is not one.
5371///
5372/// Nothing is consumed here, because the digits are only digits if the whole escape works out. A
5373/// surrogate half is not a character and upstream does not pair it up either, so `😀` is
5374/// the ten characters it was written as, which is what the caller falls back to.
5375fn four_hex(bytes: &[u8], at: usize) -> Option<u32> {
5376    let digits = bytes.get(at..at + 4)?;
5377    if !digits.iter().all(u8::is_ascii_hexdigit) {
5378        return None;
5379    }
5380    u32::from_str_radix(std::str::from_utf8(digits).ok()?, 16).ok()
5381}
5382
5383/// The body of a dollar quoted string, for the tokens that are one.
5384///
5385/// The tag is whatever sits between the opening pair of dollars and may be empty, so `$$a$$` and
5386/// `$tag$a$tag$` both arrive here, and nothing inside the body is escaped, which is the whole reason
5387/// the spelling exists. The tokenizer has already found the closing tag, which is the part that takes
5388/// work, so this says where the body starts and ends and no more. A token that is not dollar quoted
5389/// gives `None` and so does an unterminated one, which has no closing tag to take off and keeps every
5390/// byte it was given, the way the matcher already treats it. Per #276.
5391fn dollar_body(text: &str) -> Option<&str> {
5392    let rest = text.strip_prefix('$')?;
5393    let close = rest.find('$')?;
5394    let (tag, body) = (&rest[..close], &rest[close + 1..]);
5395    body.strip_suffix(&format!("${tag}$"))
5396}
5397
5398/// Strip the quoting off an identifier.
5399///
5400/// DuckDB does not fold identifier case at any point, quoted or not, so this only removes the
5401/// quotes and resolves the doubled ones. Anything else would be the parser deciding what a name is.
5402///
5403/// Single quotes are stripped too, and the only way one gets here is the file name in `FROM
5404/// 'hits.parquet'`, because the matcher takes a string for a name in that position and in `COPY t TO
5405/// '...'` and nowhere else. Leaving them on would make that name different from the one `FROM
5406/// "hits.parquet"` writes, and DuckDB reads both of those as the same file.
5407fn unquote(text: &str) -> String {
5408    if let Some(body) = text.strip_prefix('"').and_then(|rest| rest.strip_suffix('"')) {
5409        return body.replace("\"\"", "\"");
5410    }
5411    match text.strip_prefix('\'').and_then(|rest| rest.strip_suffix('\'')) {
5412        Some(body) => body.replace("''", "'"),
5413        None => text.to_string(),
5414    }
5415}
5416
5417#[cfg(test)]
5418mod tests {
5419    use super::*;
5420    use crate::corpus::CORPUS;
5421    use crate::matcher::parse;
5422
5423    /// The AST written back out as text, which is what the assertions below read.
5424    ///
5425    /// Not a SQL printer and not trying to be. It is deliberately not valid SQL: operators are
5426    /// spelled with the name of the variant and every binary node is parenthesised, so that a test
5427    /// asserting on this text is asserting on the shape of the tree and not on a formatting choice.
5428    /// `a - b - c` and `a - (b - c)` have to look different here or the test that tells them apart
5429    /// is not a test.
5430    fn show(ast: &Ast, expr: ExprRef) -> String {
5431        if expr == NONE {
5432            return "-".to_string();
5433        }
5434        /// The `FILTER` on a call, which is nothing at all when there is none.
5435        fn shown_filter(ast: &Ast, filter: ExprRef) -> String {
5436            if filter == NONE { String::new() } else { format!(" FILTER [{}]", show(ast, filter)) }
5437        }
5438        /// A run of sort keys, which a window call has two of and in two different places.
5439        fn keys(ast: &Ast, slice: Slice) -> String {
5440            ast.order_list(slice)
5441                .iter()
5442                .map(|item| format!("{} {:?} {:?}", show(ast, item.expr), item.order, item.nulls))
5443                .collect::<Vec<_>>()
5444                .join(", ")
5445        }
5446        let list = |slice: Slice| {
5447            ast.expr_list(slice).iter().map(|&item| show(ast, item)).collect::<Vec<_>>().join(", ")
5448        };
5449        match ast.expr(expr) {
5450            Expr::Star { qualifier, replacements } => {
5451                let star = if qualifier.is_empty() {
5452                    "*".to_string()
5453                } else {
5454                    format!("{}.*", ast.name_text(qualifier))
5455                };
5456                if replacements.is_empty() {
5457                    return star;
5458                }
5459                let entries: Vec<String> = ast
5460                    .target_list(replacements)
5461                    .iter()
5462                    .map(|target| {
5463                        format!("{} AS {}", show(ast, target.expr), ast.string(target.alias))
5464                    })
5465                    .collect();
5466                format!("{star} REPLACE ({})", entries.join(", "))
5467            }
5468            Expr::Column { name } => ast.name_text(name),
5469            Expr::Literal { kind, text } => match kind {
5470                LiteralKind::Number => ast.string(text).to_string(),
5471                LiteralKind::String => format!("'{}'", ast.string(text)),
5472                LiteralKind::Blob => format!("'{}'::BLOB", ast.string(text)),
5473                other => format!("{other:?}").to_uppercase(),
5474            },
5475            Expr::Unary { op, operand } => format!("({op:?} {})", show(ast, operand)),
5476            Expr::Binary { op, left, right } => {
5477                let op = match op {
5478                    BinaryOp::Named(name) => ast.string(name).to_string(),
5479                    other => format!("{other:?}"),
5480                };
5481                format!("({} {op} {})", show(ast, left), show(ast, right))
5482            }
5483            Expr::Function { name, args, distinct, filter } => {
5484                let distinct = if distinct { "DISTINCT " } else { "" };
5485                let filter = shown_filter(ast, filter);
5486                format!("{}({distinct}{}){filter}", ast.name_text(name), list(args))
5487            }
5488            Expr::Window { name, args, distinct, filter, ignore_nulls, order: inner, spec } => {
5489                let distinct = if distinct { "DISTINCT " } else { "" };
5490                let filter = shown_filter(ast, filter);
5491                let nulls = if ignore_nulls { " IGNORE NULLS" } else { "" };
5492                let inner = keys(ast, inner);
5493                let inner = if inner.is_empty() { inner } else { format!(" ORDER BY {inner}") };
5494                let held = ast.window(spec);
5495                let order = keys(ast, held.order);
5496                let bound = |end: WindowBound| match end {
5497                    WindowBound::Preceding(offset) => format!("Preceding({})", show(ast, offset)),
5498                    WindowBound::Following(offset) => format!("Following({})", show(ast, offset)),
5499                    other => format!("{other:?}"),
5500                };
5501                format!(
5502                    "{}({distinct}{}{inner}{nulls}){filter} OVER [{}] [{order}] [{:?} {} {} {:?}]",
5503                    ast.name_text(name),
5504                    list(args),
5505                    list(held.partition),
5506                    held.unit,
5507                    bound(held.start),
5508                    bound(held.end),
5509                    held.exclude
5510                )
5511            }
5512            Expr::Cast { operand, ty, try_cast } => {
5513                let word = if try_cast { "TRY_CAST" } else { "CAST" };
5514                format!("{word}({} AS {})", show(ast, operand), ast.string(ty))
5515            }
5516            Expr::Case { operand, arms, otherwise } => {
5517                let arms = ast
5518                    .arm_list(arms)
5519                    .iter()
5520                    .map(|arm| format!("WHEN {} THEN {}", show(ast, arm.when), show(ast, arm.then)))
5521                    .collect::<Vec<_>>()
5522                    .join(" ");
5523                format!("CASE {} {arms} ELSE {} END", show(ast, operand), show(ast, otherwise))
5524            }
5525            Expr::Between { operand, low, high, negated } => {
5526                let not = if negated { "NOT " } else { "" };
5527                format!(
5528                    "({not}{} BETWEEN {} AND {})",
5529                    show(ast, operand),
5530                    show(ast, low),
5531                    show(ast, high)
5532                )
5533            }
5534            Expr::In { operand, list: items, negated } => {
5535                let not = if negated { "NOT " } else { "" };
5536                format!("({not}{} IN [{}])", show(ast, operand), list(items))
5537            }
5538            Expr::List { items } => format!("[{}]", list(items)),
5539            Expr::Lambda { params, body } => {
5540                let params: Vec<&str> = ast.name(params).collect();
5541                format!("(lambda {}: {})", params.join(", "), show(ast, body))
5542            }
5543            Expr::Parameter { name } => format!("${}", ast.string(name)),
5544            Expr::Default => "DEFAULT".to_string(),
5545            Expr::Row { items } => format!("ROW({})", list(items)),
5546            Expr::Struct { names, values } => {
5547                let fields: Vec<String> = ast
5548                    .name(names)
5549                    .zip(ast.expr_list(values))
5550                    .map(|(name, &value)| format!("{name}: {}", show(ast, value)))
5551                    .collect();
5552                format!("{{{}}}", fields.join(", "))
5553            }
5554            Expr::Subquery { query, array: false } => format!("({})", show_query(ast, query)),
5555            Expr::Subquery { query, array: true } => format!("ARRAY({})", show_query(ast, query)),
5556            Expr::Exists { query, negated } => {
5557                let exists = format!("EXISTS ({})", show_query(ast, query));
5558                if negated { format!("NOT {exists}") } else { exists }
5559            }
5560            Expr::InSubquery { operand, query, negated } => {
5561                let written = format!("{} IN ({})", show(ast, operand), show_query(ast, query));
5562                if negated { format!("NOT {written}") } else { written }
5563            }
5564            Expr::QuantifiedSubquery { operand, op, query, all } => {
5565                let quantifier = if all { "ALL" } else { "ANY" };
5566                format!("{} {op:?} {quantifier} ({})", show(ast, operand), show_query(ast, query))
5567            }
5568        }
5569    }
5570
5571    /// One from item written back out.
5572    fn show_source(ast: &Ast, source: SourceRef) -> String {
5573        let alias = |alias: StrRef| match alias {
5574            NONE => String::new(),
5575            other => format!(" AS {}", ast.string(other)),
5576        };
5577        match ast.source(source) {
5578            Source::Table { name, alias: name_alias, .. } => {
5579                format!("{}{}", ast.name_text(name), alias(name_alias))
5580            }
5581            Source::Function { name, args, alias: call_alias, .. } => {
5582                let args = ast
5583                    .target_list(args)
5584                    .iter()
5585                    .map(|item| match item.alias {
5586                        NONE => show(ast, item.expr),
5587                        named => format!("{} := {}", ast.string(named), show(ast, item.expr)),
5588                    })
5589                    .collect::<Vec<_>>()
5590                    .join(", ");
5591                format!("{}({args}){}", ast.name_text(name), alias(call_alias))
5592            }
5593            Source::Subquery { query, alias: query_alias, .. } => {
5594                format!("({}){}", show_query(ast, query), alias(query_alias))
5595            }
5596            Source::Cte { cte, alias: cte_alias, .. } => {
5597                format!("{}{}", ast.string(ast.cte(cte).name), alias(cte_alias))
5598            }
5599            Source::Values { rows, alias: values_alias, .. } => {
5600                format!("{}{}", show_rows(ast, rows), alias(values_alias))
5601            }
5602            Source::Join { left, right, kind, natural, on, using } => {
5603                let natural = if natural { "NATURAL " } else { "" };
5604                let on = if on == NONE { String::new() } else { format!(" ON {}", show(ast, on)) };
5605                let using = if using.is_empty() {
5606                    String::new()
5607                } else {
5608                    format!(" USING ({})", ast.name_text(using))
5609                };
5610                format!(
5611                    "({} {natural}{kind:?} JOIN {}{on}{using})",
5612                    show_source(ast, left),
5613                    show_source(ast, right)
5614                )
5615            }
5616        }
5617    }
5618
5619    /// The rows of a `VALUES` written back out.
5620    fn show_rows(ast: &Ast, rows: Slice) -> String {
5621        let rows = ast
5622            .rows(rows)
5623            .iter()
5624            .map(|&row| {
5625                let items = ast
5626                    .expr_list(row)
5627                    .iter()
5628                    .map(|&item| show(ast, item))
5629                    .collect::<Vec<_>>()
5630                    .join(", ");
5631                format!("({items})")
5632            })
5633            .collect::<Vec<_>>()
5634            .join(", ");
5635        format!("VALUES {rows}")
5636    }
5637
5638    /// A writing statement written back out with its `RETURNING` query after it, if it has one.
5639    fn show_returning(ast: &Ast, insert: &Insert, out: String) -> String {
5640        match insert.returning {
5641            Some(returning) => out + &format!(" RETURNING {}", show_query(ast, returning)),
5642            None => out,
5643        }
5644    }
5645
5646    /// One query written back out.
5647    fn show_query(ast: &Ast, index: QueryRef) -> String {
5648        let query = ast.query(index);
5649        let list = |slice: Slice| {
5650            ast.expr_list(slice).iter().map(|&item| show(ast, item)).collect::<Vec<_>>().join(", ")
5651        };
5652        let mut out = String::new();
5653        for &index in ast.cte_list(query.ctes) {
5654            let cte = ast.cte(index);
5655            let columns = ast.name(cte.columns).collect::<Vec<_>>().join(", ");
5656            let columns = if columns.is_empty() { columns } else { format!("({columns})") };
5657            out += &format!(
5658                "WITH {}{columns} AS MATERIALIZED ({}) ",
5659                ast.string(cte.name),
5660                show_query(ast, cte.query)
5661            );
5662        }
5663        out += &match query.body {
5664            QueryBody::SetOp { op, quantifier, by_name, left, right } => {
5665                let by_name = if by_name { " BY NAME" } else { "" };
5666                format!(
5667                    "({} {op:?} {quantifier:?}{by_name} {})",
5668                    show_query(ast, left),
5669                    show_query(ast, right)
5670                )
5671            }
5672            QueryBody::Select(index) => {
5673                let select = ast.select(index);
5674                let distinct = match select.distinct {
5675                    Distinct::No => String::new(),
5676                    Distinct::Yes => " DISTINCT".to_string(),
5677                    Distinct::On(on) => format!(" DISTINCT ON ({})", list(on)),
5678                };
5679                let targets = ast
5680                    .target_list(select.targets)
5681                    .iter()
5682                    .map(|target| match target.alias {
5683                        NONE => show(ast, target.expr),
5684                        alias => format!("{} AS {}", show(ast, target.expr), ast.string(alias)),
5685                    })
5686                    .collect::<Vec<_>>()
5687                    .join(", ");
5688                let mut out = format!("SELECT{distinct} {targets}");
5689                if !select.from.is_empty() {
5690                    let from = ast
5691                        .source_list(select.from)
5692                        .iter()
5693                        .map(|&source| show_source(ast, source))
5694                        .collect::<Vec<_>>()
5695                        .join(", ");
5696                    out += &format!(" FROM {from}");
5697                }
5698                if select.filter != NONE {
5699                    out += &format!(" WHERE {}", show(ast, select.filter));
5700                }
5701                if select.group_by_all {
5702                    out += " GROUP BY ALL";
5703                } else if !select.group_by.is_empty() {
5704                    out += &format!(" GROUP BY {}", list(select.group_by));
5705                }
5706                if select.having != NONE {
5707                    out += &format!(" HAVING {}", show(ast, select.having));
5708                }
5709                out
5710            }
5711            QueryBody::Values(rows) => show_rows(ast, rows),
5712            QueryBody::Describe(inner) => format!("DESCRIBE {}", show_query(ast, inner)),
5713            QueryBody::Show { name, .. } => format!("SHOW {}", ast.name_text(name)),
5714        };
5715        if query.order_by_all {
5716            out += " ORDER BY ALL";
5717        } else if !query.order_by.is_empty() {
5718            let items = ast
5719                .order_list(query.order_by)
5720                .iter()
5721                .map(|item| format!("{} {:?} {:?}", show(ast, item.expr), item.order, item.nulls))
5722                .collect::<Vec<_>>()
5723                .join(", ");
5724            out += &format!(" ORDER BY {items}");
5725        }
5726        if query.limit != NONE {
5727            let percent = if query.limit_percent { "%" } else { "" };
5728            out += &format!(" LIMIT {}{percent}", show(ast, query.limit));
5729        }
5730        if query.offset != NONE {
5731            out += &format!(" OFFSET {}", show(ast, query.offset));
5732        }
5733        out
5734    }
5735
5736    /// One statement, transformed and written back out.
5737    fn round(query: &str) -> String {
5738        let ast = parse_ast(query).unwrap_or_else(|error| panic!("{query}: {error}"));
5739        assert_eq!(ast.statements.len(), 1, "{query} is one statement");
5740        let Statement::Query(index) = ast.statements[0] else {
5741            panic!("{query} is not a query");
5742        };
5743        show_query(&ast, index)
5744    }
5745
5746    fn round_with_case(query: &str, case: IdentifierCase) -> String {
5747        let ast =
5748            parse_ast_with_case(query, case).unwrap_or_else(|error| panic!("{query}: {error}"));
5749        let Statement::Query(index) = ast.statements[0] else {
5750            panic!("{query} is not a query");
5751        };
5752        show_query(&ast, index)
5753    }
5754
5755    /// One statement, transformed and written back out as the DDL and DML shape it is.
5756    fn round_statement(query: &str) -> String {
5757        let ast = parse_ast(query).unwrap_or_else(|error| panic!("{query}: {error}"));
5758        assert_eq!(ast.statements.len(), 1, "{query} is one statement");
5759        match ast.statements[0] {
5760            Statement::Query(index) => show_query(&ast, index),
5761            Statement::CreateTable(index) => {
5762                let create = ast.create_table(index);
5763                let mut out = "CREATE".to_string();
5764                if create.or_replace {
5765                    out += " OR REPLACE";
5766                }
5767                if create.temporary {
5768                    out += " TEMPORARY";
5769                }
5770                out += " TABLE";
5771                if create.if_not_exists {
5772                    out += " IF NOT EXISTS";
5773                }
5774                out += &format!(" {}", ast.name_text(create.name));
5775                let columns = ast
5776                    .column_defs(create.columns)
5777                    .iter()
5778                    .map(|def| {
5779                        let ty = match def.ty {
5780                            NONE => String::new(),
5781                            other => format!(" {}", ast.string(other)),
5782                        };
5783                        let null = if def.not_null { " NOT NULL" } else { "" };
5784                        format!("{}{ty}{null}", ast.string(def.name))
5785                    })
5786                    .collect::<Vec<_>>()
5787                    .join(", ");
5788                if !columns.is_empty() || create.query == NONE {
5789                    out += &format!(" ({columns})");
5790                }
5791                if create.query != NONE {
5792                    out += &format!(" AS {}", show_query(&ast, create.query));
5793                }
5794                out
5795            }
5796            Statement::CreateView(index) => {
5797                let create = ast.create_view(index);
5798                let mut out = "CREATE".to_string();
5799                if create.or_replace {
5800                    out += " OR REPLACE";
5801                }
5802                if create.temporary {
5803                    out += " TEMPORARY";
5804                }
5805                out += " VIEW";
5806                if create.if_not_exists {
5807                    out += " IF NOT EXISTS";
5808                }
5809                out += &format!(" {}", ast.name_text(create.name));
5810                if !create.columns.is_empty() {
5811                    let columns = ast.name(create.columns).collect::<Vec<_>>().join(", ");
5812                    out += &format!(" ({columns})");
5813                }
5814                out + &format!(" AS {}", show_query(&ast, create.query))
5815            }
5816            Statement::DropTable(index) => {
5817                let drop = ast.drop_table(index);
5818                let mut out = if drop.view { "DROP VIEW" } else { "DROP TABLE" }.to_string();
5819                if drop.if_exists {
5820                    out += " IF EXISTS";
5821                }
5822                let names = ast
5823                    .name_list(drop.names)
5824                    .iter()
5825                    .map(|&name| ast.name_text(name))
5826                    .collect::<Vec<_>>()
5827                    .join(", ");
5828                out + &format!(" {names}")
5829            }
5830            Statement::Schema(index) => {
5831                let schema = ast.schema(index);
5832                let mut out = if schema.drop { "DROP" } else { "CREATE" }.to_string();
5833                if schema.or_replace {
5834                    out += " OR REPLACE";
5835                }
5836                if schema.temporary {
5837                    out += " TEMPORARY";
5838                }
5839                out += " SCHEMA";
5840                if schema.quiet {
5841                    out += if schema.drop { " IF EXISTS" } else { " IF NOT EXISTS" };
5842                }
5843                out += &format!(" {}", ast.name_text(schema.name));
5844                if schema.cascade {
5845                    out += " CASCADE";
5846                }
5847                out
5848            }
5849            Statement::Alter(index) => {
5850                let alter = ast.alter(index);
5851                let mut out = if alter.view { "ALTER VIEW" } else { "ALTER TABLE" }.to_string();
5852                if alter.quiet {
5853                    out += " IF EXISTS";
5854                }
5855                out += &format!(" {} ", ast.name_text(alter.name));
5856                let expr = |expr| show(&ast, expr);
5857                out + &match alter.action {
5858                    AlterAction::Rename { to } => format!("RENAME TO {}", ast.string(to)),
5859                    AlterAction::RenameColumn { column, to } => {
5860                        format!("RENAME COLUMN {} TO {}", ast.string(column), ast.string(to))
5861                    }
5862                    AlterAction::AddColumn { column, quiet } => {
5863                        let mut out = "ADD COLUMN ".to_string();
5864                        if quiet {
5865                            out += "IF NOT EXISTS ";
5866                        }
5867                        out += &format!("{} {}", ast.string(column.name), ast.string(column.ty));
5868                        if column.default != NONE {
5869                            out += &format!(" DEFAULT {}", expr(column.default));
5870                        }
5871                        if column.not_null {
5872                            out += " NOT NULL";
5873                        }
5874                        out
5875                    }
5876                    AlterAction::DropColumn { column, quiet } => {
5877                        let quiet = if quiet { "IF EXISTS " } else { "" };
5878                        format!("DROP COLUMN {quiet}{}", ast.string(column))
5879                    }
5880                    AlterAction::Default { column, default } if default == NONE => {
5881                        format!("ALTER COLUMN {} DROP DEFAULT", ast.string(column))
5882                    }
5883                    AlterAction::Default { column, default } => {
5884                        format!("ALTER COLUMN {} SET DEFAULT {}", ast.string(column), expr(default))
5885                    }
5886                    AlterAction::NotNull { column, set } => {
5887                        let which = if set { "SET" } else { "DROP" };
5888                        format!("ALTER COLUMN {} {which} NOT NULL", ast.string(column))
5889                    }
5890                    AlterAction::Type { column, ty, using } => {
5891                        let mut out = format!("ALTER COLUMN {} SET DATA TYPE", ast.string(column));
5892                        if ty != NONE {
5893                            out += &format!(" {}", ast.string(ty));
5894                        }
5895                        if using != NONE {
5896                            out += &format!(" USING {}", expr(using));
5897                        }
5898                        out
5899                    }
5900                }
5901            }
5902            Statement::Index(index) => {
5903                let index = ast.index(index);
5904                if index.drop {
5905                    return format!("DROP INDEX {}", ast.name_text(index.name));
5906                }
5907                let unique = if index.unique { " UNIQUE" } else { "" };
5908                format!(
5909                    "CREATE{unique} INDEX {} ON {} ({})",
5910                    ast.name_text(index.name),
5911                    ast.name_text(index.table),
5912                    index.elements.len
5913                )
5914            }
5915            Statement::Type(index) => {
5916                let made = ast.type_def(index);
5917                let mut out = if made.drop { "DROP" } else { "CREATE" }.to_string();
5918                if made.or_replace {
5919                    out += " OR REPLACE";
5920                }
5921                if made.temporary {
5922                    out += " TEMPORARY";
5923                }
5924                out += " TYPE";
5925                if made.quiet {
5926                    out += if made.drop { " IF EXISTS" } else { " IF NOT EXISTS" };
5927                }
5928                out += &format!(" {}", ast.name_text(made.name));
5929                if !made.drop {
5930                    out += &format!(" AS {}", ast.string(made.ty));
5931                }
5932                if made.cascade {
5933                    out += " CASCADE";
5934                }
5935                out
5936            }
5937            Statement::Sequence(index) => {
5938                let sequence = ast.sequence(index);
5939                if !sequence.owner.is_empty() {
5940                    let mut out = "ALTER SEQUENCE".to_string();
5941                    if sequence.quiet {
5942                        out += " IF EXISTS";
5943                    }
5944                    return format!(
5945                        "{out} {} OWNED BY {}",
5946                        ast.name_text(sequence.name),
5947                        ast.name_text(sequence.owner)
5948                    );
5949                }
5950                let mut out = if sequence.drop { "DROP" } else { "CREATE" }.to_string();
5951                if sequence.or_replace {
5952                    out += " OR REPLACE";
5953                }
5954                if sequence.temporary {
5955                    out += " TEMPORARY";
5956                }
5957                out += " SEQUENCE";
5958                if sequence.quiet {
5959                    out += if sequence.drop { " IF EXISTS" } else { " IF NOT EXISTS" };
5960                }
5961                out += &format!(" {}", ast.name_text(sequence.name));
5962                if !sequence.drop {
5963                    let options = sequence.options;
5964                    out += &format!(
5965                        " INCREMENT BY {} MINVALUE {} MAXVALUE {} START {}{}",
5966                        options.increment,
5967                        options.min,
5968                        options.max,
5969                        options.start,
5970                        if options.cycle { " CYCLE" } else { " NO CYCLE" }
5971                    );
5972                }
5973                if sequence.cascade {
5974                    out += " CASCADE";
5975                }
5976                out
5977            }
5978            Statement::Insert(index) => {
5979                let insert = ast.insert(index);
5980                let mut out = format!("INSERT INTO {}", ast.name_text(insert.name));
5981                if !insert.columns.is_empty() {
5982                    let columns = ast.name(insert.columns).collect::<Vec<_>>().join(", ");
5983                    out += &format!(" ({columns})");
5984                }
5985                out += &format!(" {}", show_query(&ast, insert.source));
5986                show_returning(&ast, &insert, out)
5987            }
5988            Statement::Update(index) | Statement::Delete(index) => {
5989                let change = ast.insert(index);
5990                let columns = ast.name(change.columns).collect::<Vec<_>>().join(", ");
5991                let out = format!(
5992                    "{} {} ({columns}) {}",
5993                    if matches!(ast.statements[0], Statement::Update(_)) {
5994                        "UPDATE"
5995                    } else {
5996                        "DELETE"
5997                    },
5998                    ast.name_text(change.name),
5999                    show_query(&ast, change.source)
6000                );
6001                show_returning(&ast, &change, out)
6002            }
6003            Statement::Set(index) if ast.setting(index).pragma => {
6004                format!("PRAGMA {}", ast.string(ast.setting(index).name))
6005            }
6006            Statement::Set(index) => {
6007                let setting = ast.setting(index);
6008                let scope = match setting.scope.keyword() {
6009                    "" => String::new(),
6010                    word => format!(" {word}"),
6011                };
6012                format!("SET{scope} {} = {}", ast.string(setting.name), show(&ast, setting.value))
6013            }
6014            Statement::Reset(index) => {
6015                let setting = ast.setting(index);
6016                let scope = match setting.scope.keyword() {
6017                    "" => String::new(),
6018                    word => format!(" {word}"),
6019                };
6020                format!("RESET{scope} {}", ast.string(setting.name))
6021            }
6022            Statement::Checkpoint(name) if name == NONE => "CHECKPOINT".to_string(),
6023            Statement::Checkpoint(name) => format!("CHECKPOINT {}", ast.string(name)),
6024            Statement::Attach(index) => {
6025                let attach = ast.attach(index);
6026                let alias = if attach.alias == NONE {
6027                    String::new()
6028                } else {
6029                    format!(" AS {}", ast.string(attach.alias))
6030                };
6031                format!("ATTACH {}{alias}", show(&ast, attach.path))
6032            }
6033            Statement::Detach { name, if_exists } => {
6034                let exists = if if_exists { "IF EXISTS " } else { "" };
6035                format!("DETACH {exists}{}", ast.string(name))
6036            }
6037            Statement::Transaction(Transaction::Begin { read_only: false }) => "BEGIN".to_string(),
6038            Statement::Transaction(Transaction::Begin { read_only: true }) => {
6039                "BEGIN READ ONLY".to_string()
6040            }
6041            Statement::Transaction(Transaction::Commit) => "COMMIT".to_string(),
6042            Statement::Transaction(Transaction::Rollback) => "ROLLBACK".to_string(),
6043            Statement::Explain { query, analyze, statistics, codegen } => {
6044                let analyze = if analyze { "ANALYZE " } else { "" };
6045                let statistics = if statistics { "(STATISTICS) " } else { "" };
6046                let codegen = if codegen { "(CODEGEN) " } else { "" };
6047                format!("EXPLAIN {analyze}{statistics}{codegen}{}", show_query(&ast, query))
6048            }
6049            Statement::CopyTo(index) => {
6050                let copy = &ast.copies[index as usize];
6051                let options = copy
6052                    .options
6053                    .iter()
6054                    .map(|(name, value)| match value {
6055                        Some(value) => format!(" {name}={value}"),
6056                        None => format!(" {name}"),
6057                    })
6058                    .collect::<String>();
6059                format!("COPY ({}) TO {}{options}", show_query(&ast, copy.query), copy.path)
6060            }
6061        }
6062    }
6063
6064    #[test]
6065    fn expressions_and_queries_keep_their_source_ranges() {
6066        let sql = "SELECT 1 + 22";
6067        let ast = parse_ast(sql).expect("the query parses");
6068        let Statement::Query(query) = ast.statements[0] else { panic!("a query") };
6069        assert_eq!(ast.query_span(query), Span::new(0, sql.len() as u32));
6070        let twenty_two = ast
6071            .exprs
6072            .iter()
6073            .enumerate()
6074            .find_map(|(at, expr)| match *expr {
6075                Expr::Literal { kind: LiteralKind::Number, text } if ast.string(text) == "22" => {
6076                    Some(at as u32)
6077                }
6078                _ => None,
6079            })
6080            .expect("the literal is in the arena");
6081        assert_eq!(ast.expr_span(twenty_two), Span::new(11, 13));
6082    }
6083
6084    #[test]
6085    fn an_explain_keeps_the_query_it_was_asked_about() {
6086        assert_eq!(
6087            round_statement("EXPLAIN SELECT a FROM t WHERE a > 1"),
6088            "EXPLAIN SELECT a FROM t WHERE (a Gt 1)"
6089        );
6090        assert_eq!(round_statement("explain select 1"), "EXPLAIN SELECT 1");
6091        assert_eq!(round_statement("explain analyze select 1"), "EXPLAIN ANALYZE SELECT 1");
6092    }
6093
6094    #[test]
6095    fn the_three_explain_options_this_answers_mean_what_their_names_say() {
6096        // `ANALYZE` in the list is the keyword written the other way, so the two spellings have to
6097        // land on the same statement rather than on two that happen to print alike.
6098        assert_eq!(round_statement("EXPLAIN (ANALYZE) SELECT 1"), "EXPLAIN ANALYZE SELECT 1");
6099        assert_eq!(
6100            round_statement("explain (analyze) select 1"),
6101            round_statement("explain analyze select 1")
6102        );
6103        // `LOGICAL` names the plan this already prints, so asking for it changes nothing.
6104        assert_eq!(round_statement("EXPLAIN (LOGICAL) SELECT 1"), "EXPLAIN SELECT 1");
6105        assert_eq!(
6106            round_statement("EXPLAIN (STATISTICS) SELECT 1"),
6107            "EXPLAIN (STATISTICS) SELECT 1"
6108        );
6109        assert_eq!(
6110            round_statement("EXPLAIN (ANALYZE, STATISTICS) SELECT 1"),
6111            "EXPLAIN ANALYZE (STATISTICS) SELECT 1"
6112        );
6113        assert_eq!(
6114            round_statement("EXPLAIN ANALYZE (STATISTICS) SELECT 1"),
6115            "EXPLAIN ANALYZE (STATISTICS) SELECT 1"
6116        );
6117        assert_eq!(round_statement("explain (codegen) select 1"), "EXPLAIN (CODEGEN) SELECT 1");
6118    }
6119
6120    #[test]
6121    fn the_parts_of_an_explain_that_are_not_the_query_are_refused_by_name() {
6122        // An option name this does not answer is refused in DuckDB's own words, an option that
6123        // carries a value is refused by its grammar rule because none of the three takes one, and a
6124        // statement that is not a query has no plan to show.
6125        for (query, named) in [
6126            ("EXPLAIN (FORMAT JSON) SELECT 1", "Unimplemented explain type: format"),
6127            ("EXPLAIN (NONSENSE) SELECT 1", "Unimplemented explain type: nonsense"),
6128            ("EXPLAIN (CODEGEN, ANALYZE) SELECT 1", "cannot be combined"),
6129            ("EXPLAIN (ANALYZE false) SELECT 1", "ExplainOption"),
6130            ("EXPLAIN INSERT INTO t VALUES (1)", "InsertStatement"),
6131            ("EXPLAIN CREATE TABLE u (a INTEGER)", "CreateStatement"),
6132        ] {
6133            let error = parse_ast(query).expect_err(query).to_string();
6134            assert!(error.contains(named), "{query}: {error}");
6135        }
6136    }
6137
6138    #[test]
6139    fn a_set_keeps_its_name_its_scope_and_its_value() {
6140        assert_eq!(round_statement("SET memory_limit = '1GB'"), "SET memory_limit = '1GB'");
6141        assert_eq!(round_statement("set threads=4"), "SET threads = 4");
6142        assert_eq!(round_statement("SET GLOBAL threads = 4"), "SET GLOBAL threads = 4");
6143        assert_eq!(round_statement("SET SESSION threads = 4"), "SET SESSION threads = 4");
6144        assert_eq!(round_statement("SET LOCAL threads = 4"), "SET LOCAL threads = 4");
6145        assert_eq!(round_statement("RESET memory_limit"), "RESET memory_limit");
6146        assert_eq!(round_statement("RESET GLOBAL memory_limit"), "RESET GLOBAL memory_limit");
6147        assert_eq!(
6148            round_statement("SET TIME ZONE 'Asia/Kathmandu'"),
6149            "SET TimeZone = 'Asia/Kathmandu'"
6150        );
6151        assert_eq!(round_statement("SET TIME ZONE UTC"), "SET TimeZone = 'UTC'");
6152        assert_eq!(round_statement("SET TIME ZONE DEFAULT"), "RESET TimeZone");
6153        assert_eq!(round_statement("SET TIME ZONE LOCAL"), "RESET TimeZone");
6154    }
6155
6156    #[test]
6157    fn a_session_variable_is_refused_rather_than_read_as_a_setting() {
6158        // `SET VARIABLE x = 1` declares a session variable, which is not a knob on the engine, and
6159        // reading it as one would change an answer quietly.
6160        let error = parse_ast("SET VARIABLE x = 1").expect_err("a variable");
6161        assert_eq!(error.code().duckdb_name(), "Not implemented Error");
6162    }
6163
6164    #[test]
6165    fn set_schema_and_use_are_the_schema_setting() {
6166        assert_eq!(round_statement("SET SCHEMA 'main'"), "SET schema = 'main'");
6167        assert_eq!(round_statement("USE s1"), "SET schema = 's1'");
6168        assert_eq!(round_statement("USE memory.s1"), "SET schema = 'memory.s1'");
6169        assert_eq!(round_statement("USE \"a.b\""), "SET schema = '\"a.b\"'");
6170        let error = parse_ast("USE a.b.c").expect_err("three parts");
6171        assert_eq!(error.message(), "Expected \"USE database\" or \"USE database.schema\"");
6172    }
6173
6174    #[test]
6175    fn a_setting_written_with_a_list_of_values_is_refused_rather_than_taking_the_first() {
6176        let error = parse_ast("SET search_path = a, b").expect_err("a list of two");
6177        assert_eq!(error.message(), "SET can only contain a single value");
6178    }
6179
6180    #[test]
6181    fn the_query_m0_has_to_run_transforms() {
6182        assert_eq!(round("SELECT * FROM t WHERE x > 5"), "SELECT * FROM t WHERE (x Gt 5)");
6183    }
6184
6185    #[test]
6186    fn a_replace_list_rides_on_the_star_it_changes() {
6187        // The parentheses are optional around a single entry, which is how the clickbench load
6188        // recipe is not written but is how a lot of hand written sql is.
6189        assert_eq!(
6190            round("SELECT * REPLACE (a + 1 AS a) FROM t"),
6191            "SELECT * REPLACE ((a Add 1) AS a) FROM t"
6192        );
6193        assert_eq!(
6194            round("SELECT * REPLACE a + 1 AS a FROM t"),
6195            "SELECT * REPLACE ((a Add 1) AS a) FROM t"
6196        );
6197        assert_eq!(
6198            round("SELECT t.* REPLACE (make_date(a) AS a, b * 2 AS b) FROM t"),
6199            "SELECT t.* REPLACE (make_date(a) AS a, (b Multiply 2) AS b) FROM t"
6200        );
6201    }
6202
6203    #[test]
6204    fn one_column_cannot_be_replaced_twice() {
6205        // Caught here rather than in the binder because it is a mistake in what was written and
6206        // not a mistake about what is in the table, and duckdb reports it the same way.
6207        let error = parse_ast("SELECT * REPLACE (a + 1 AS a, a + 2 AS A) FROM t").unwrap_err();
6208        assert_eq!(error.to_string(), "Parser Error: Duplicate entry \"A\" in REPLACE list");
6209    }
6210
6211    #[test]
6212    fn a_table_function_argument_can_have_a_name_written_in_front_of_it() {
6213        // The grammar has `:=` and `=>`. It does not have `=`, which parses as a comparison and is
6214        // read back apart here, and that is the spelling the clickbench load recipe uses.
6215        for spelling in
6216            ["binary_as_string := True", "binary_as_string => True", "binary_as_string = True"]
6217        {
6218            assert_eq!(
6219                round(&format!("SELECT * FROM read_parquet('f.parquet', {spelling})")),
6220                "SELECT * FROM read_parquet('f.parquet', binary_as_string := TRUE)",
6221                "{spelling}"
6222            );
6223        }
6224    }
6225
6226    #[test]
6227    fn an_equality_that_is_not_a_bare_name_stays_an_argument() {
6228        // A qualified name on the left is not a parameter name, and neither is anything that is
6229        // not a name at all, so both of those stay the comparison they were written as.
6230        assert_eq!(round("SELECT * FROM f(t.a = 1)"), "SELECT * FROM f((t.a Eq 1))");
6231        assert_eq!(round("SELECT * FROM f(1 = 1)"), "SELECT * FROM f((1 Eq 1))");
6232    }
6233
6234    #[test]
6235    fn a_create_table_keeps_its_types_as_text() {
6236        assert_eq!(
6237            round_statement("CREATE TABLE t (a INTEGER, b VARCHAR NOT NULL)"),
6238            "CREATE TABLE t (a INTEGER, b VARCHAR NOT NULL)"
6239        );
6240        // The type is the text between the identifier and whatever follows it, parentheses and
6241        // all, because resolving `DECIMAL(18, 3)` into a width and a scale is the binder's job and
6242        // doing it here would mean two places that know the type table.
6243        assert_eq!(
6244            round_statement("CREATE TABLE t (a DECIMAL(18, 3), b STRUCT(x INT))"),
6245            "CREATE TABLE t (a DECIMAL(18, 3), b STRUCT(x INT))"
6246        );
6247    }
6248
6249    #[test]
6250    fn the_modifiers_on_a_create_table_survive() {
6251        assert_eq!(
6252            round_statement("CREATE OR REPLACE TEMPORARY TABLE s.t (a INT)"),
6253            "CREATE OR REPLACE TEMPORARY TABLE s.t (a INT)"
6254        );
6255        assert_eq!(
6256            round_statement("CREATE TEMPORARY TABLE IF NOT EXISTS s.t (a INT)"),
6257            "CREATE TEMPORARY TABLE IF NOT EXISTS s.t (a INT)"
6258        );
6259    }
6260
6261    #[test]
6262    fn or_replace_and_if_not_exists_in_one_statement_is_refused_here_and_not_later() {
6263        // The grammar has room for both and duckdb's has not, so its refusal is a parser error with
6264        // a caret under the `NOT` and this one is a parser error at the same stage. It is the same
6265        // sentence whatever is being created.
6266        for sql in [
6267            "CREATE OR REPLACE TABLE IF NOT EXISTS t (a INT)",
6268            "CREATE OR REPLACE VIEW IF NOT EXISTS v AS SELECT 1",
6269        ] {
6270            let error = parse_ast(sql).unwrap_err().to_string();
6271            assert_eq!(
6272                error,
6273                "Parser Error: Cannot specify both OR REPLACE and IF NOT EXISTS within single \
6274                 create statement"
6275            );
6276        }
6277    }
6278
6279    #[test]
6280    fn a_create_table_as_carries_the_query_and_not_the_types() {
6281        assert_eq!(
6282            round_statement("CREATE TABLE t AS SELECT a FROM u"),
6283            "CREATE TABLE t AS SELECT a FROM u"
6284        );
6285        // The names are the syntax's to say and the types are the query's, so the column
6286        // definitions here have names and no types.
6287        assert_eq!(
6288            round_statement("CREATE TABLE t (x, y) AS SELECT a, b FROM u"),
6289            "CREATE TABLE t (x, y) AS SELECT a, b FROM u"
6290        );
6291    }
6292
6293    #[test]
6294    fn a_create_view_carries_its_body_twice_over() {
6295        assert_eq!(
6296            round_statement("CREATE VIEW v AS SELECT a FROM u"),
6297            "CREATE VIEW v AS SELECT a FROM u"
6298        );
6299        assert_eq!(
6300            round_statement("CREATE OR REPLACE VIEW main.v (x, y) AS SELECT a, b FROM u"),
6301            "CREATE OR REPLACE VIEW main.v (x, y) AS SELECT a, b FROM u"
6302        );
6303        // The text the catalog keeps is the body and only the body, so that binding it again is
6304        // binding a query rather than a `CREATE` statement.
6305        let ast = parse_ast("CREATE VIEW v (x) AS SELECT a FROM u WHERE a > 1").expect("parses");
6306        let Statement::CreateView(index) = ast.statements[0] else {
6307            panic!("not a create view");
6308        };
6309        assert_eq!(ast.string(ast.create_view(index).sql), "SELECT a FROM u WHERE a > 1");
6310    }
6311
6312    #[test]
6313    fn a_drop_view_is_not_a_drop_table() {
6314        assert_eq!(round_statement("DROP VIEW IF EXISTS a, b"), "DROP VIEW IF EXISTS a, b");
6315        assert_eq!(round_statement("DROP TABLE a"), "DROP TABLE a");
6316    }
6317
6318    #[test]
6319    fn a_drop_table_is_a_list_of_qualified_names() {
6320        assert_eq!(round_statement("DROP TABLE t"), "DROP TABLE t");
6321        assert_eq!(round_statement("DROP TABLE IF EXISTS a, b.c"), "DROP TABLE IF EXISTS a, b.c");
6322    }
6323
6324    #[test]
6325    fn dropping_something_that_is_neither_a_table_nor_a_view_is_refused() {
6326        // `TableOrView` covers `MATERIALIZED VIEW` as well, which is not a thing this database has,
6327        // and dropping one as if it were an ordinary view is a wrong answer rather than a missing
6328        // feature.
6329        let error = parse_ast("DROP MATERIALIZED VIEW v").unwrap_err().to_string();
6330        assert!(error.starts_with("Not implemented Error"), "{error}");
6331    }
6332
6333    #[test]
6334    fn both_spellings_of_insert_arrive_at_a_query() {
6335        assert_eq!(
6336            round_statement("INSERT INTO t VALUES (1, 'a'), (2, 'b')"),
6337            "INSERT INTO t VALUES (1, 'a'), (2, 'b')"
6338        );
6339        assert_eq!(
6340            round_statement("INSERT INTO t (a, b) SELECT x, y FROM u"),
6341            "INSERT INTO t (a, b) SELECT x, y FROM u"
6342        );
6343    }
6344
6345    #[test]
6346    fn a_returning_list_is_held_as_a_query_over_the_table_it_writes() {
6347        assert_eq!(
6348            round_statement("INSERT INTO t AS x VALUES (1) RETURNING x.a, a + 1 AS b"),
6349            "INSERT INTO t VALUES (1) RETURNING SELECT x.a, (a Add 1) AS b FROM t AS x"
6350        );
6351        let deleted = round_statement("DELETE FROM t WHERE a = 1 RETURNING *");
6352        assert!(deleted.ends_with(" RETURNING SELECT * FROM t"), "{deleted}");
6353        let updated = round_statement("UPDATE t SET a = 2 RETURNING a");
6354        assert!(updated.ends_with(" RETURNING SELECT a FROM t"), "{updated}");
6355    }
6356
6357    #[test]
6358    fn an_insert_clause_that_changes_the_answer_is_refused() {
6359        for query in [
6360            "INSERT INTO t BY NAME SELECT 1 AS a",
6361            "INSERT INTO t VALUES (1) ON CONFLICT ON CONSTRAINT c DO NOTHING",
6362        ] {
6363            let error = parse_ast(query).unwrap_err().to_string();
6364            assert!(error.starts_with("Not implemented Error"), "{query} gave {error}");
6365        }
6366    }
6367
6368    #[test]
6369    fn a_copy_from_a_file_is_an_insert_from_read_csv() {
6370        let ast = parse_ast(
6371            "COPY name FROM '/data/name.csv' (FORMAT csv, HEADER false, ESCAPE '\\', QUOTE '\"', NULL '')",
6372        )
6373        .unwrap();
6374        let Statement::Insert(index) = ast.statements[0] else { panic!("not an insert") };
6375        assert!(ast.insert(index).copy);
6376        assert_eq!(
6377            round_statement(
6378                "COPY name FROM '/data/name.csv' (FORMAT csv, HEADER false, ESCAPE '\\', QUOTE '\"', NULL '')"
6379            ),
6380            "INSERT INTO name SELECT * FROM read_csv('/data/name.csv', header := FALSE, \
6381             escape := '\\', quote := '\"', nullstr := '')"
6382        );
6383        assert_eq!(
6384            round_statement("COPY t (a, b) FROM 'in.csv' (HEADER, DELIMITER '|')"),
6385            "INSERT INTO t (a, b) SELECT * FROM read_csv('in.csv', header := TRUE, delim := '|')"
6386        );
6387        assert_eq!(
6388            round_statement("COPY t FROM 'in.csv' WITH DELIMITER AS ';' NULL 'NA' CSV HEADER"),
6389            "INSERT INTO t SELECT * FROM read_csv('in.csv', delim := ';', nullstr := 'NA', \
6390             header := TRUE)"
6391        );
6392        assert_eq!(
6393            round_statement("COPY t FROM 'x.parquet'"),
6394            "INSERT INTO t SELECT * FROM read_parquet('x.parquet')"
6395        );
6396        assert!(!{
6397            let ast = parse_ast("INSERT INTO t VALUES (1)").unwrap();
6398            let Statement::Insert(index) = ast.statements[0] else { panic!("not an insert") };
6399            ast.insert(index).copy
6400        });
6401    }
6402
6403    #[test]
6404    fn a_copy_this_does_not_read_is_refused_by_name() {
6405        for (query, message) in [
6406            ("COPY t FROM 'in.csv' (FOO 1)", "Unrecognized option \"foo\" for csv"),
6407            ("COPY t FROM 'in.csv' (SKIP 1)", "the option skip is not supported yet"),
6408            ("COPY t FROM 'in.json' (FORMAT json)", "FORMAT json is not supported yet"),
6409        ] {
6410            let error = parse_ast(query).unwrap_err().to_string();
6411            assert!(error.starts_with("Not implemented Error"), "{query} gave {error}");
6412            assert!(error.contains(message), "{query} gave {error}");
6413        }
6414    }
6415
6416    #[test]
6417    fn copy_to_holds_a_query_and_the_options_as_written() {
6418        for (query, shown) in [
6419            ("COPY t TO 'out.csv'", "COPY (SELECT * FROM t) TO out.csv"),
6420            ("COPY t (a, b) TO 'out.csv'", "COPY (SELECT a, b FROM t) TO out.csv"),
6421            (
6422                "COPY (SELECT 1 AS x) TO 'o.csv' (HEADER false, DELIMITER '|', NULL 'NA')",
6423                "COPY (SELECT 1 AS x) TO o.csv header=false delimiter=| null=NA",
6424            ),
6425            (
6426                "COPY t TO 'o.csv' (FORCE_QUOTE (a, b), QUOTE '''')",
6427                "COPY (SELECT * FROM t) TO o.csv force_quote=(a, b) quote='",
6428            ),
6429            (
6430                "COPY t TO 'o.csv' WITH DELIMITER ';' CSV HEADER",
6431                "COPY (SELECT * FROM t) TO o.csv delimiter=; format=csv header",
6432            ),
6433        ] {
6434            assert_eq!(round_statement(query), shown, "{query}");
6435        }
6436    }
6437
6438    #[test]
6439    fn a_foreign_key_the_pin_refuses_is_refused_with_its_sentence() {
6440        for (query, message) in [
6441            (
6442                "CREATE TABLE t (a INT REFERENCES u (b) ON DELETE CASCADE)",
6443                "FOREIGN KEY constraints cannot use CASCADE, SET NULL or SET DEFAULT",
6444            ),
6445            (
6446                "CREATE TABLE t (a INT, FOREIGN KEY (a) REFERENCES u (b, c))",
6447                "The number of referencing and referenced columns for foreign keys must be the same",
6448            ),
6449        ] {
6450            let error = parse_ast(query).unwrap_err().to_string();
6451            assert!(error.ends_with(message), "{query} gave {error}");
6452        }
6453        let ast = parse_ast(
6454            "CREATE TABLE t (a INT REFERENCES u, b INT, FOREIGN KEY (b) REFERENCES s.v (c))",
6455        )
6456        .unwrap();
6457        let Statement::CreateTable(index) = ast.statements[0] else { panic!("not a create") };
6458        let create = ast.create_table(index);
6459        let lists = |slice| {
6460            ast.name_list(slice)
6461                .iter()
6462                .map(|&names| ast.name(names).collect::<Vec<_>>().join("."))
6463                .collect::<Vec<_>>()
6464        };
6465        assert_eq!(lists(create.foreign), ["a", "b"]);
6466        assert_eq!(lists(create.foreign_tables), ["u", "s.v"]);
6467        assert_eq!(lists(create.foreign_referenced), ["", "c"]);
6468    }
6469
6470    #[test]
6471    fn keys_are_held_in_the_order_written_with_the_primary_one_marked() {
6472        let ast = parse_ast(
6473            "CREATE TABLE t (a INT UNIQUE, b INT PRIMARY KEY, c INT, CONSTRAINT k UNIQUE (c, \"A\"))",
6474        )
6475        .unwrap();
6476        let Statement::CreateTable(index) = ast.statements[0] else { panic!() };
6477        let create = ast.create_table(index);
6478        let keys: Vec<Vec<&str>> =
6479            ast.name_list(create.keys).iter().map(|&names| ast.name(names).collect()).collect();
6480        assert_eq!(keys, [vec!["a"], vec!["b"], vec!["c", "A"]]);
6481        assert_eq!(create.primary, 1);
6482        for (query, message) in [
6483            (
6484                "CREATE TABLE t (i INT PRIMARY KEY, PRIMARY KEY (i))",
6485                "Parser Error: table \"t\" has more than one primary key",
6486            ),
6487            (
6488                "CREATE TABLE t (i INT, UNIQUE (i, I))",
6489                "Parser Error: column \"\"I\"\" appears twice in primary key constraint",
6490            ),
6491        ] {
6492            assert_eq!(parse_ast(query).unwrap_err().to_string(), message);
6493        }
6494    }
6495
6496    #[test]
6497    fn values_is_a_query_on_its_own_and_in_a_from() {
6498        assert_eq!(round("VALUES (1), (2)"), "VALUES (1), (2)");
6499        // Parenthesised it is a subquery whose body is the values, and bare it is a `ValuesRef`.
6500        // Two rules and one meaning, which is the grammar's doing and not something to flatten
6501        // here, because the parenthesised form can carry an order by and the bare one cannot.
6502        assert_eq!(
6503            round("SELECT * FROM (VALUES (1, 2), (3, 4)) t(a, b)"),
6504            "SELECT * FROM (VALUES (1, 2), (3, 4)) AS t"
6505        );
6506        assert_eq!(
6507            round("SELECT * FROM VALUES (1, 2), (3, 4) AS t(a, b)"),
6508            "SELECT * FROM VALUES (1, 2), (3, 4) AS t"
6509        );
6510        // Rows of different widths parse. Saying so wants the column count, which for an insert is
6511        // the table's, so the check belongs to the binder and not here.
6512        assert_eq!(round("VALUES (1), (2, 3)"), "VALUES (1), (2, 3)");
6513    }
6514
6515    #[test]
6516    fn non_recursive_ctes_inline_and_semantic_variants_are_explicit() {
6517        assert_eq!(
6518            round("WITH t AS (SELECT 1 AS x) SELECT x FROM t"),
6519            "SELECT x FROM (SELECT 1 AS x) AS t"
6520        );
6521        assert_eq!(
6522            round("WITH t(x) AS NOT MATERIALIZED (SELECT 1) SELECT x FROM t"),
6523            "SELECT x FROM (SELECT 1) AS t"
6524        );
6525        let query = "WITH RECURSIVE t(x) AS (SELECT 1) SELECT x FROM t";
6526        let error = parse_ast(query).expect_err("the unsupported CTE shape is refused");
6527        assert!(error.to_string().starts_with("Not implemented Error"), "{query}: {error}");
6528    }
6529
6530    /// A plain definition named twice is held, and the same one named once is not.
6531    ///
6532    /// Inlining a definition that two places read means running it twice, so the rule is the count
6533    /// of reads and the word written only settles the cases where somebody wrote one. `NOT
6534    /// MATERIALIZED` is the one that says inline it anyway, and it says so however many times the
6535    /// name is read.
6536    #[test]
6537    fn a_plain_cte_read_twice_is_held_and_one_read_once_is_inlined() {
6538        assert_eq!(
6539            round("WITH t AS (SELECT 1 AS x) SELECT * FROM t a, t b"),
6540            "WITH t AS MATERIALIZED (SELECT 1 AS x) SELECT * FROM t AS a, t AS b"
6541        );
6542        assert_eq!(
6543            round("WITH t AS (SELECT 1 AS x) SELECT x FROM t"),
6544            "SELECT x FROM (SELECT 1 AS x) AS t"
6545        );
6546        assert_eq!(
6547            round("WITH t AS NOT MATERIALIZED (SELECT 1 AS x) SELECT * FROM t a, t b"),
6548            "SELECT * FROM (SELECT 1 AS x) AS a, (SELECT 1 AS x) AS b"
6549        );
6550        // A name a later definition reads is read, since that definition runs too.
6551        assert_eq!(
6552            round("WITH t AS (SELECT 1 AS x), u AS (SELECT x FROM t) SELECT x FROM t"),
6553            "WITH t AS MATERIALIZED (SELECT 1 AS x) SELECT x FROM t"
6554        );
6555        // Qualified, so it is not a read of the definition and there is only the one.
6556        assert_eq!(
6557            round("WITH t AS (SELECT 1 AS x) SELECT * FROM t a, main.t b"),
6558            "SELECT * FROM (SELECT 1 AS x) AS a, main.t AS b"
6559        );
6560    }
6561
6562    /// A definition written inside a subquery is inlined however many times it is read.
6563    ///
6564    /// The rows of a held definition are produced once for the whole statement, and a definition
6565    /// written inside a subquery can name a column of the query around it, which is an answer per
6566    /// outer row. Telling the two apart is a question about resolved columns, so what is asked here
6567    /// is the question this pass can answer: whether there is any query around it at all.
6568    #[test]
6569    fn a_cte_written_inside_a_subquery_is_inlined_however_often_it_is_read() {
6570        assert_eq!(
6571            round("SELECT * FROM (WITH t AS (SELECT 1 AS x) SELECT * FROM t a, t b) c"),
6572            "SELECT * FROM (SELECT * FROM (SELECT 1 AS x) AS a, (SELECT 1 AS x) AS b) AS c"
6573        );
6574        assert_eq!(
6575            round("WITH o AS (WITH i AS (SELECT 1 AS x) SELECT * FROM i a, i b) SELECT * FROM o"),
6576            "SELECT * FROM (SELECT * FROM (SELECT 1 AS x) AS a, (SELECT 1 AS x) AS b) AS o"
6577        );
6578    }
6579
6580    /// A name a definition further in takes over is left alone.
6581    ///
6582    /// Which of the two definitions a read means is a question about scopes, and the count here is
6583    /// a count of spellings, so a query that writes the name twice gets what every query got before
6584    /// the count existed.
6585    #[test]
6586    fn a_plain_cte_whose_name_is_written_again_further_in_is_inlined() {
6587        assert_eq!(
6588            round(
6589                "WITH t AS (SELECT 1 AS x) SELECT * FROM t a, \
6590                 (WITH t AS (SELECT 2 AS x) SELECT x FROM t) b"
6591            ),
6592            "SELECT * FROM (SELECT 1 AS x) AS a, (SELECT x FROM (SELECT 2 AS x) AS t) AS b"
6593        );
6594    }
6595
6596    /// A materialised one keeps its definition, because putting it in two places runs it twice.
6597    #[test]
6598    fn a_materialized_cte_stays_a_definition_and_its_references_stay_references() {
6599        assert_eq!(
6600            round("WITH t AS MATERIALIZED (SELECT 1 AS x) SELECT x FROM t"),
6601            "WITH t AS MATERIALIZED (SELECT 1 AS x) SELECT x FROM t"
6602        );
6603        assert_eq!(
6604            round("WITH t(y) AS MATERIALIZED (SELECT 1) SELECT y FROM t"),
6605            "WITH t(y) AS MATERIALIZED (SELECT 1) SELECT y FROM t"
6606        );
6607        // Two references are two sources naming one definition, which is the whole point of the
6608        // word: the inlined form above would be two copies of the query.
6609        assert_eq!(
6610            round("WITH t AS MATERIALIZED (SELECT 1 AS x) SELECT * FROM t a, t b"),
6611            "WITH t AS MATERIALIZED (SELECT 1 AS x) SELECT * FROM t AS a, t AS b"
6612        );
6613        // The inner name shadows the outer one, which is decided here and nowhere later.
6614        assert_eq!(
6615            round(
6616                "WITH t AS MATERIALIZED (SELECT 1 AS x) SELECT (WITH t AS (SELECT 2 AS x) \
6617                 SELECT x FROM t) AS inner"
6618            ),
6619            "WITH t AS MATERIALIZED (SELECT 1 AS x) SELECT (SELECT x FROM (SELECT 2 AS x) AS t) \
6620             AS inner"
6621        );
6622        // A definition may read one written before it, and it is the definition that is read
6623        // rather than a second copy of the query behind it.
6624        assert_eq!(
6625            round(
6626                "WITH a AS MATERIALIZED (SELECT 1 AS x), b AS MATERIALIZED (SELECT x + 1 AS y \
6627                 FROM a) SELECT y FROM b"
6628            ),
6629            "WITH a AS MATERIALIZED (SELECT 1 AS x) WITH b AS MATERIALIZED (SELECT (x Add 1) \
6630             AS y FROM a) SELECT y FROM b"
6631        );
6632    }
6633
6634    /// `DESCRIBE` is a query body, and the two spellings that name something become a star over it.
6635    ///
6636    /// Naming a table is not a shortcut for the query. On the reference binary `DESCRIBE t` and
6637    /// `DESCRIBE SELECT * FROM t` print the same six columns and the same rows, down to the `NO` on
6638    /// a column that refuses nulls, so rewriting one into the other costs nothing and leaves the
6639    /// binder with one case instead of three. A file name goes down the same path as a table name
6640    /// because a bare string in a `FROM` clause is already a name the replacement scan picks up.
6641    #[test]
6642    fn describe_rewrites_a_name_into_a_star_over_it() {
6643        assert_eq!(round("DESCRIBE SELECT 1 AS a"), "DESCRIBE SELECT 1 AS a");
6644        assert_eq!(round("DESCRIBE t"), "DESCRIBE SELECT * FROM t");
6645        assert_eq!(round("DESC t"), "DESCRIBE SELECT * FROM t");
6646        assert_eq!(round("DESCRIBE 'x.parquet'"), "DESCRIBE SELECT * FROM x.parquet");
6647        // A body and not a statement kind, so it nests both ways with no rule of its own.
6648        assert_eq!(
6649            round("SELECT column_name FROM (DESCRIBE SELECT 1 AS a)"),
6650            "SELECT column_name FROM (DESCRIBE SELECT 1 AS a)"
6651        );
6652        assert_eq!(round("DESCRIBE DESCRIBE SELECT 1 AS a"), "DESCRIBE DESCRIBE SELECT 1 AS a");
6653    }
6654
6655    /// `SUMMARIZE` shares both of `DESCRIBE`'s grammar rules and is a different statement.
6656    ///
6657    /// It reads every row and returns one row per column carrying the min, the max, the count and
6658    /// the approximate distinct count, so none of it falls out of the `DESCRIBE` path. The word is
6659    /// the only thing in the tree that tells the two apart, which is why the transform looks at it
6660    /// rather than trusting the rule name it arrived under.
6661    #[test]
6662    fn summarize_is_refused_even_though_it_parses_as_a_describe() {
6663        for query in ["SUMMARIZE t", "SUMMARIZE SELECT 1"] {
6664            let error = parse_ast(query).expect_err("summarize is not implemented");
6665            let message = error.to_string();
6666            assert!(message.starts_with("Not implemented Error"), "{query} failed with {message}");
6667        }
6668    }
6669
6670    #[test]
6671    fn every_statement_in_the_corpus_gets_a_defined_answer() {
6672        // The point of the test is the word defined. Half of these are statement kinds and
6673        // clauses this milestone does not cover, and the requirement is not that they work, it is
6674        // that they fail by saying so. A panic, a silently dropped clause or an internal error
6675        // would each be a different bug and all three would be invisible without this.
6676        let mut done = 0;
6677        for query in CORPUS {
6678            match parse_ast(query) {
6679                Ok(ast) => {
6680                    assert_eq!(ast.statements.len(), 1, "{query}");
6681                    done += 1;
6682                }
6683                Err(error) => {
6684                    let message = error.to_string();
6685                    assert!(
6686                        message.starts_with("Not implemented Error"),
6687                        "{query} failed with {message}, which is not a not-implemented error"
6688                    );
6689                }
6690            }
6691        }
6692        // Not an assertion about the right number. It is a ratchet: this only moves up, and the
6693        // day it moves down somebody has taken a construct out without meaning to.
6694        assert!(done >= 31, "only {done} of the corpus transforms, which is fewer than it was");
6695    }
6696
6697    #[test]
6698    fn the_ast_is_far_smaller_than_the_parse_tree() {
6699        let query = CORPUS[4];
6700        let tree = parse(query).unwrap();
6701        let ast = parse_ast(query).unwrap();
6702        // The twenty precedence levels are the difference. Every one of them is a node in the
6703        // parse tree for every expression at every depth, and none of them survives into the AST.
6704        assert!(
6705            ast.node_count() * 20 < tree.arena_len(),
6706            "{} ast nodes against {} parse nodes",
6707            ast.node_count(),
6708            tree.arena_len()
6709        );
6710    }
6711
6712    #[test]
6713    fn precedence_comes_out_of_the_chain_and_into_the_tree() {
6714        assert_eq!(round("SELECT 1 + 2 * 3"), "SELECT (1 Add (2 Multiply 3))");
6715        assert_eq!(round("SELECT (1 + 2) * 3"), "SELECT ((1 Add 2) Multiply 3)");
6716        assert_eq!(round("SELECT 1 + 2 + 3"), "SELECT ((1 Add 2) Add 3)");
6717        assert_eq!(round("SELECT 1 - 2 - 3"), "SELECT ((1 Subtract 2) Subtract 3)");
6718        assert_eq!(
6719            round("SELECT a OR b AND c"),
6720            "SELECT (a Or (b And c))",
6721            "and binds tighter than or"
6722        );
6723    }
6724
6725    #[test]
6726    fn a_double_negation_is_two_nodes_and_not_none() {
6727        // Folding it would be an optimizer decision and this is not the optimizer. It also would
6728        // not be safe in general: `NOT NOT x` on a null is still null and on a non boolean it is
6729        // still an error, and both of those have to survive to the binder to be reported.
6730        assert_eq!(round("SELECT NOT NOT a"), "SELECT (Not (Not a))");
6731    }
6732
6733    #[test]
6734    fn a_parenthesised_single_expression_is_not_a_row() {
6735        assert_eq!(round("SELECT (a)"), "SELECT a");
6736        assert_eq!(round("SELECT (a, b)"), "SELECT ROW(a, b)");
6737    }
6738
6739    #[test]
6740    fn a_bracketed_list_is_a_list_of_however_many_items_were_written() {
6741        // One item is a list of one, which is where this parts company with the parenthesised form
6742        // above: `(a)` is `a` and `[a]` is a list, because the brackets are what say list.
6743        assert_eq!(round("SELECT [a]"), "SELECT [a]");
6744        assert_eq!(round("SELECT [1, 2, 3]"), "SELECT [1, 2, 3]");
6745        assert_eq!(round("SELECT []"), "SELECT []");
6746        assert_eq!(round("SELECT ['a.parquet', 'b.parquet']"), "SELECT ['a.parquet', 'b.parquet']");
6747    }
6748
6749    #[test]
6750    fn a_parameter_carries_its_identifier_however_it_was_written() {
6751        assert_eq!(round("SELECT $1"), "SELECT $1");
6752        assert_eq!(round("SELECT ?1"), "SELECT $1");
6753        assert_eq!(round("SELECT $name"), "SELECT $name");
6754        // A bare question mark is numbered by where it is, and the counting is its own, so a later
6755        // `$2` does not push the first one along. This is duckdb v1.4.1, which prints `$1 + $2`.
6756        assert_eq!(round("SELECT ? + $2"), "SELECT ($1 Add $2)");
6757        assert_eq!(round("SELECT ?, ?, ?"), "SELECT $1, $2, $3");
6758    }
6759
6760    #[test]
6761    fn the_parameters_of_a_statement_are_listed_once_each_in_written_order() {
6762        let ast = parse_ast("SELECT $b, $a, $b WHERE $a").expect("parses");
6763        assert_eq!(ast.parameters(), vec!["b", "a"]);
6764        assert!(parse_ast("SELECT 1").expect("parses").parameters().is_empty());
6765    }
6766
6767    #[test]
6768    fn the_three_ways_to_write_an_alias_all_arrive() {
6769        assert_eq!(round("SELECT a AS b"), "SELECT a AS b");
6770        assert_eq!(round("SELECT a b"), "SELECT a AS b");
6771        assert_eq!(round("SELECT b: a"), "SELECT a AS b");
6772        assert_eq!(round("SELECT a"), "SELECT a", "and no alias when none was written");
6773    }
6774
6775    #[test]
6776    fn a_from_with_no_select_selects_everything() {
6777        // DuckDB's own shorthand. Inventing the star here rather than in the binder means the
6778        // binder never has to know that the clause it is looking at was the one that was missing.
6779        assert_eq!(round("FROM t"), "SELECT * FROM t");
6780        assert_eq!(round("FROM t SELECT a"), "SELECT a FROM t");
6781    }
6782
6783    #[test]
6784    fn joins_nest_to_the_left() {
6785        assert_eq!(
6786            round("SELECT * FROM a JOIN b ON a.i = b.i LEFT JOIN c USING (k)"),
6787            "SELECT * FROM ((a Inner JOIN b ON (a.i Eq b.i)) Left JOIN c USING (k))"
6788        );
6789        assert_eq!(
6790            round("SELECT * FROM a NATURAL JOIN b"),
6791            "SELECT * FROM (a NATURAL Inner JOIN b)"
6792        );
6793        assert_eq!(round("SELECT * FROM a CROSS JOIN b"), "SELECT * FROM (a Cross JOIN b)");
6794        assert_eq!(
6795            round("SELECT * FROM a POSITIONAL JOIN b"),
6796            "SELECT * FROM (a Positional JOIN b)"
6797        );
6798        assert_eq!(round("SELECT * FROM a, b"), "SELECT * FROM a, b", "a comma is not a join node");
6799    }
6800
6801    #[test]
6802    fn a_qualified_name_keeps_its_parts_however_it_was_spelled() {
6803        // Five grammar rules can produce a column reference and they disagree about which
6804        // component is a schema and which is a table. None of that is decidable without the
6805        // catalog, so the AST holds the parts and the binder decides.
6806        assert_eq!(round("SELECT a"), "SELECT a");
6807        assert_eq!(round("SELECT t.a"), "SELECT t.a");
6808        assert_eq!(round("SELECT s.t.a"), "SELECT s.t.a");
6809        assert_eq!(round("SELECT c.s.t.a"), "SELECT c.s.t.a");
6810        assert_eq!(round("SELECT * FROM s.t"), "SELECT * FROM s.t");
6811    }
6812
6813    #[test]
6814    fn a_star_can_be_qualified() {
6815        assert_eq!(round("SELECT *"), "SELECT *");
6816        assert_eq!(round("SELECT t.*"), "SELECT t.*");
6817        assert_eq!(round("SELECT s.t.*"), "SELECT s.t.*");
6818    }
6819
6820    #[test]
6821    fn a_quoted_identifier_keeps_its_case_and_loses_its_quotes() {
6822        // DuckDB does not fold identifier case at any point, quoted or not, which the tokenizer
6823        // work established by reading the source. So the only thing to do here is take the quotes
6824        // off and resolve the doubled ones.
6825        let ast = parse_ast("SELECT \"Mixed Case\", \"a\"\"b\"").unwrap();
6826        assert_eq!(ast.strings[0], "Mixed Case");
6827        assert_eq!(ast.strings[1], "a\"b");
6828    }
6829
6830    #[test]
6831    fn a_string_literal_is_decoded_and_adjacent_ones_are_joined() {
6832        assert_eq!(round("SELECT 'it''s'"), "SELECT 'it's'");
6833        assert_eq!(round("SELECT 'a'\n'b'"), "SELECT 'ab'", "the standard's adjacency rule");
6834    }
6835
6836    /// Per #276, where the tag and the dollars were coming through as part of the value.
6837    #[test]
6838    fn a_dollar_quoted_string_loses_its_dollars_and_its_tag() {
6839        assert_eq!(round("SELECT $$dollar quoted$$"), "SELECT 'dollar quoted'");
6840        assert_eq!(round("SELECT $tag$body$tag$"), "SELECT 'body'");
6841        assert_eq!(round("SELECT $$$$"), "SELECT ''", "an empty tag and an empty body");
6842        // Nothing in the body is escaped, which is what the spelling is for, so a quote is a quote
6843        // and a dollar that is not the closing tag is a dollar.
6844        assert_eq!(round("SELECT $tag$it''s $other$ fine$tag$"), "SELECT 'it''s $other$ fine'");
6845        // An unterminated one has no closing tag to take off and keeps every byte it was given.
6846        assert_eq!(round("SELECT $$open"), "SELECT '$$open'");
6847    }
6848
6849    /// Per #329, where every prefixed spelling came back as the source text it was written as.
6850    ///
6851    /// The escapes are the ones the pinned binary takes, read off it one at a time. The two that
6852    /// are easy to get wrong are `\v`, which is not an escape and is the letter, and `\u`, which
6853    /// wants all four digits and otherwise drops the backslash and keeps the letter.
6854    #[test]
6855    fn an_escape_string_resolves_its_backslashes() {
6856        assert_eq!(round("SELECT E'a\\nb'"), "SELECT 'a\nb'");
6857        assert_eq!(round("SELECT e'a\\tb'"), "SELECT 'a\tb'", "the prefix is a letter, not a name");
6858        assert_eq!(round("SELECT E'a\\rb'"), "SELECT 'a\rb'");
6859        assert_eq!(round("SELECT E'a\\bb'"), "SELECT 'a\u{8}b'");
6860        assert_eq!(round("SELECT E'a\\fb'"), "SELECT 'a\u{c}b'");
6861        assert_eq!(round("SELECT E'a\\\\b'"), "SELECT 'a\\b'");
6862        assert_eq!(round("SELECT E'a\\'b'"), "SELECT 'a'b'", "a quote, the same as ''");
6863        assert_eq!(round("SELECT E'a''b'"), "SELECT 'a'b'", "and '' still means a quote here");
6864        // A backslash in front of anything else is dropped and the character is kept, which is what
6865        // makes \v the letter v.
6866        assert_eq!(round("SELECT E'a\\vb'"), "SELECT 'avb'");
6867        assert_eq!(round("SELECT E'a\\qb'"), "SELECT 'aqb'");
6868    }
6869
6870    /// The escapes that write a byte rather than a character, and the one that writes a character.
6871    #[test]
6872    fn a_numeric_escape_writes_the_byte_or_the_character_it_names() {
6873        assert_eq!(round("SELECT E'\\x41'"), "SELECT 'A'");
6874        assert_eq!(round("SELECT E'\\x4142'"), "SELECT 'A42'", "two digits at the most");
6875        assert_eq!(
6876            round("SELECT E'a\\x'"),
6877            "SELECT 'ax'",
6878            "and one at the least, or it is a letter"
6879        );
6880        assert_eq!(round("SELECT E'\\101'"), "SELECT 'A'");
6881        assert_eq!(round("SELECT E'\\1011'"), "SELECT 'A1'", "three digits at the most");
6882        assert_eq!(round("SELECT E'\\8'"), "SELECT '8'", "8 is not an octal digit");
6883        // Bytes and not characters, so two of them make one character and one of them makes none.
6884        assert_eq!(round("SELECT E'\\xc3\\xa9'"), "SELECT 'é'");
6885        assert_eq!(round("SELECT E'\\u00e9'"), "SELECT 'é'");
6886        assert_eq!(round("SELECT E'a\\u41'"), "SELECT 'au41'", "four digits or it is a letter");
6887        assert_eq!(round("SELECT E'a\\uZZZZ'"), "SELECT 'auZZZZ'");
6888        assert_eq!(
6889            round("SELECT E'\\ud83d\\ude00'"),
6890            "SELECT 'ud83dude00'",
6891            "surrogates are not it"
6892        );
6893    }
6894
6895    /// The two ways an escape string is not a string at all, both with the message upstream gives.
6896    #[test]
6897    fn an_escape_string_that_is_not_a_string_raises() {
6898        let error = parse_ast("SELECT E'a\\x00'").unwrap_err().to_string();
6899        assert_eq!(error, "Parser Error: Null character not permitted in escape string literal");
6900        let error = parse_ast("SELECT E'a\\377'").unwrap_err().to_string();
6901        assert_eq!(
6902            error,
6903            "Parser Error: Invalid UTF-8 in escape string literal at byte offset 1: byte mismatch",
6904            "the offset is where the bytes stop being a string, not where the escape was written"
6905        );
6906    }
6907
6908    /// The other prefixes, all of them measured against the pinned binary rather than assumed.
6909    #[test]
6910    fn the_other_string_prefixes_are_what_upstream_makes_of_them() {
6911        // N is the string and a cast of it to VARCHAR, which is where the column name comes from.
6912        assert_eq!(round("SELECT N'abc'"), "SELECT CAST('abc' AS VARCHAR)");
6913        assert_eq!(round("SELECT n'abc'"), "SELECT CAST('abc' AS VARCHAR)");
6914        // B is not a bit string. It is the letter b in front of the body, untouched.
6915        assert_eq!(round("SELECT B'101'"), "SELECT 'b101'");
6916        assert_eq!(round("SELECT b'abc'"), "SELECT 'babc'");
6917        assert_eq!(round("SELECT B''"), "SELECT 'b'", "an empty one is the letter on its own");
6918    }
6919
6920    /// X is the prefix that is not a string at all, per #329.
6921    ///
6922    /// What is kept is the text the blob prints as, because that is the text the column is named
6923    /// after and the text the cast reads the bytes back from, and one text that does both is one
6924    /// text that cannot disagree with itself.
6925    #[test]
6926    fn a_hex_string_is_a_blob_and_not_a_string() {
6927        assert_eq!(round("SELECT x'4142'"), "SELECT 'AB'::BLOB");
6928        assert_eq!(round("SELECT X'4142'"), "SELECT 'AB'::BLOB");
6929        assert_eq!(round("SELECT x'ff41'"), "SELECT '\\xFFA'::BLOB", "a byte that does not print");
6930        assert_eq!(round("SELECT x''"), "SELECT ''::BLOB", "an empty one is an empty blob");
6931        // A quote and a backslash are bytes that do not print either, which is what keeps the text
6932        // something the cast can read back.
6933        assert_eq!(round("SELECT x'2741'"), "SELECT '\\x27A'::BLOB");
6934        assert_eq!(round("SELECT x'5c7834314141'"), "SELECT '\\x5Cx41AA'::BLOB");
6935        // An odd number of digits is a parser error and a digit that is not one is not, because
6936        // upstream writes the pairs out without looking at them and the cast is what looks.
6937        let error = parse_ast("SELECT x'4'").unwrap_err().to_string();
6938        assert_eq!(
6939            error,
6940            "Parser Error: Hex string literal must have an even number of hex digits"
6941        );
6942        assert_eq!(round("SELECT x'41zz'"), "SELECT '\\x41\\xzz'::BLOB");
6943    }
6944
6945    #[test]
6946    fn the_null_and_boolean_tests_are_postfix_unary_operators() {
6947        assert_eq!(round("SELECT x IS NULL"), "SELECT (IsNull x)");
6948        assert_eq!(round("SELECT x IS NOT NULL"), "SELECT (IsNotNull x)");
6949        assert_eq!(round("SELECT x ISNULL"), "SELECT (IsNull x)");
6950        assert_eq!(round("SELECT x NOTNULL"), "SELECT (IsNotNull x)");
6951        assert_eq!(round("SELECT x IS TRUE"), "SELECT (IsTrue x)");
6952        assert_eq!(round("SELECT x IS NOT FALSE"), "SELECT (IsNotFalse x)");
6953        assert_eq!(round("SELECT x IS DISTINCT FROM y"), "SELECT (x IsDistinctFrom y)");
6954        assert_eq!(round("SELECT x IS NOT DISTINCT FROM y"), "SELECT (x IsNotDistinctFrom y)");
6955    }
6956
6957    #[test]
6958    fn the_like_family_folds_its_negation_into_the_operator() {
6959        assert_eq!(round("SELECT x LIKE 'a'"), "SELECT (x Like 'a')");
6960        assert_eq!(round("SELECT x NOT LIKE 'a'"), "SELECT (x NotLike 'a')");
6961        assert_eq!(round("SELECT x ILIKE 'a'"), "SELECT (x ILike 'a')");
6962        assert_eq!(round("SELECT x ~~ 'a'"), "SELECT (x Like 'a')", "the operator spelling");
6963        assert_eq!(round("SELECT x !~~ 'a'"), "SELECT (x NotLike 'a')");
6964        assert_eq!(round("SELECT x SIMILAR TO 'a'"), "SELECT (x SimilarTo 'a')");
6965        // Glob has no negated operator to fold into, so the negation stays where it was written.
6966        assert_eq!(round("SELECT x NOT GLOB 'a'"), "SELECT (Not (x Glob 'a'))");
6967    }
6968
6969    #[test]
6970    fn between_and_in_carry_their_negation_as_a_flag() {
6971        assert_eq!(round("SELECT x BETWEEN 1 AND 2"), "SELECT (x BETWEEN 1 AND 2)");
6972        assert_eq!(round("SELECT x NOT BETWEEN 1 AND 2"), "SELECT (NOT x BETWEEN 1 AND 2)");
6973        assert_eq!(round("SELECT x IN (1, 2)"), "SELECT (x IN [1, 2])");
6974        assert_eq!(round("SELECT x NOT IN (1, 2)"), "SELECT (NOT x IN [1, 2])");
6975    }
6976
6977    #[test]
6978    fn both_spellings_of_a_cast_are_the_same_node() {
6979        assert_eq!(round("SELECT CAST(x AS BIGINT)"), "SELECT CAST(x AS BIGINT)");
6980        assert_eq!(round("SELECT x::BIGINT"), "SELECT CAST(x AS BIGINT)");
6981        assert_eq!(round("SELECT TRY_CAST(x AS BIGINT)"), "SELECT TRY_CAST(x AS BIGINT)");
6982        assert_eq!(
6983            round("SELECT x::DECIMAL(18, 3)"),
6984            "SELECT CAST(x AS DECIMAL(18, 3))",
6985            "the type is kept as text because parsing it is the type system's job"
6986        );
6987    }
6988
6989    #[test]
6990    fn a_typed_literal_is_a_third_spelling_of_the_same_cast() {
6991        assert_eq!(round("SELECT DATE '1995-09-01'"), "SELECT CAST('1995-09-01' AS DATE)");
6992        assert_eq!(
6993            round("SELECT date '1995-09-01'"),
6994            "SELECT CAST('1995-09-01' AS date)",
6995            "the type is kept as written, the same as it is in the other two spellings"
6996        );
6997        assert_eq!(
6998            round("SELECT TIMESTAMP '2020-01-01 03:04:05'"),
6999            "SELECT CAST('2020-01-01 03:04:05' AS TIMESTAMP)"
7000        );
7001        assert_eq!(
7002            round("SELECT DECIMAL(5, 2) '1.5'"),
7003            "SELECT CAST('1.5' AS DECIMAL(5, 2))",
7004            "any type the cast takes is a typed literal, parameters and all"
7005        );
7006        assert_eq!(
7007            round("SELECT VARCHAR 'hi' FROM t"),
7008            "SELECT CAST('hi' AS VARCHAR) FROM t",
7009            "including the ones where the cast has nothing to do"
7010        );
7011    }
7012
7013    #[test]
7014    fn a_case_keeps_its_arms_in_order() {
7015        assert_eq!(
7016            round("SELECT CASE WHEN a THEN 1 WHEN b THEN 2 ELSE 3 END"),
7017            "SELECT CASE - WHEN a THEN 1 WHEN b THEN 2 ELSE 3 END"
7018        );
7019        assert_eq!(
7020            round("SELECT CASE x WHEN 1 THEN 'a' END"),
7021            "SELECT CASE x WHEN 1 THEN 'a' ELSE - END",
7022            "a simple case keeps the operand and a missing else is not an implicit null yet"
7023        );
7024    }
7025
7026    #[test]
7027    fn a_field_access_and_a_method_call_are_ordinary_function_calls() {
7028        // Which is what DuckDB makes of them too. Giving each its own AST node would mean the
7029        // binder needs a rule for something the function resolver already handles.
7030        assert_eq!(round("SELECT (f(x)).y"), "SELECT struct_extract(f(x), 'y')");
7031        assert_eq!(round("SELECT a[1]"), "SELECT array_extract(a, 1)");
7032    }
7033
7034    /// The four ways of leaving a bound out, all of which upstream fills in the same way.
7035    #[test]
7036    fn a_range_gets_the_bounds_the_query_left_out() {
7037        assert_eq!(round("SELECT a[1:2]"), "SELECT array_slice(a, 1, 2)");
7038        assert_eq!(round("SELECT a[:2]"), "SELECT array_slice(a, 1, 2)");
7039        assert_eq!(round("SELECT a[2:]"), "SELECT array_slice(a, 2, -1)");
7040        assert_eq!(round("SELECT a[:]"), "SELECT array_slice(a, 1, -1)");
7041        // `EndSliceMinus`, which is a range with no end rather than a subtraction of nothing.
7042        assert_eq!(round("SELECT a[1:-]"), "SELECT array_slice(a, 1, -1)");
7043        assert_eq!(round("SELECT a[1:2:3]"), "SELECT array_slice(a, 1, 2, 3)");
7044        // A step that was written and left empty, which upstream fills with a list so that the call
7045        // fails to bind. Answering a row here would be answering where the reference refuses.
7046        assert_eq!(round("SELECT a[1:2:]"), "SELECT array_slice(a, 1, 2, [])");
7047    }
7048
7049    /// `[]` is the one subscript the parser takes and the transformer refuses, in upstream's words.
7050    #[test]
7051    fn an_empty_subscript_is_not_a_subscript() {
7052        let error = parse_ast("SELECT a[]").expect_err("an empty subscript");
7053        assert_eq!(error.message(), "Empty subscript '[]' is not allowed");
7054    }
7055
7056    /// A rule that wrote a keyword is not a rule that said nothing, however few children it has.
7057    /// Per #313.
7058    #[test]
7059    fn a_keyword_is_not_stepped_through_on_the_way_to_its_one_argument() {
7060        for (sql, rule) in [
7061            ("SELECT unpack([1])", "UnpackExpression"),
7062            ("SELECT columns('a')", "ColumnsExpression"),
7063        ] {
7064            let error = parse_ast(sql).expect_err(sql);
7065            assert!(error.message().ends_with(rule), "{sql}: {error}");
7066        }
7067        // Grouping brackets really do say nothing, and that is the one rule of this shape that is
7068        // stepped through rather than refused.
7069        assert_eq!(round("SELECT (1 + 2) * 3"), "SELECT ((1 Add 2) Multiply 3)");
7070        assert_eq!(round("SELECT -(7)"), "SELECT (Negate 7)");
7071    }
7072
7073    /// The three spellings of a null check, two of which are their own grammar rule. Per #306.
7074    #[test]
7075    fn the_null_checks_are_calls_by_the_names_duckdb_prints() {
7076        // The keyword is the name, so the call is written with the canonical spelling of it whichever
7077        // case the query used. What the column is called is the binder's to decide.
7078        assert_eq!(round("SELECT COALESCE(a, b, 1)"), "SELECT coalesce(a, b, 1)");
7079        assert_eq!(round("SELECT coalesce(a)"), "SELECT coalesce(a)");
7080        assert_eq!(round("SELECT NULLIF(a, 1)"), "SELECT nullif(a, 1)");
7081        // `IFNULL` is a plain call that upstream's parser turns into the operator, qualifier and all.
7082        assert_eq!(round("SELECT ifnull(a, 1)"), "SELECT coalesce(a, 1)");
7083        assert_eq!(round("SELECT main.ifnull(a, 1)"), "SELECT coalesce(a, 1)");
7084        let error = parse_ast("SELECT ifnull(a)").expect_err("one argument to ifnull");
7085        assert_eq!(error.message(), "Wrong number of arguments to IFNULL.");
7086        let error = parse_ast("SELECT ifnull(a, b, c)").expect_err("three arguments to ifnull");
7087        assert_eq!(error.message(), "Wrong number of arguments to IFNULL.");
7088    }
7089
7090    /// The four string functions with a grammar rule of their own, written back out as the calls
7091    /// DuckDB's parser writes them as. Per #314.
7092    #[test]
7093    fn the_string_keywords_are_the_calls_duckdb_prints() {
7094        assert_eq!(round("SELECT substring(s, 2, 3)"), "SELECT substring(s, 2, 3)");
7095        assert_eq!(round("SELECT SUBSTRING(s FROM 2 FOR 3)"), "SELECT substring(s, 2, 3)");
7096        assert_eq!(round("SELECT substring(s FROM 2)"), "SELECT substring(s, 2)");
7097        // The `FOR` on its own is three arguments and not two, with the start filled in.
7098        assert_eq!(round("SELECT substring(s FOR 3)"), "SELECT substring(s, 1, 3)");
7099        // The haystack comes first in the call and second in the query.
7100        assert_eq!(round("SELECT position('c' IN s)"), "SELECT position(s, 'c')");
7101        assert_eq!(round("SELECT trim(s)"), "SELECT trim(s)");
7102        assert_eq!(round("SELECT trim(BOTH 'x' FROM s)"), "SELECT trim(s, 'x')");
7103        assert_eq!(round("SELECT trim(BOTH FROM s)"), "SELECT trim(s)");
7104        assert_eq!(round("SELECT trim(s, 'xy')"), "SELECT trim(s, 'xy')");
7105        // A direction is a different function and not a different argument.
7106        assert_eq!(round("SELECT trim(LEADING FROM s)"), "SELECT ltrim(s)");
7107        assert_eq!(round("SELECT trim(TRAILING FROM s)"), "SELECT rtrim(s)");
7108        assert_eq!(round("SELECT trim(LEADING 'x' FROM s)"), "SELECT ltrim(s, 'x')");
7109        assert_eq!(round("SELECT trim(TRAILING 'x' FROM s)"), "SELECT rtrim(s, 'x')");
7110        assert_eq!(
7111            round("SELECT overlay(s PLACING 'X' FROM 2 FOR 1)"),
7112            "SELECT overlay(s, 'X', 2, 1)"
7113        );
7114        assert_eq!(round("SELECT overlay(s PLACING 'X' FROM 2)"), "SELECT overlay(s, 'X', 2)");
7115        assert_eq!(round("SELECT overlay(s, 'X', 2, 1)"), "SELECT overlay(s, 'X', 2, 1)");
7116    }
7117
7118    #[test]
7119    fn an_aggregate_keeps_its_distinct() {
7120        assert_eq!(round("SELECT count(*)"), "SELECT count(*)");
7121        assert_eq!(round("SELECT count(DISTINCT x)"), "SELECT count(DISTINCT x)");
7122        assert_eq!(round("SELECT count(ALL x)"), "SELECT count(x)");
7123        assert_eq!(round("SELECT main.count(x)"), "SELECT main.count(x)");
7124    }
7125
7126    #[test]
7127    fn a_call_keeps_the_filter_it_was_written_with_and_the_word_where_is_optional() {
7128        // `FilterClauseContents <- 'WHERE'? Expression`, so both spellings parse and both land on
7129        // the same predicate. Which names are allowed to carry one is not a question the parser
7130        // can answer, so it keeps one wherever it was written and lets the binder refuse it.
7131        assert_eq!(round("SELECT sum(x) FILTER (WHERE y > 1)"), "SELECT sum(x) FILTER [(y Gt 1)]");
7132        assert_eq!(round("SELECT sum(x) FILTER (y > 1)"), "SELECT sum(x) FILTER [(y Gt 1)]");
7133        assert_eq!(round("SELECT count(*) FILTER (WHERE b)"), "SELECT count(*) FILTER [b]");
7134        assert_eq!(
7135            round("SELECT sum(DISTINCT x) FILTER (WHERE b)"),
7136            "SELECT sum(DISTINCT x) FILTER [b]"
7137        );
7138        assert_eq!(round("SELECT abs(x) FILTER (WHERE b)"), "SELECT abs(x) FILTER [b]");
7139    }
7140
7141    /// The `FILTER` goes before the `OVER`, which is a rule of the grammar and not of the binder.
7142    #[test]
7143    fn a_window_call_carries_its_filter_in_front_of_its_over() {
7144        assert_eq!(
7145            round("SELECT sum(x) FILTER (WHERE b) OVER ()"),
7146            "SELECT sum(x) FILTER [b] OVER [] [] [Range UnboundedPreceding CurrentRow NoOthers]"
7147        );
7148    }
7149
7150    #[test]
7151    fn the_modifiers_hang_off_the_query_and_not_off_the_select() {
7152        // `a UNION b ORDER BY x` sorts the union. Putting the order by on the select would have
7153        // made that unrepresentable, which is why the grammar puts it outside the chain and why
7154        // the AST follows.
7155        assert_eq!(
7156            round("SELECT 1 UNION ALL SELECT 2 ORDER BY 1"),
7157            "(SELECT 1 Union All SELECT 2) ORDER BY 1 Unstated Unstated"
7158        );
7159        assert_eq!(
7160            round("SELECT a FROM t UNION SELECT b FROM u EXCEPT SELECT c FROM v"),
7161            "((SELECT a FROM t Union Unstated SELECT b FROM u) Except Unstated SELECT c FROM v)",
7162            "set operators are left associative"
7163        );
7164        assert_eq!(
7165            round("SELECT 1 UNION SELECT 2 INTERSECT SELECT 3"),
7166            "(SELECT 1 Union Unstated (SELECT 2 Intersect Unstated SELECT 3))",
7167            "and intersect binds tighter than the other two"
7168        );
7169    }
7170
7171    #[test]
7172    fn the_sort_and_limit_clauses_keep_what_was_written() {
7173        assert_eq!(
7174            round("SELECT a FROM t ORDER BY a"),
7175            "SELECT a FROM t ORDER BY a Unstated Unstated"
7176        );
7177        assert_eq!(
7178            round("SELECT a FROM t ORDER BY a DESC NULLS LAST"),
7179            "SELECT a FROM t ORDER BY a Descending Last"
7180        );
7181        assert_eq!(round("SELECT a FROM t ORDER BY ALL"), "SELECT a FROM t ORDER BY ALL");
7182        assert_eq!(round("SELECT a FROM t GROUP BY ALL"), "SELECT a FROM t GROUP BY ALL");
7183        assert_eq!(round("SELECT a FROM t LIMIT 10 OFFSET 5"), "SELECT a FROM t LIMIT 10 OFFSET 5");
7184        assert_eq!(round("SELECT a FROM t OFFSET 5 LIMIT 10"), "SELECT a FROM t LIMIT 10 OFFSET 5");
7185        assert_eq!(round("SELECT a FROM t LIMIT 10%"), "SELECT a FROM t LIMIT 10%");
7186        assert_eq!(round("SELECT a FROM t LIMIT ALL"), "SELECT a FROM t", "which is no limit");
7187    }
7188
7189    #[test]
7190    fn a_subquery_appears_in_both_places_it_can() {
7191        assert_eq!(
7192            round("SELECT * FROM (SELECT x FROM t) AS s"),
7193            "SELECT * FROM (SELECT x FROM t) AS s"
7194        );
7195        assert_eq!(round("SELECT (SELECT 1)"), "SELECT (SELECT 1)");
7196    }
7197
7198    #[test]
7199    fn distinct_on_keeps_its_expressions() {
7200        assert_eq!(round("SELECT DISTINCT a"), "SELECT DISTINCT a");
7201        assert_eq!(round("SELECT ALL a"), "SELECT a", "which is the default written out");
7202        assert_eq!(round("SELECT DISTINCT ON (a, b) a"), "SELECT DISTINCT ON (a, b) a");
7203    }
7204
7205    #[test]
7206    fn an_operator_the_dialect_does_not_name_is_kept_by_name() {
7207        // The grammar text says `OperatorLiteral <- Identifier`, which reads as though any bare
7208        // word could be written infix. It cannot. That rule is one of the 24 the matcher overrides
7209        // and it is overridden to the bare operator matcher, so what it takes is a run of operator
7210        // characters. Believing the body here would have produced a transformer that accepted
7211        // `a foo b`, which DuckDB rejects.
7212        assert_eq!(round("SELECT a <=> b"), "SELECT (a <=> b)");
7213        assert!(parse_ast("SELECT a foo b").is_err(), "a bare word is not an operator");
7214    }
7215
7216    #[test]
7217    fn a_script_is_a_list_of_statements() {
7218        let ast = parse_ast("SELECT 1; SELECT 2;").unwrap();
7219        assert_eq!(ast.statements.len(), 2);
7220        // A trailing semicolon makes an empty top level statement in the parse tree, because the
7221        // grammar's `Statement? (';'+ / EndOfInput)` is happy with nothing on both sides. It is
7222        // dropped here rather than pretended away in the matcher.
7223        let Statement::Query(second) = ast.statements[1] else {
7224            panic!("the second statement is a query");
7225        };
7226        assert_eq!(show_query(&ast, second), "SELECT 2");
7227    }
7228
7229    #[test]
7230    fn an_unsupported_construct_names_itself_and_what_was_written() {
7231        let error = parse_ast("COMMENT ON TABLE t IS 'a note'").unwrap_err().to_string();
7232        assert!(error.starts_with("Not implemented Error"), "{error}");
7233        assert!(error.contains("COMMENT ON TABLE t IS 'a note'"), "{error}");
7234        assert!(error.contains("CommentStatement"), "{error}");
7235    }
7236
7237    #[test]
7238    fn a_long_construct_is_cut_short_in_the_message() {
7239        let query = format!("COMMENT ON TABLE t IS '{}'", "a".repeat(80));
7240        let error = parse_ast(&query).unwrap_err().to_string();
7241        assert!(error.contains("..."), "{error}");
7242        assert!(error.len() < 200, "{error}");
7243    }
7244
7245    #[test]
7246    fn the_transformer_never_panics_on_anything_the_matcher_accepts() {
7247        // The matcher accepts a good deal that means nothing, because the grammar does. Every one
7248        // of these parses and none of them is a statement this milestone covers, and the contract
7249        // is that the answer is an error either way.
7250        for query in [
7251            "SELECT",
7252            "FROM t SELECT",
7253            "SELECT * FROM t WHERE",
7254            "SELECT ()",
7255            "SELECT a FROM t GROUP BY ()",
7256        ] {
7257            let answer = parse_ast(query);
7258            if let Err(error) = answer {
7259                let message = error.to_string();
7260                assert!(
7261                    message.starts_with("Not implemented Error")
7262                        || message.starts_with("Parser Error"),
7263                    "{query} failed with {message}"
7264                );
7265            }
7266        }
7267    }
7268
7269    #[test]
7270    fn a_file_name_in_a_from_clause_is_a_table_name_with_the_quotes_off() {
7271        // Both spellings have to arrive as the same name, because the binder decides whether it is
7272        // a file by looking at the name, and `'hits.parquet'` with the quotes still on it is not
7273        // a path that anything can open.
7274        assert_eq!(round("SELECT * FROM 'hits.parquet'"), "SELECT * FROM hits.parquet");
7275        assert_eq!(round("SELECT * FROM \"hits.parquet\""), "SELECT * FROM hits.parquet");
7276        assert_eq!(round("SELECT * FROM 'hits.parquet' AS h"), "SELECT * FROM hits.parquet AS h");
7277        assert_eq!(
7278            round_with_case("SELECT Mixed FROM 'NoSuch/Mixed/File.csv'", IdentifierCase::Lower),
7279            "SELECT mixed FROM NoSuch/Mixed/File.csv"
7280        );
7281        assert_eq!(
7282            round_with_case("SELECT Mixed FROM \"QuotedTable\"", IdentifierCase::Upper),
7283            "SELECT MIXED FROM QuotedTable"
7284        );
7285    }
7286
7287    #[test]
7288    fn a_function_call_in_a_from_clause_is_a_source_and_not_an_expression() {
7289        assert_eq!(round("SELECT * FROM range(3)"), "SELECT * FROM range(3)");
7290        assert_eq!(round("SELECT * FROM range(1, 10, 2)"), "SELECT * FROM range(1, 10, 2)");
7291        assert_eq!(round("SELECT * FROM main.range(3)"), "SELECT * FROM main.range(3)");
7292        assert_eq!(round("SELECT * FROM range(3) AS t"), "SELECT * FROM range(3) AS t");
7293        // The grammar allows a call with no arguments here and the transformer keeps it, because
7294        // whether a particular function takes none is the binder's question and not this one's.
7295        assert_eq!(round("SELECT * FROM some_function()"), "SELECT * FROM some_function()");
7296        // `LATERAL` is read and dropped, because a FROM entry here already sees the entries written
7297        // to its left and the word asks for nothing more.
7298        assert_eq!(round("SELECT * FROM LATERAL range(3)"), "SELECT * FROM range(3)");
7299        assert_eq!(
7300            round("SELECT * FROM t, LATERAL (SELECT t.x) AS v"),
7301            "SELECT * FROM t, (SELECT t.x) AS v"
7302        );
7303    }
7304
7305    #[test]
7306    fn the_forms_of_a_table_function_this_does_not_cover_are_turned_away_by_name() {
7307        for query in ["SELECT * FROM range(3) WITH ORDINALITY", "SELECT * FROM t: range(3)"] {
7308            let error = parse_ast(query).unwrap_err().to_string();
7309            assert!(error.contains("grammar rule"), "{query} failed with {error}");
7310        }
7311    }
7312
7313    #[test]
7314    fn a_pragma_is_the_call_it_stands_for_by_the_time_it_leaves_here() {
7315        assert_eq!(round("PRAGMA version"), "SELECT * FROM pragma_version()");
7316        assert_eq!(round("PRAGMA database_size"), "SELECT * FROM pragma_database_size()");
7317        // The case the user wrote survives, because the name goes back out in the message about a
7318        // pragma that does not exist and the pin prints it back as it was typed.
7319        assert_eq!(round("PRAGMA VERSION"), "SELECT * FROM pragma_VERSION()");
7320        assert_eq!(round("PRAGMA table_info('t')"), "SELECT * FROM pragma_table_info('t')");
7321    }
7322
7323    #[test]
7324    fn a_pragma_that_is_a_statement_stays_one_rather_than_becoming_a_call() {
7325        // These write a setting and return no rows, so there is nothing to select from. The name
7326        // carries the value as well, and which name means what is decided a layer up.
7327        assert_eq!(round_statement("PRAGMA disable_optimizer"), "PRAGMA disable_optimizer");
7328        assert_eq!(round_statement("PRAGMA enable_profiling"), "PRAGMA enable_profiling");
7329        assert_eq!(round_statement("PRAGMA force_checkpoint"), "PRAGMA force_checkpoint");
7330        assert_eq!(round_statement("PRAGMA verify_parallelism"), "PRAGMA verify_parallelism");
7331        // A name of the same shape that no engine has gets here too, and the catalog is what turns
7332        // it down, so that the sentence about it is the one the catalog says about any pragma.
7333        assert_eq!(round_statement("PRAGMA enable_nothing_at_all"), "PRAGMA enable_nothing_at_all");
7334        // With parentheses it is a call again, because a pragma that takes an argument returns rows.
7335        assert_eq!(
7336            round("PRAGMA disable_optimizer('x')"),
7337            "SELECT * FROM pragma_disable_optimizer('x')"
7338        );
7339    }
7340
7341    #[test]
7342    fn a_bare_name_in_a_pragmas_parentheses_is_a_name_and_not_a_column() {
7343        // There is no FROM clause here for a column to come out of, so both spellings have to
7344        // arrive as the same string, and a qualified one has to arrive as one string and not two.
7345        assert_eq!(round("PRAGMA table_info(t)"), "SELECT * FROM pragma_table_info('t')");
7346        assert_eq!(round("PRAGMA table_info(main.t)"), "SELECT * FROM pragma_table_info('main.t')");
7347        assert_eq!(round("PRAGMA table_info(\"T\")"), "SELECT * FROM pragma_table_info('T')");
7348        // Anything that is not a name is left alone, so the binder is the one that says there is
7349        // no overload taking an integer rather than a table called 1 being looked for.
7350        assert_eq!(round("PRAGMA table_info(1)"), "SELECT * FROM pragma_table_info(1)");
7351    }
7352
7353    #[test]
7354    fn a_pragma_with_an_equals_sign_is_a_set_and_nothing_else() {
7355        assert_eq!(round_statement("PRAGMA memory_limit = '1GB'"), "SET memory_limit = '1GB'");
7356        assert_eq!(round_statement("PRAGMA threads = 4"), "SET threads = 4");
7357    }
7358
7359    #[test]
7360    fn a_pragma_with_empty_parentheses_does_not_parse_on_either_engine() {
7361        // The rule is `PragmaParameters <- Parens(List(Expression))` and a list of no expressions
7362        // does not match, which is where the pin's parser error comes from as well.
7363        let error = parse_ast("PRAGMA version()").unwrap_err().to_string();
7364        assert!(error.contains("syntax error at or near \")\""), "{error}");
7365    }
7366
7367    #[test]
7368    fn a_window_call_carries_its_partition_its_order_and_its_frame() {
7369        assert_eq!(
7370            round("SELECT row_number() OVER () FROM t"),
7371            "SELECT row_number() OVER [] [] [Range UnboundedPreceding CurrentRow NoOthers] FROM t"
7372        );
7373        assert_eq!(
7374            round("SELECT sum(a) OVER (PARTITION BY b, c ORDER BY d DESC NULLS FIRST) FROM t"),
7375            "SELECT sum(a) OVER [b, c] [d Descending First] \
7376             [Range UnboundedPreceding CurrentRow NoOthers] FROM t"
7377        );
7378        assert_eq!(
7379            round(
7380                "SELECT sum(a) OVER (ORDER BY b GROUPS BETWEEN 1 PRECEDING AND 2 FOLLOWING EXCLUDE TIES) FROM t"
7381            ),
7382            "SELECT sum(a) OVER [] [b Unstated Unstated] \
7383             [Groups Preceding(1) Following(2) Ties] FROM t"
7384        );
7385    }
7386
7387    /// A frame over the whole partition is the same frame however it was measured, so the three
7388    /// units collapse to one here rather than three ways of saying it reaching the binder.
7389    #[test]
7390    fn a_frame_with_both_ends_unbounded_is_counted_in_rows() {
7391        for unit in ["ROWS", "RANGE", "GROUPS"] {
7392            let query = format!(
7393                "SELECT sum(a) OVER (ORDER BY b {unit} BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) FROM t"
7394            );
7395            assert_eq!(
7396                round(&query),
7397                "SELECT sum(a) OVER [] [b Unstated Unstated] \
7398                 [Rows UnboundedPreceding UnboundedFollowing NoOthers] FROM t"
7399            );
7400        }
7401    }
7402
7403    /// A single bound names the start and the end is the current row, which is the standard's rule
7404    /// and is why the two spellings below have to arrive as the same frame.
7405    #[test]
7406    fn a_frame_written_with_one_bound_ends_at_the_current_row() {
7407        assert_eq!(
7408            round("SELECT sum(a) OVER (ORDER BY b ROWS UNBOUNDED PRECEDING) FROM t"),
7409            round(
7410                "SELECT sum(a) OVER (ORDER BY b ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) FROM t"
7411            )
7412        );
7413    }
7414
7415    #[test]
7416    fn a_named_window_is_resolved_here_and_not_carried_any_further() {
7417        let inlined = round("SELECT sum(a) OVER (PARTITION BY b ORDER BY c) FROM t");
7418        assert_eq!(
7419            round("SELECT sum(a) OVER w FROM t WINDOW w AS (PARTITION BY b ORDER BY c)"),
7420            inlined
7421        );
7422        assert_eq!(
7423            round("SELECT sum(a) OVER (w) FROM t WINDOW w AS (PARTITION BY b ORDER BY c)"),
7424            inlined
7425        );
7426        // A definition can build on one written before it, and a copy can add the half the base
7427        // did not say.
7428        assert_eq!(
7429            round("SELECT sum(a) OVER v FROM t WINDOW w AS (PARTITION BY b), v AS (w ORDER BY c)"),
7430            inlined
7431        );
7432        assert_eq!(
7433            round("SELECT sum(a) OVER (w ORDER BY c) FROM t WINDOW w AS (PARTITION BY b)"),
7434            inlined
7435        );
7436        // The name is matched without regard to case, the way every other name here is.
7437        assert_eq!(
7438            round("SELECT sum(a) OVER W FROM t WINDOW w AS (PARTITION BY b ORDER BY c)"),
7439            inlined
7440        );
7441    }
7442
7443    /// A window clause is visible to the whole block it was written on, including a subquery
7444    /// inside it, which was measured on the pin.
7445    #[test]
7446    fn a_named_window_reaches_a_subquery_written_in_the_same_block() {
7447        let ast = parse_ast("SELECT (SELECT sum(b) OVER w FROM u) FROM t WINDOW w AS (ORDER BY b)");
7448        assert!(ast.is_ok(), "{:?}", ast.err());
7449        // And no further than that: the next statement in the script starts with none of them.
7450        let error =
7451            parse_ast("SELECT 1 FROM t WINDOW w AS (ORDER BY b); SELECT sum(a) OVER w FROM u;")
7452                .unwrap_err()
7453                .to_string();
7454        assert!(error.contains("window \"\"w\"\" does not exist"), "{error}");
7455    }
7456
7457    /// All four are the pin's sentences, in the pin's words, including the doubled quotes in the
7458    /// first one.
7459    #[test]
7460    fn the_four_complaints_about_a_named_window_are_upstreams() {
7461        let cases = [
7462            ("SELECT sum(a) OVER w FROM t", "window \"\"w\"\" does not exist"),
7463            (
7464                "SELECT sum(a) OVER (w PARTITION BY b) FROM t WINDOW w AS (PARTITION BY b)",
7465                "Cannot override PARTITION BY clause of window \"w\"",
7466            ),
7467            (
7468                "SELECT sum(a) OVER (w ORDER BY b) FROM t WINDOW w AS (ORDER BY b)",
7469                "Cannot override ORDER BY clause of window \"w\"",
7470            ),
7471            (
7472                "SELECT sum(a) OVER (w ROWS UNBOUNDED PRECEDING) FROM t WINDOW w AS (ORDER BY b ROWS UNBOUNDED PRECEDING)",
7473                "cannot copy window \"w\" because it has a frame clause",
7474            ),
7475        ];
7476        for (query, expected) in cases {
7477            let error = parse_ast(query).expect_err(query).to_string();
7478            assert!(error.contains(expected), "{query}: {error}");
7479        }
7480    }
7481
7482    /// `IGNORE NULLS` is a window modifier, so a call without an `OVER` still has nowhere to put
7483    /// it, and `EXCLUDE` needs a framing keyword in front of it on both engines.
7484    #[test]
7485    fn the_modifiers_that_only_a_window_takes_are_turned_down_without_one() {
7486        let error = parse_ast("SELECT first_value(a IGNORE NULLS) FROM t").unwrap_err().to_string();
7487        assert!(
7488            error.contains("RESPECT/IGNORE NULLS is not supported for non-window functions"),
7489            "{error}"
7490        );
7491        let error = parse_ast("SELECT sum(a) OVER (ORDER BY b EXCLUDE TIES) FROM t")
7492            .unwrap_err()
7493            .to_string();
7494        assert!(error.contains("syntax error at or near \"EXCLUDE\""), "{error}");
7495    }
7496
7497    /// A call with an `OVER` on it skips the rewrites an ordinary call goes through, which is
7498    /// visible on the one name that has a rewrite and an arity check of its own.
7499    #[test]
7500    fn a_window_call_is_not_put_through_the_rewrites_a_plain_call_is() {
7501        assert_eq!(
7502            round("SELECT ifnull(1) OVER () FROM t"),
7503            "SELECT ifnull(1) OVER [] [] [Range UnboundedPreceding CurrentRow NoOthers] FROM t"
7504        );
7505        let error = parse_ast("SELECT ifnull(1) FROM t").unwrap_err().to_string();
7506        assert!(error.contains("Wrong number of arguments to IFNULL."), "{error}");
7507    }
7508
7509    #[test]
7510    fn interning_means_a_name_written_twice_is_stored_once() {
7511        let ast = parse_ast("SELECT a, a, a FROM t WHERE a = a").unwrap();
7512        assert_eq!(ast.strings.iter().filter(|text| *text == "a").count(), 1);
7513    }
7514}