1use std::sync::Arc;
16
17use rudb_catalog::{Catalog, Entry, QualifiedName, same_name};
18use rudb_common::bounds::Zones;
19use rudb_common::{
20 Error, Field, LogicalType, Result, Semantics, Session, ShowBehavior, Span, Stat, Value,
21};
22use rudb_functions::{
23 Columns, FILE_ROW_NUMBER, FunctionKind, Given, Resolved, TableFunction, csv_fields, csv_given,
24 files, is_file, is_pattern, kind_of, parquet_footers, resolve, resolve_pragma, resolve_table,
25};
26use rudb_kernels::{percentage, row_count};
27use rudb_parse::ast::{self, Ast, Distinct, LiteralKind, Nulls, Order, Quantifier, SetOp};
28use rudb_parse::{NONE, identifier_parts, parse_ast_with_case};
29use rudb_plan::{
30 Bound, BuildSide, ColumnBinding, ConjunctionOp, Expr, ExprRef, JoinKind, Node, NodeRef, Plan,
31 SetOpKind, Share, SortKey, WindowBound, WindowExclude, WindowFrame, WindowUnit,
32};
33
34use crate::expr::{describe, has_aggregate};
35use crate::fold;
36use crate::parameters::Parameters;
37use crate::scope::{Scope, Visible};
38
39pub fn bind(ast: &Ast, catalog: &Catalog) -> Result<Plan> {
46 bind_with(ast, catalog, &Parameters::new(), &Session::new())
47}
48
49pub fn bind_with(
58 ast: &Ast,
59 catalog: &Catalog,
60 parameters: &Parameters,
61 session: &Session,
62) -> Result<Plan> {
63 let query = match ast.statements.as_slice() {
64 [ast::Statement::Query(query)] => *query,
65 [] => return Err(Error::binder("no statement to bind")),
66 [_] => return Err(Error::not_implemented("a statement that is not a query")),
69 _ => return Err(Error::not_implemented("a script of more than one statement")),
70 };
71 let mut binder = Binder::with(catalog, parameters, session);
72 let (root, _) = binder.bind_query(ast, query)?;
73 let mut plan = binder.into_plan();
74 plan.set_root(root);
75 plan.validate()?;
76 Ok(plan)
77}
78
79pub fn bind_sql(query: &str, catalog: &Catalog) -> Result<Plan> {
85 bind_sql_with(query, catalog, &Session::new())
86}
87
88pub fn bind_sql_with(query: &str, catalog: &Catalog, session: &Session) -> Result<Plan> {
94 let ast = parse_ast_with_case(query, session.semantics().identifier_case())?;
95 bind_with(&ast, catalog, &Parameters::new(), session)
96}
97
98#[derive(Debug)]
100pub(crate) struct Aggregation {
101 pub(crate) index: u32,
103 pub(crate) groups: Vec<ExprRef>,
105 pub(crate) aggregates: Vec<ExprRef>,
107}
108
109#[derive(Debug)]
117pub(crate) struct WindowRun {
118 index: u32,
120 partition: Vec<ExprRef>,
122 order: Vec<SortKey>,
124 frame: WindowFrame,
126 calls: Vec<ExprRef>,
128}
129
130pub(crate) struct WindowCall<'a> {
135 pub(crate) name: &'a str,
137 pub(crate) args: &'a [ast::ExprRef],
139 pub(crate) distinct: bool,
141 pub(crate) filter: ast::ExprRef,
143 pub(crate) ignore_nulls: bool,
145 pub(crate) order: ast::Slice,
148 pub(crate) spec: ast::WindowRef,
150}
151
152struct WindowParts {
154 args: Vec<ExprRef>,
156 partition: Vec<ExprRef>,
158 order: Vec<SortKey>,
160 inner: Vec<SortKey>,
163 frame: WindowFrame,
165}
166
167#[derive(Debug)]
174struct Read {
175 fields: Vec<Field>,
177 rows: Stat<u64>,
179 distincts: Vec<(String, Stat<u64>)>,
181 zones: Option<Arc<dyn Zones>>,
183}
184
185impl Read {
186 fn uncounted(fields: Vec<Field>) -> Self {
188 Self { fields, rows: Stat::Unknown, distincts: Vec::new(), zones: None }
189 }
190}
191
192#[derive(Debug)]
194struct Materialized {
195 written: u32,
197 cte: u32,
199 name: String,
201 fields: Vec<Field>,
203}
204
205#[derive(Debug)]
206pub(crate) struct PendingSubquery {
207 pub(crate) node: NodeRef,
208 pub(crate) kind: JoinKind,
209 pub(crate) conditions: Vec<ExprRef>,
210 pub(crate) dependent: bool,
211 pub(crate) reads: Vec<ColumnBinding>,
217 pub(crate) index: u32,
223 pub(crate) inside_aggregate: bool,
230}
231
232#[derive(Debug, Clone, Copy, PartialEq, Eq)]
234enum Side {
235 Left,
236 Right,
237}
238
239#[derive(Debug)]
241pub(crate) struct Binder<'a> {
242 catalog: &'a Catalog,
243 pub(crate) parameters: &'a Parameters,
245 pub(crate) session: &'a Session,
247 pub(crate) semantics: Semantics,
249 plan: Plan,
250 next_index: u32,
251 pub(crate) current_span: Span,
253 pub(crate) aggregation: Option<Aggregation>,
255 pub(crate) in_aggregate: bool,
257 pub(crate) in_filter: bool,
259 pub(crate) windows: Vec<WindowRun>,
261 pub(crate) in_window: bool,
263 pub(crate) scalar_subqueries: Vec<PendingSubquery>,
265 pub(crate) joined_above: Vec<u32>,
271 pub(crate) outer_scopes: Vec<Scope>,
272 pub(crate) lateral_scopes: Vec<usize>,
279 pub(crate) correlations: Vec<Vec<ColumnBinding>>,
280 pub(crate) clause: &'static str,
282 expanding: Vec<String>,
284 materialized: Vec<Materialized>,
290 next_cte: u32,
292 started: Option<i64>,
294}
295
296impl<'a> Binder<'a> {
297 pub(crate) fn with(
298 catalog: &'a Catalog,
299 parameters: &'a Parameters,
300 session: &'a Session,
301 ) -> Self {
302 Self {
303 catalog,
304 parameters,
305 session,
306 semantics: session.semantics(),
307 plan: Plan::new(),
308 next_index: 0,
309 current_span: Span::new(0, 0),
310 aggregation: None,
311 in_aggregate: false,
312 in_filter: false,
313 windows: Vec::new(),
314 in_window: false,
315 scalar_subqueries: Vec::new(),
316 joined_above: Vec::new(),
317 outer_scopes: Vec::new(),
318 lateral_scopes: Vec::new(),
319 correlations: Vec::new(),
320 clause: "SELECT clause",
321 expanding: Vec::new(),
322 materialized: Vec::new(),
323 next_cte: 0,
324 started: None,
325 }
326 }
327
328 pub(crate) fn catalog(&self) -> &Catalog {
329 self.catalog
330 }
331
332 pub(crate) fn instant(&mut self) -> i64 {
339 *self.started.get_or_insert_with(crate::context::micros_now)
340 }
341
342 pub(crate) fn plan(&self) -> &Plan {
343 &self.plan
344 }
345
346 pub(crate) fn plan_mut(&mut self) -> &mut Plan {
347 &mut self.plan
348 }
349
350 pub(crate) fn add_expr(&mut self, expr: Expr, ty: LogicalType) -> ExprRef {
351 self.plan.add_expr_at(expr, ty, self.current_span)
352 }
353
354 pub(crate) fn add_constant(&mut self, value: Value) -> ExprRef {
355 let ty = value.logical_type();
356 let reference = self.plan.add_value(value);
357 self.plan.add_expr_at(Expr::Constant(reference), ty, self.current_span)
358 }
359
360 pub(crate) fn add_node(&mut self, node: Node) -> NodeRef {
361 self.plan.add_node_at(node, self.current_span)
362 }
363
364 pub(crate) fn into_plan(self) -> Plan {
365 self.plan
366 }
367
368 pub(crate) fn fresh_index(&mut self) -> u32 {
370 let index = self.next_index;
371 self.next_index += 1;
372 index
373 }
374
375 fn column(&mut self, index: u32, position: usize, ty: LogicalType) -> ExprRef {
377 let binding = ColumnBinding::new(index, position as u32);
378 self.plan.add_expr(Expr::Column(binding), ty)
379 }
380
381 fn attach_scalar_subqueries(&mut self, mut input: NodeRef) -> NodeRef {
383 let subqueries = std::mem::take(&mut self.scalar_subqueries);
384 for pending in subqueries {
385 input = self.attach_subquery(input, pending);
386 }
387 input
388 }
389
390 fn attach_subquery(&mut self, input: NodeRef, pending: PendingSubquery) -> NodeRef {
397 let PendingSubquery {
398 node: mut right,
399 kind,
400 conditions,
401 dependent,
402 reads: _,
403 index: _,
404 inside_aggregate: _,
405 } = pending;
406 if kind == JoinKind::Single && !self.semantics.scalar_subquery_error_on_multiple_rows() {
407 right = self.add_node(Node::Limit {
408 input: right,
409 count: Bound::Rows(1),
410 offset: Bound::Rows(0),
411 });
412 }
413 let conditions = self.plan.add_expr_list(&conditions);
414 if dependent {
415 self.add_node(Node::DependentJoin { left: input, right, kind, conditions })
416 } else {
417 self.add_node(Node::Join {
418 left: input,
419 right,
420 kind,
421 conditions,
422 build: BuildSide::default(),
423 })
424 }
425 }
426
427 pub(crate) fn bind_query(
430 &mut self,
431 ast: &Ast,
432 query: ast::QueryRef,
433 ) -> Result<(NodeRef, Scope)> {
434 let span = ast.query_span(query);
435 let outer = std::mem::replace(&mut self.current_span, span);
436 let result =
437 self.bind_query_inner(ast, query).map_err(|error| error.with_fallback_span(span));
438 self.current_span = outer;
439 result
440 }
441
442 fn bind_query_inner(&mut self, ast: &Ast, query: ast::QueryRef) -> Result<(NodeRef, Scope)> {
443 let written = ast.query(query);
444 if written.ctes.is_empty() {
445 return self.bind_body(ast, &written);
446 }
447 let depth = self.materialized.len();
451 let result = self.bind_materialized(ast, &written);
452 self.materialized.truncate(depth);
453 result
454 }
455
456 fn bind_materialized(&mut self, ast: &Ast, written: &ast::Query) -> Result<(NodeRef, Scope)> {
462 let depth = self.materialized.len();
463 let held = ast.cte_list(written.ctes).to_vec();
464 let mut definitions = Vec::with_capacity(held.len());
465 for &index in &held {
466 definitions.push(self.bind_definition(ast, index)?);
467 }
468 let (mut node, scope) = self.bind_body(ast, written)?;
469 for (at, definition) in definitions.into_iter().enumerate().rev() {
470 let entry = &self.materialized[depth + at];
471 let cte = entry.cte;
472 let name = entry.name.clone();
473 let fields = entry.fields.clone();
474 let name = self.plan.intern(&name);
475 let columns = self.plan.add_fields(&fields);
476 node =
477 self.add_node(Node::MaterializedCte { definition, body: node, name, cte, columns });
478 }
479 Ok((node, scope))
480 }
481
482 fn bind_definition(&mut self, ast: &Ast, index: u32) -> Result<NodeRef> {
492 let held = ast.cte(index);
493 let name = ast.string(held.name).to_string();
494 let (node, mut scope) = self.bind_query(ast, held.query)?;
495 if !held.columns.is_empty() {
496 let names: Vec<&str> = ast.name(held.columns).collect();
497 scope.rename_prefix(&names);
498 }
499 let table = self.fresh_index();
500 let mut exprs = Vec::with_capacity(scope.len());
501 let mut names = Vec::with_capacity(scope.len());
502 for column in &scope.columns {
503 exprs.push(self.plan.add_expr(Expr::Column(column.binding), column.ty.clone()));
504 names.push(self.plan.intern(&column.name));
505 }
506 let exprs = self.plan.add_expr_list(&exprs);
507 let names = self.plan.add_name_list(&names);
508 let node = self.add_node(Node::Project { input: node, index: table, exprs, names });
509 let cte = self.next_cte;
510 self.next_cte += 1;
511 self.materialized.push(Materialized { written: index, cte, name, fields: scope.fields() });
512 Ok(node)
513 }
514
515 fn bind_body(&mut self, ast: &Ast, written: &ast::Query) -> Result<(NodeRef, Scope)> {
516 match written.body {
517 ast::QueryBody::Select(select) => self.bind_select(ast, select, written),
518 ast::QueryBody::SetOp { op, quantifier, by_name, left, right } => {
519 let operator = Operator { op, quantifier, by_name };
520 self.bind_set_op(ast, written, operator, left, right)
521 }
522 ast::QueryBody::Values(rows) => self.bind_values(ast, written, rows),
523 ast::QueryBody::Describe(inner) => self.bind_describe(ast, written, inner),
524 ast::QueryBody::Show { name, relation } => self.bind_show(ast, written, name, relation),
525 }
526 }
527
528 fn bind_show(
530 &mut self,
531 ast: &Ast,
532 query: &ast::Query,
533 name: ast::Slice,
534 relation: ast::QueryRef,
535 ) -> Result<(NodeRef, Scope)> {
536 let text = ast.name_text(name);
537 let parts: Vec<&str> = ast.name(name).collect();
538 let table_exists = self.catalog.resolve(&parts).is_ok();
539 let as_table = match self.semantics.show_behavior() {
540 ShowBehavior::Auto => table_exists,
541 ShowBehavior::Setting => false,
542 ShowBehavior::Table => true,
543 };
544 if as_table {
545 return self.bind_describe(ast, query, relation);
546 }
547 let Some((_, value)) =
548 self.session.iter().find(|(name, _)| name.eq_ignore_ascii_case(&text))
549 else {
550 return Err(Error::catalog(format!("Setting with name \"{text}\" does not exist")));
551 };
552 let field = Field::new(text, LogicalType::Varchar);
553 let expr = self.plan.add_constant(Value::Varchar(value.to_string()));
554 let row = self.plan.add_expr_list(&[expr]);
555 let rows = self.plan.add_rows(&[row]);
556 let columns = self.plan.add_fields(std::slice::from_ref(&field));
557 let index = self.fresh_index();
558 let node = self.add_node(Node::Values { index, columns, rows });
559 let mut scope = Scope::empty();
560 scope.push(Visible {
561 table: String::new(),
562 name: field.name,
563 binding: ColumnBinding::new(index, 0),
564 ty: LogicalType::Varchar,
565 not_null: false,
566 });
567 Ok((node, scope))
568 }
569
570 fn bind_describe(
586 &mut self,
587 ast: &Ast,
588 query: &ast::Query,
589 inner: ast::QueryRef,
590 ) -> Result<(NodeRef, Scope)> {
591 let (_, described) = self.bind_query(ast, inner)?;
592 let fields: Vec<Field> = ["column_name", "column_type", "null", "key", "default", "extra"]
593 .iter()
594 .map(|name| Field::new(*name, LogicalType::Varchar))
595 .collect();
596 let mut slices = Vec::with_capacity(described.columns.len());
597 for column in described.columns.clone() {
598 let written = [
601 column.name.clone(),
602 column.ty.to_string(),
603 if column.not_null { "NO" } else { "YES" }.to_owned(),
604 ];
605 let mut items: Vec<ExprRef> = written
606 .into_iter()
607 .map(|text| self.plan.add_constant(Value::Varchar(text)))
608 .collect();
609 for _ in 0..3 {
610 let empty = self.plan.add_constant(Value::Null);
611 items.push(self.cast_to(empty, &LogicalType::Varchar));
612 }
613 slices.push(self.plan.add_expr_list(&items));
614 }
615 let rows = self.plan.add_rows(&slices);
616 let columns = self.plan.add_fields(&fields);
617 let index = self.fresh_index();
618 let mut node = self.add_node(Node::Values { index, columns, rows });
619 let mut scope = Scope::empty();
620 for (at, field) in fields.iter().enumerate() {
621 scope.push(Visible {
622 table: String::new(),
623 name: field.name.clone(),
624 binding: ColumnBinding::new(index, at as u32),
625 ty: field.ty.clone(),
626 not_null: false,
627 });
628 }
629 let keys = self.sort_keys(ast, query, &scope, &[])?;
630 if !keys.is_empty() {
631 let keys = self.plan.add_sort_keys(&keys);
632 node = self.add_node(Node::Sort { input: node, keys });
633 }
634 node = self.apply_limit(ast, query, node, &mut scope)?;
635 Ok((node, scope))
636 }
637
638 fn passes_through(&self, expr: ExprRef, input: &Scope) -> bool {
644 let Expr::Column(binding) = *self.plan.expr(expr) else { return false };
645 input.columns.iter().any(|column| column.binding == binding && column.not_null)
646 }
647
648 fn bind_values(
655 &mut self,
656 ast: &Ast,
657 query: &ast::Query,
658 rows: ast::Slice,
659 ) -> Result<(NodeRef, Scope)> {
660 let written = ast.rows(rows).to_vec();
661 let Some(first) = written.first() else {
662 return Err(Error::binder("VALUES needs at least one row"));
663 };
664 let width = first.len as usize;
665 for (at, row) in written.iter().enumerate() {
666 if row.len as usize != width {
667 return Err(Error::binder(format!(
668 "VALUES lists must all be the same length, expected {width} columns but row {} has {}",
669 at + 1,
670 row.len
671 )));
672 }
673 }
674 let empty = Scope::empty();
676 let previous = std::mem::replace(&mut self.clause, "VALUES clause");
677 let mut bound: Vec<Vec<ExprRef>> = Vec::with_capacity(written.len());
678 for row in &written {
679 let mut items = Vec::with_capacity(width);
680 for &expr in ast.expr_list(*row) {
681 items.push(self.bind_expr(ast, expr, &empty)?);
682 }
683 bound.push(items);
684 }
685 self.clause = previous;
686 let mut types = Vec::with_capacity(width);
687 for at in 0..width {
688 let mut ty = self.plan.expr_type(bound[0][at]).clone();
689 for row in &bound[1..] {
690 let other = self.plan.expr_type(row[at]).clone();
691 ty = ty.promote(&other).ok_or_else(|| {
692 Error::binder(format!(
693 "Cannot combine a value of type {ty} with a value of type {other} in column {} of a VALUES",
694 at + 1
695 ))
696 })?;
697 }
698 types.push(ty);
699 }
700 let mut slices = Vec::with_capacity(bound.len());
701 for row in &bound {
702 let items: Vec<ExprRef> = row
703 .iter()
704 .zip(&types)
705 .map(|(&expr, ty)| self.checked_cast_to(expr, ty, false))
706 .collect::<Result<_>>()?;
707 slices.push(self.plan.add_expr_list(&items));
708 }
709 let rows = self.plan.add_rows(&slices);
710 let fields: Vec<Field> = types
711 .iter()
712 .enumerate()
713 .map(|(at, ty)| Field::new(format!("col{at}"), ty.clone()))
714 .collect();
715 let columns = self.plan.add_fields(&fields);
716 let index = self.fresh_index();
717 let mut node = self.add_node(Node::Values { index, columns, rows });
718 let mut scope = Scope::empty();
719 for (at, field) in fields.iter().enumerate() {
720 scope.push(Visible {
721 table: String::new(),
722 name: field.name.clone(),
723 binding: ColumnBinding::new(index, at as u32),
724 ty: field.ty.clone(),
725 not_null: false,
726 });
727 }
728 let keys = self.sort_keys(ast, query, &scope, &[])?;
729 if !keys.is_empty() {
730 let keys = self.plan.add_sort_keys(&keys);
731 node = self.add_node(Node::Sort { input: node, keys });
732 }
733 node = self.apply_limit(ast, query, node, &mut scope)?;
734 Ok((node, scope))
735 }
736
737 fn bind_set_op(
738 &mut self,
739 ast: &Ast,
740 query: &ast::Query,
741 operator: Operator,
742 left: ast::QueryRef,
743 right: ast::QueryRef,
744 ) -> Result<(NodeRef, Scope)> {
745 let (left_node, left_scope) = self.bind_query(ast, left)?;
746 let (right_node, right_scope) = self.bind_query(ast, right)?;
747 let merged = if operator.by_name {
748 match_by_name(&left_scope, &right_scope)?
749 } else {
750 match_by_position(&left_scope, &right_scope)?
751 };
752 let left_node = self.conform(left_node, &left_scope, &merged, |column| column.left)?;
753 let right_node = self.conform(right_node, &right_scope, &merged, |column| column.right)?;
754 let index = self.fresh_index();
755 let kind = match operator.op {
756 SetOp::Union => SetOpKind::Union,
757 SetOp::Except => SetOpKind::Except,
758 SetOp::Intersect => SetOpKind::Intersect,
759 };
760 let all = operator.quantifier == Quantifier::All;
763 let mut node =
764 self.add_node(Node::SetOp { left: left_node, right: right_node, kind, all, index });
765 let mut scope = Scope::empty();
766 for (at, column) in merged.iter().enumerate() {
767 scope.push(Visible {
768 table: String::new(),
769 name: column.name.clone(),
770 binding: ColumnBinding::new(index, at as u32),
771 ty: column.ty.clone(),
772 not_null: false,
775 });
776 }
777 let keys = self.sort_keys(ast, query, &scope, &[])?;
781 if !keys.is_empty() {
782 let keys = self.plan.add_sort_keys(&keys);
783 node = self.add_node(Node::Sort { input: node, keys });
784 }
785 node = self.apply_limit(ast, query, node, &mut scope)?;
786 Ok((node, scope))
787 }
788
789 fn conform(
795 &mut self,
796 node: NodeRef,
797 scope: &Scope,
798 merged: &[Merged],
799 pick: impl Fn(&Merged) -> Option<usize>,
800 ) -> Result<NodeRef> {
801 let unchanged = merged.len() == scope.len()
802 && merged
803 .iter()
804 .enumerate()
805 .all(|(at, column)| pick(column) == Some(at) && column.ty == scope.columns[at].ty);
806 if unchanged {
807 return Ok(node);
808 }
809 let index = self.fresh_index();
810 let mut exprs = Vec::with_capacity(merged.len());
811 let mut names = Vec::with_capacity(merged.len());
812 for column in merged {
813 let expr = match pick(column) {
814 Some(at) => {
815 let held = &scope.columns[at];
816 self.plan.add_expr(Expr::Column(held.binding), held.ty.clone())
817 }
818 None => self.plan.add_constant(Value::Null),
819 };
820 exprs.push(self.checked_cast_to(expr, &column.ty, false)?);
821 names.push(self.plan.intern(&column.name));
822 }
823 let exprs = self.plan.add_expr_list(&exprs);
824 let names = self.plan.add_name_list(&names);
825 Ok(self.add_node(Node::Project { input: node, index, exprs, names }))
826 }
827
828 fn bind_select(
831 &mut self,
832 ast: &Ast,
833 select: ast::SelectRef,
834 query: &ast::Query,
835 ) -> Result<(NodeRef, Scope)> {
836 let written = ast.select(select);
837 let outer_windows = std::mem::take(&mut self.windows);
841 let outer_joined_above = std::mem::take(&mut self.joined_above);
846 let (mut node, input) = self.bind_from(ast, written.from)?;
847 node = self.attach_scalar_subqueries(node);
848
849 if written.filter != NONE {
850 self.clause = "WHERE clause";
851 let predicate = self.bind_expr(ast, written.filter, &input)?;
852 let predicate = self.as_boolean(predicate, "WHERE")?;
853 node = self.attach_scalar_subqueries(node);
854 node = self.add_node(Node::Filter { input: node, predicate });
855 }
856
857 let targets = ast.target_list(written.targets).to_vec();
858 if targets.is_empty() {
859 return Err(Error::binder("a SELECT needs at least one expression to select"));
860 }
861
862 let group_items = self.group_items(ast, &written, &targets)?;
863 let aggregating = !group_items.is_empty()
864 || written.having != NONE
865 || targets.iter().any(|target| has_aggregate(ast, target.expr));
866 if aggregating {
867 self.clause = "GROUP BY clause";
868 let mut groups = Vec::with_capacity(group_items.len());
869 for item in &group_items {
870 groups.push(self.bind_expr(ast, *item, &input)?);
871 }
872 let index = self.fresh_index();
873 self.aggregation = Some(Aggregation { index, groups, aggregates: Vec::new() });
874 }
875
876 let mut above = Vec::new();
883
884 self.clause = "SELECT clause";
885 let (mut exprs, mut names) = self.bind_targets(ast, &targets, &input, &mut above)?;
886 let visible = exprs.len();
887
888 let mut having = None;
889 if written.having != NONE {
890 self.clause = "HAVING clause";
891 let before = self.scalar_subqueries.len();
892 let predicate = self.bind_expr(ast, written.having, &input)?;
893 self.lift_over_aggregate(before, &mut above, &input)?;
894 let predicate = self.over_aggregate(predicate, &input)?;
895 having = Some(self.as_boolean(predicate, "HAVING")?);
896 }
897
898 let project = self.fresh_index();
901 let mut output = Scope::empty();
902 for (at, (expr, name)) in exprs.iter().zip(&names).enumerate() {
903 output.push(Visible {
904 table: String::new(),
905 name: name.clone(),
906 binding: ColumnBinding::new(project, at as u32),
907 ty: self.plan.expr_type(*expr).clone(),
908 not_null: self.passes_through(*expr, &input),
909 });
910 }
911
912 self.clause = "ORDER BY clause";
913 let mut extra = Vec::new();
914 let keys = self.select_sort_keys(
915 ast, query, &input, &output, project, &mut exprs, &mut names, &mut extra, &mut above,
916 )?;
917 self.joined_above = outer_joined_above;
918 if !extra.is_empty() && written.distinct != Distinct::No {
919 return Err(Error::binder(
920 "For SELECT DISTINCT, ORDER BY expressions must appear in the select list",
921 ));
922 }
923 let on = self.distinct_on(ast, written.distinct, &output)?;
924
925 node = self.attach_scalar_subqueries(node);
926
927 if let Some(aggregation) = self.aggregation.take() {
928 let index = aggregation.index;
929 let groups = self.plan.add_expr_list(&aggregation.groups);
930 let aggregates = self.plan.add_expr_list(&aggregation.aggregates);
931 node = self.add_node(Node::Aggregate { input: node, index, groups, aggregates });
932 }
933 if !above.is_empty() {
934 debug_assert!(self.scalar_subqueries.is_empty(), "a query is waiting to be joined");
935 self.scalar_subqueries = above;
936 node = self.attach_scalar_subqueries(node);
937 }
938 if let Some(predicate) = having {
939 node = self.add_node(Node::Filter { input: node, predicate });
940 }
941
942 for run in std::mem::replace(&mut self.windows, outer_windows) {
946 let partition = self.plan.add_expr_list(&run.partition);
947 let order = self.plan.add_sort_keys(&run.order);
948 let expressions = self.plan.add_expr_list(&run.calls);
949 node = self.add_node(Node::Window {
950 input: node,
951 index: run.index,
952 partition,
953 order,
954 frame: run.frame,
955 expressions,
956 });
957 }
958
959 let interned: Vec<u32> = names.iter().map(|name| self.plan.intern(name)).collect();
960 let exprs_slice = self.plan.add_expr_list(&exprs);
961 let names_slice = self.plan.add_name_list(&interned);
962 node = self.add_node(Node::Project {
963 input: node,
964 index: project,
965 exprs: exprs_slice,
966 names: names_slice,
967 });
968
969 if written.distinct != Distinct::No {
970 let on = self.plan.add_expr_list(&on);
971 node = self.add_node(Node::Distinct { input: node, on });
972 }
973 if !keys.is_empty() {
974 let keys = self.plan.add_sort_keys(&keys);
975 node = self.add_node(Node::Sort { input: node, keys });
976 }
977 node = self.apply_limit(ast, query, node, &mut output)?;
978
979 if extra.is_empty() {
980 output.columns.truncate(visible);
981 return Ok((node, output));
982 }
983 let index = self.fresh_index();
986 let mut kept = Vec::with_capacity(visible);
987 let mut kept_names = Vec::with_capacity(visible);
988 let mut scope = Scope::empty();
989 for (at, name) in names.iter().enumerate().take(visible) {
990 let ty = output.columns[at].ty.clone();
991 let binding = output.columns[at].binding;
995 kept.push(self.plan.add_expr(Expr::Column(binding), ty.clone()));
996 kept_names.push(self.plan.intern(name));
997 scope.push(Visible {
998 table: String::new(),
999 name: name.clone(),
1000 binding: ColumnBinding::new(index, at as u32),
1001 ty,
1002 not_null: output.columns[at].not_null,
1003 });
1004 }
1005 let exprs = self.plan.add_expr_list(&kept);
1006 let names = self.plan.add_name_list(&kept_names);
1007 node = self.add_node(Node::Project { input: node, index, exprs, names });
1008 Ok((node, scope))
1009 }
1010
1011 fn lift_over_aggregate(
1029 &mut self,
1030 before: usize,
1031 above: &mut Vec<PendingSubquery>,
1032 scope: &Scope,
1033 ) -> Result<()> {
1034 if self.aggregation.is_none() {
1035 return Ok(());
1036 }
1037 let mut lifted = Vec::new();
1038 for pending in self.scalar_subqueries.split_off(before) {
1039 if pending.dependent || pending.inside_aggregate {
1040 self.scalar_subqueries.push(pending);
1041 } else {
1042 self.joined_above.push(pending.index);
1043 lifted.push(pending);
1044 }
1045 }
1046 for pending in &mut lifted {
1051 let conditions = std::mem::take(&mut pending.conditions);
1052 let mut over = Vec::with_capacity(conditions.len());
1053 for condition in conditions {
1054 over.push(self.over_aggregate(condition, scope)?);
1055 }
1056 pending.conditions = over;
1057 }
1058 above.append(&mut lifted);
1059 Ok(())
1060 }
1061
1062 fn bind_targets(
1063 &mut self,
1064 ast: &Ast,
1065 targets: &[ast::Target],
1066 input: &Scope,
1067 above: &mut Vec<PendingSubquery>,
1068 ) -> Result<(Vec<ExprRef>, Vec<String>)> {
1069 let mut exprs = Vec::with_capacity(targets.len());
1070 let mut names = Vec::with_capacity(targets.len());
1071 for target in targets {
1072 if let ast::Expr::Star { qualifier, replacements } = ast.expr(target.expr) {
1073 let table = ast.name(qualifier).last().map(str::to_string);
1074 let expanded: Vec<Visible> =
1075 input.star(table.as_deref())?.into_iter().cloned().collect();
1076 let replacements = ast.target_list(replacements).to_vec();
1077 let mut used = vec![false; replacements.len()];
1078 for column in expanded {
1079 let found = replacements.iter().zip(&mut used).find(|(replacement, _)| {
1080 same_name(ast.string(replacement.alias), &column.name)
1081 });
1082 let before = self.scalar_subqueries.len();
1087 let (expr, name) = match found {
1088 Some((replacement, used)) => {
1089 *used = true;
1090 let expr = self.bind_expr(ast, replacement.expr, input)?;
1091 (expr, ast.string(replacement.alias).to_string())
1092 }
1093 None => (
1094 self.plan.add_expr(Expr::Column(column.binding), column.ty),
1095 column.name,
1096 ),
1097 };
1098 self.lift_over_aggregate(before, above, input)?;
1099 exprs.push(self.over_aggregate(expr, input)?);
1100 names.push(name);
1101 }
1102 if let Some((replacement, _)) =
1106 replacements.iter().zip(&used).find(|(_, used)| !**used)
1107 {
1108 return Err(missing_replacement(ast.string(replacement.alias), input));
1109 }
1110 continue;
1111 }
1112 let before = self.scalar_subqueries.len();
1113 let expr = self.bind_expr(ast, target.expr, input)?;
1114 self.lift_over_aggregate(before, above, input)?;
1115 exprs.push(self.over_aggregate(expr, input)?);
1116 names.push(if target.alias == NONE {
1117 self.output_name(ast, target.expr, input)
1118 } else {
1119 ast.string(target.alias).to_string()
1120 });
1121 }
1122 Ok((exprs, names))
1123 }
1124
1125 fn output_name(&self, ast: &Ast, target: ast::ExprRef, input: &Scope) -> String {
1131 if let ast::Expr::Column { name } = ast.expr(target) {
1132 let parts: Vec<&str> = ast.name(name).collect();
1133 if let Ok(found) = input.resolve(&parts) {
1134 return found.name.clone();
1135 }
1136 }
1137 describe(ast, target, self.semantics)
1138 }
1139
1140 fn group_items(
1142 &self,
1143 ast: &Ast,
1144 select: &ast::Select,
1145 targets: &[ast::Target],
1146 ) -> Result<Vec<ast::ExprRef>> {
1147 if select.group_by_all {
1148 return Ok(targets
1151 .iter()
1152 .filter(|target| !has_aggregate(ast, target.expr))
1153 .map(|target| target.expr)
1154 .collect());
1155 }
1156 let mut items = Vec::new();
1157 for &item in ast.expr_list(select.group_by) {
1158 items.push(self.output_reference(ast, item, targets, "GROUP BY")?.unwrap_or(item));
1159 }
1160 Ok(items)
1161 }
1162
1163 fn output_reference(
1165 &self,
1166 ast: &Ast,
1167 item: ast::ExprRef,
1168 targets: &[ast::Target],
1169 clause: &str,
1170 ) -> Result<Option<ast::ExprRef>> {
1171 match ast.expr(item) {
1172 ast::Expr::Literal { kind: LiteralKind::Number, text } => {
1173 let written = ast.string(text);
1174 let position: usize = written.parse().map_err(|_| {
1175 Error::binder(format!("{clause} term {written} is not a column"))
1176 })?;
1177 if position == 0 || position > targets.len() {
1178 return Err(Error::binder(format!(
1179 "{clause} term out of range - should be between 1 and {}",
1180 targets.len()
1181 )));
1182 }
1183 Ok(Some(targets[position - 1].expr))
1184 }
1185 ast::Expr::Column { name } => {
1186 let parts: Vec<&str> = ast.name(name).collect();
1187 let [written] = parts.as_slice() else { return Ok(None) };
1188 let mut found = None;
1189 for target in targets {
1190 if target.alias != NONE && same_name(ast.string(target.alias), written) {
1191 if found.is_some() {
1192 return Ok(None);
1193 }
1194 found = Some(target.expr);
1195 }
1196 }
1197 Ok(found)
1198 }
1199 _ => Ok(None),
1200 }
1201 }
1202
1203 #[allow(clippy::too_many_arguments)]
1207 fn select_sort_keys(
1208 &mut self,
1209 ast: &Ast,
1210 query: &ast::Query,
1211 input: &Scope,
1212 output: &Scope,
1213 project: u32,
1214 exprs: &mut Vec<ExprRef>,
1215 names: &mut Vec<String>,
1216 extra: &mut Vec<usize>,
1217 above: &mut Vec<PendingSubquery>,
1218 ) -> Result<Vec<SortKey>> {
1219 if query.order_by_all {
1220 return Ok(self.every_column(output));
1221 }
1222 let items = ast.order_list(query.order_by).to_vec();
1223 let mut keys = Vec::with_capacity(items.len());
1224 for item in items {
1225 self.check_order_literal(ast, item.expr)?;
1226 let position = match self.output_position(ast, item.expr, output)? {
1227 Some(position) => position,
1228 None => {
1229 let before = self.scalar_subqueries.len();
1230 let bound = self.bind_expr(ast, item.expr, input)?;
1231 self.lift_over_aggregate(before, above, input)?;
1232 let bound = self.over_aggregate(bound, input)?;
1233 match exprs.iter().position(|&held| self.same_expr(held, bound)) {
1234 Some(position) => position,
1235 None => {
1236 exprs.push(bound);
1237 names.push(describe(ast, item.expr, self.semantics));
1238 extra.push(exprs.len() - 1);
1239 exprs.len() - 1
1240 }
1241 }
1242 }
1243 };
1244 let ty = self.plan.expr_type(exprs[position]).clone();
1245 let expr = self.column(project, position, ty);
1246 keys.push(self.sort_key(expr, item));
1247 }
1248 Ok(keys)
1249 }
1250
1251 fn sort_keys(
1253 &mut self,
1254 ast: &Ast,
1255 query: &ast::Query,
1256 output: &Scope,
1257 targets: &[ast::Target],
1258 ) -> Result<Vec<SortKey>> {
1259 if query.order_by_all {
1260 return Ok(self.every_column(output));
1261 }
1262 let items = ast.order_list(query.order_by).to_vec();
1263 let mut keys = Vec::with_capacity(items.len());
1264 for item in items {
1265 self.check_order_literal(ast, item.expr)?;
1266 let expr = match self.output_position(ast, item.expr, output)? {
1267 Some(position) => {
1268 let column = &output.columns[position];
1269 let (binding, ty) = (column.binding, column.ty.clone());
1270 self.plan.add_expr(Expr::Column(binding), ty)
1271 }
1272 None => {
1273 let _ = targets;
1274 self.bind_expr(ast, item.expr, output)?
1275 }
1276 };
1277 keys.push(self.sort_key(expr, item));
1278 }
1279 Ok(keys)
1280 }
1281
1282 fn every_column(&mut self, output: &Scope) -> Vec<SortKey> {
1283 let columns: Vec<(ColumnBinding, LogicalType)> =
1284 output.columns.iter().map(|column| (column.binding, column.ty.clone())).collect();
1285 columns
1286 .into_iter()
1287 .map(|(binding, ty)| {
1288 let expr = self.plan.add_expr(Expr::Column(binding), ty);
1289 let descending = self.semantics.default_descending();
1290 SortKey { expr, descending, nulls_first: self.semantics.nulls_first(descending) }
1291 })
1292 .collect()
1293 }
1294
1295 fn sort_key(&self, expr: ExprRef, item: ast::OrderItem) -> SortKey {
1297 let descending = match item.order {
1298 Order::Unstated => self.semantics.default_descending(),
1299 Order::Ascending => false,
1300 Order::Descending => true,
1301 };
1302 let nulls_first = match item.nulls {
1303 Nulls::First => true,
1304 Nulls::Last => false,
1305 Nulls::Unstated => self.semantics.nulls_first(descending),
1306 };
1307 SortKey { expr, descending, nulls_first }
1308 }
1309
1310 fn output_position(
1312 &self,
1313 ast: &Ast,
1314 item: ast::ExprRef,
1315 output: &Scope,
1316 ) -> Result<Option<usize>> {
1317 match ast.expr(item) {
1318 ast::Expr::Literal { kind: LiteralKind::Number, text } => {
1319 let written = ast.string(text);
1320 if written.contains(['.', 'e', 'E']) {
1321 return Ok(None);
1322 }
1323 let position: usize = written.parse().map_err(|_| {
1324 Error::binder(format!("ORDER BY term {written} is not a column"))
1325 })?;
1326 if position == 0 || position > output.len() {
1327 return Err(Error::binder(format!(
1328 "ORDER BY term out of range - should be between 1 and {}",
1329 output.len()
1330 )));
1331 }
1332 Ok(Some(position - 1))
1333 }
1334 ast::Expr::Column { name } => {
1335 let parts: Vec<&str> = ast.name(name).collect();
1336 let [written] = parts.as_slice() else { return Ok(None) };
1337 Ok(output.position_of(None, written))
1338 }
1339 _ => Ok(None),
1340 }
1341 }
1342
1343 fn check_order_literal(&self, ast: &Ast, item: ast::ExprRef) -> Result<()> {
1345 if !self.semantics.order_by_non_integer_literal()
1346 && matches!(
1347 ast.expr(item),
1348 ast::Expr::Literal { kind, text }
1349 if kind != LiteralKind::Number
1350 || ast.string(text).contains(['.', 'e', 'E'])
1351 )
1352 {
1353 return Err(Error::binder(
1354 "ORDER BY non-integer literal has no effect.\n* SET order_by_non_integer_literal=true to allow this behavior.",
1355 ));
1356 }
1357 Ok(())
1358 }
1359
1360 fn distinct_on(
1362 &mut self,
1363 ast: &Ast,
1364 distinct: Distinct,
1365 output: &Scope,
1366 ) -> Result<Vec<ExprRef>> {
1367 let Distinct::On(items) = distinct else {
1368 return Ok(Vec::new());
1369 };
1370 let items = ast.expr_list(items).to_vec();
1371 let mut on = Vec::with_capacity(items.len());
1372 for item in items {
1373 let Some(position) = self.output_position(ast, item, output)? else {
1374 return Err(Error::not_implemented(
1375 "DISTINCT ON an expression that is not in the select list",
1376 ));
1377 };
1378 let column = &output.columns[position];
1379 let (binding, ty) = (column.binding, column.ty.clone());
1380 on.push(self.plan.add_expr(Expr::Column(binding), ty));
1381 }
1382 Ok(on)
1383 }
1384
1385 fn apply_limit(
1392 &mut self,
1393 ast: &Ast,
1394 query: &ast::Query,
1395 input: NodeRef,
1396 scope: &mut Scope,
1397 ) -> Result<NodeRef> {
1398 let waiting = self.scalar_subqueries.len();
1399 if query.limit_percent {
1400 let percent = self.share(ast, query.limit)?;
1401 let offset = self.skipped(ast, query.offset)?;
1402 let node = |binder: &mut Self, input| match percent {
1403 Some(percent) => binder.add_node(Node::LimitPercent { input, percent, offset }),
1404 None => binder.limited(input, Bound::All, offset),
1407 };
1408 return self.over_subqueries(waiting, input, scope, node);
1409 }
1410 let count = self.count_bound(ast, query.limit, "LIMIT")?;
1411 let offset = self.skipped(ast, query.offset)?;
1412 let node = |binder: &mut Self, input| binder.limited(input, count, offset);
1413 self.over_subqueries(waiting, input, scope, node)
1414 }
1415
1416 fn skipped(&mut self, ast: &Ast, written: ast::ExprRef) -> Result<Bound> {
1421 Ok(match self.count_bound(ast, written, "OFFSET")? {
1422 Bound::All => Bound::Rows(0),
1423 named => named,
1424 })
1425 }
1426
1427 fn over_subqueries(
1434 &mut self,
1435 waiting: usize,
1436 input: NodeRef,
1437 scope: &mut Scope,
1438 node: impl FnOnce(&mut Self, NodeRef) -> NodeRef,
1439 ) -> Result<NodeRef> {
1440 let joined = self.scalar_subqueries.split_off(waiting);
1441 if joined.is_empty() {
1442 return Ok(node(self, input));
1443 }
1444 let mut input = input;
1445 for pending in joined {
1446 input = self.attach_subquery(input, pending);
1447 }
1448 let limit = node(self, input);
1449 Ok(self.reproject(limit, scope))
1450 }
1451
1452 fn limited(&mut self, input: NodeRef, count: Bound, offset: Bound) -> NodeRef {
1455 if count == Bound::All && offset == Bound::Rows(0) {
1456 return input;
1457 }
1458 self.add_node(Node::Limit { input, count, offset })
1459 }
1460
1461 fn reproject(&mut self, node: NodeRef, scope: &mut Scope) -> NodeRef {
1467 let index = self.fresh_index();
1468 let mut exprs = Vec::with_capacity(scope.columns.len());
1469 let mut names = Vec::with_capacity(scope.columns.len());
1470 for column in &scope.columns {
1471 exprs.push(self.plan.add_expr(Expr::Column(column.binding), column.ty.clone()));
1472 names.push(self.plan.intern(&column.name));
1473 }
1474 for (at, column) in scope.columns.iter_mut().enumerate() {
1475 column.binding = ColumnBinding::new(index, at as u32);
1476 }
1477 let exprs = self.plan.add_expr_list(&exprs);
1478 let names = self.plan.add_name_list(&names);
1479 self.add_node(Node::Project { input: node, index, exprs, names })
1480 }
1481
1482 fn share(&mut self, ast: &Ast, written: ast::ExprRef) -> Result<Option<Share>> {
1499 if written == NONE {
1500 return Ok(None);
1501 }
1502 self.clause = "LIMIT clause";
1503 let scope = Scope::empty();
1504 let bound = self.bind_expr(ast, written, &scope)?;
1505 let Some(value) = fold::value_of(&self.plan, bound)? else {
1506 return Ok(Some(Share::Read(bound)));
1507 };
1508 if value.is_null() {
1509 return Ok(None);
1510 }
1511 let percent = percentage(&value)?;
1512 if !(0.0..=100.0).contains(&percent) {
1513 return Err(Error::out_of_range(
1514 "Limit percent out of range, should be between 0% and 100%",
1515 ));
1516 }
1517 Ok(Some(Share::Percent(percent)))
1518 }
1519
1520 fn count_bound(&mut self, ast: &Ast, written: ast::ExprRef, clause: &str) -> Result<Bound> {
1539 if written == NONE {
1540 return Ok(Bound::All);
1541 }
1542 self.clause = "LIMIT clause";
1543 let scope = Scope::empty();
1544 let bound = self.bind_expr(ast, written, &scope)?;
1545 let Some(value) = fold::value_of(&self.plan, bound)? else {
1546 return Ok(Bound::Read(bound));
1547 };
1548 if value.is_null() {
1551 return Ok(Bound::All);
1552 }
1553 row_count(&value, clause).map(Bound::Rows)
1554 }
1555
1556 fn bind_from(&mut self, ast: &Ast, from: ast::Slice) -> Result<(NodeRef, Scope)> {
1559 let sources = ast.source_list(from).to_vec();
1560 let Some((first, rest)) = sources.split_first() else {
1561 return Ok((self.add_node(Node::Dummy), Scope::empty()));
1564 };
1565 let (mut node, mut scope) = self.bind_source(ast, *first)?;
1566 for source in rest {
1567 let (right, right_scope, correlations) = self.bind_lateral(ast, *source, &scope)?;
1568 node = if correlations.is_empty() {
1569 self.add_node(Node::CrossProduct { left: node, right })
1570 } else {
1571 let conditions = self.plan.add_expr_list(&[]);
1572 self.add_node(Node::DependentJoin {
1573 left: node,
1574 right,
1575 kind: JoinKind::Inner,
1576 conditions,
1577 })
1578 };
1579 scope = scope.concat(right_scope);
1580 }
1581 Ok((node, scope))
1582 }
1583
1584 fn bind_lateral(
1596 &mut self,
1597 ast: &Ast,
1598 source: ast::SourceRef,
1599 left: &Scope,
1600 ) -> Result<(NodeRef, Scope, Vec<ColumnBinding>)> {
1601 self.lateral_scopes.push(self.outer_scopes.len());
1602 self.outer_scopes.push(left.clone());
1603 self.correlations.push(Vec::new());
1604 let bound = self.bind_source(ast, source);
1605 let read = self.correlations.pop().expect("correlation frame");
1606 self.outer_scopes.pop();
1607 self.lateral_scopes.pop();
1608 let (node, scope) = bound?;
1609
1610 let mut here = Vec::new();
1611 for binding in read {
1612 if left.columns.iter().any(|column| column.binding == binding) {
1613 here.push(binding);
1614 } else if let Some(enclosing) = self.correlations.last_mut() {
1615 if !enclosing.contains(&binding) {
1616 enclosing.push(binding);
1617 }
1618 }
1619 }
1620 Ok((node, scope, here))
1630 }
1631
1632 fn bind_source(&mut self, ast: &Ast, source: ast::SourceRef) -> Result<(NodeRef, Scope)> {
1633 match ast.source(source) {
1634 ast::Source::Table { name, alias, columns } => {
1635 self.bind_table(ast, name, alias, columns)
1636 }
1637 ast::Source::Function { name, args, alias, columns, pragma } => {
1638 self.bind_table_function(ast, name, args, alias, columns, pragma)
1639 }
1640 ast::Source::Subquery { query, alias, columns } => {
1641 let (node, mut scope) = self.bind_query(ast, query)?;
1642 let label = if alias == NONE {
1643 "unnamed_subquery".to_string()
1644 } else {
1645 ast.string(alias).to_string()
1646 };
1647 scope.relabel(&label);
1648 if !columns.is_empty() {
1649 let names: Vec<&str> = ast.name(columns).collect();
1650 scope.rename(&names, &label)?;
1651 }
1652 Ok((node, scope))
1653 }
1654 ast::Source::Values { rows, alias, columns } => {
1655 let bare = ast::Query::bare(ast::QueryBody::Values(rows));
1656 let (node, mut scope) = self.bind_values(ast, &bare, rows)?;
1657 let label =
1658 if alias == NONE { String::new() } else { ast.string(alias).to_string() };
1659 scope.relabel(&label);
1660 if !columns.is_empty() {
1661 let names: Vec<&str> = ast.name(columns).collect();
1662 scope.rename(&names, &label)?;
1663 }
1664 Ok((node, scope))
1665 }
1666 ast::Source::Cte { cte, alias, columns } => {
1667 self.bind_cte_scan(ast, cte, alias, columns)
1668 }
1669 ast::Source::Join { left, right, kind, natural, on, using } => {
1670 self.bind_join(ast, left, right, kind, natural, on, using)
1671 }
1672 }
1673 }
1674
1675 fn bind_cte_scan(
1682 &mut self,
1683 ast: &Ast,
1684 written: u32,
1685 alias: ast::StrRef,
1686 columns: ast::Slice,
1687 ) -> Result<(NodeRef, Scope)> {
1688 let Some(held) = self.materialized.iter().rev().find(|held| held.written == written) else {
1689 let name = ast.string(ast.cte(written).name);
1690 return Err(Error::binder(format!("Table with name {name} does not exist!")));
1691 };
1692 let cte = held.cte;
1693 let fields = held.fields.clone();
1694 let text = held.name.clone();
1695 let label = if alias == NONE { text.clone() } else { ast.string(alias).to_string() };
1696 let name = self.plan.intern(&text);
1697 let index = self.fresh_index();
1698 let mut scope = Scope::empty();
1699 for (at, field) in fields.iter().enumerate() {
1700 scope.push(Visible {
1701 table: label.clone(),
1702 name: field.name.clone(),
1703 binding: ColumnBinding::new(index, at as u32),
1704 ty: field.ty.clone(),
1705 not_null: field.not_null,
1706 });
1707 }
1708 if !columns.is_empty() {
1709 let names: Vec<&str> = ast.name(columns).collect();
1710 scope.rename(&names, &label)?;
1711 }
1712 let columns = self.plan.add_fields(&fields);
1713 let node = self.add_node(Node::CteScan { index, cte, name, columns });
1714 Ok((node, scope))
1715 }
1716
1717 fn bind_table(
1718 &mut self,
1719 ast: &Ast,
1720 name: ast::Slice,
1721 alias: ast::StrRef,
1722 columns: ast::Slice,
1723 ) -> Result<(NodeRef, Scope)> {
1724 let parts: Vec<&str> = ast.name(name).collect();
1725 let catalog = self.catalog;
1726 let resolved = match catalog.resolve(&parts) {
1729 Ok(resolved) => resolved,
1730 Err(missing) => {
1731 return self.bind_replacement_scan(ast, &parts, alias, columns, missing);
1732 }
1733 };
1734 if catalog.entry(&resolved)? == Entry::View {
1735 return self.bind_view(ast, &resolved, alias, columns);
1736 }
1737 let table = catalog.table(&resolved)?;
1738 let fields: Vec<Field> = table.columns().to_vec();
1739 let label =
1740 if alias == NONE { resolved.table.clone() } else { ast.string(alias).to_string() };
1741 let index = self.fresh_index();
1742 let mut scope = Scope::empty();
1743 for (at, field) in fields.iter().enumerate() {
1744 scope.push(Visible {
1745 table: label.clone(),
1746 name: field.name.clone(),
1747 binding: ColumnBinding::new(index, at as u32),
1748 ty: field.ty.clone(),
1749 not_null: field.not_null,
1750 });
1751 }
1752 if !columns.is_empty() {
1753 let names: Vec<&str> = ast.name(columns).collect();
1754 scope.rename(&names, &label)?;
1755 }
1756 let catalog_name = self.plan.intern(&resolved.catalog);
1757 let schema = self.plan.intern(&resolved.schema);
1758 let table_name = self.plan.intern(&resolved.table);
1759 let alias = self.plan.intern(&label);
1760 let columns = self.plan.add_fields(&fields);
1761 if let Some(zones) = table.rows().zones() {
1766 self.plan.set_zones(index, zones);
1767 }
1768 if let Some(frequencies) = table.frequencies() {
1769 self.plan.set_frequencies(index, frequencies);
1770 }
1771 for (column, distinct) in table.distincts() {
1772 self.plan.measure_distinct(index, &column, distinct);
1773 }
1774 let node = self.add_node(Node::Get {
1775 catalog: catalog_name,
1776 schema,
1777 table: table_name,
1778 alias,
1779 index,
1780 columns,
1781 });
1782 Ok((node, scope))
1783 }
1784
1785 fn bind_view(
1797 &mut self,
1798 ast: &Ast,
1799 name: &QualifiedName,
1800 alias: ast::StrRef,
1801 columns: ast::Slice,
1802 ) -> Result<(NodeRef, Scope)> {
1803 let view = self.catalog.view(name)?;
1804 let full = name.to_string();
1805 if self.expanding.contains(&full) {
1806 return Err(Error::binder(format!(
1810 "infinite recursion detected: attempting to recursively bind view \"\"{}\"\"",
1811 name.table
1812 )));
1813 }
1814 let body = parse_ast_with_case(view.sql(), self.semantics.identifier_case())?;
1815 let query = match body.statements.as_slice() {
1816 [ast::Statement::Query(query)] => *query,
1817 _ => return Err(Error::binder(format!("view \"{}\" is not a query", name.table))),
1820 };
1821 self.expanding.push(full);
1822 let bound = self.bind_query(&body, query);
1823 self.expanding.pop();
1824 let (node, mut scope) = bound?;
1825
1826 let aliases: Vec<&str> = view.aliases().iter().map(String::as_str).collect();
1827 if !aliases.is_empty() {
1828 scope.rename(&aliases, "unnamed_subquery")?;
1829 }
1830 view.remember(scope.fields());
1837 let label = if alias == NONE { name.table.clone() } else { ast.string(alias).to_string() };
1838 scope.relabel(&label);
1839 if !columns.is_empty() {
1840 let names: Vec<&str> = ast.name(columns).collect();
1841 scope.rename(&names, &label)?;
1842 }
1843 Ok((node, scope))
1844 }
1845
1846 fn bind_table_function(
1854 &mut self,
1855 ast: &Ast,
1856 name: ast::Slice,
1857 args: ast::Slice,
1858 alias: ast::StrRef,
1859 columns: ast::Slice,
1860 pragma: bool,
1861 ) -> Result<(NodeRef, Scope)> {
1862 let parts: Vec<&str> = ast.name(name).collect();
1863 let function_name = *parts.last().unwrap_or(&"");
1867 if let Some(schema) = parts.iter().rev().nth(1) {
1868 if !schema.eq_ignore_ascii_case("main") && !schema.eq_ignore_ascii_case("system") {
1869 return Err(Error::catalog(format!(
1870 "Table Function with name {} does not exist!",
1871 parts.join(".")
1872 )));
1873 }
1874 }
1875 let Some(called) = TableFunction::lookup(function_name) else {
1879 if pragma {
1880 if args.is_empty() && self.catalog.resolve(&parts).is_ok() {
1886 return self.bind_table(ast, name, alias, columns);
1887 }
1888 let spelled = function_name.strip_prefix("pragma_").unwrap_or(function_name);
1889 return Err(Error::catalog(format!(
1890 "Pragma Function with name {spelled} does not exist!"
1891 )));
1892 }
1893 return Err(Error::catalog(format!(
1894 "Table Function with name {function_name} does not exist!"
1895 )));
1896 };
1897 let written = ast.target_list(args).to_vec();
1898 let empty = Scope::empty();
1899 let previous = std::mem::replace(&mut self.clause, "table function arguments");
1900 let mut bound = Vec::new();
1901 let mut written_options = Vec::new();
1902 for argument in written {
1903 let expr = self.bind_expr(ast, argument.expr, &empty)?;
1904 if argument.alias == NONE {
1905 bound.push(expr);
1906 } else {
1907 let name = ast.string(argument.alias).to_string();
1908 let (parameter, value) = self.named_argument(called, &name, expr)?;
1909 written_options.push((parameter, value, expr));
1910 }
1911 }
1912 self.clause = previous;
1913 let options = Options::of(&written_options)?;
1914
1915 let given: Vec<LogicalType> =
1918 bound.iter().map(|&expr| self.plan.expr_type(expr).clone()).collect();
1919 let resolved = if pragma {
1920 resolve_pragma(function_name, &given)?
1921 } else {
1922 resolve_table(function_name, &given)?
1923 };
1924 let mut cast: Vec<ExprRef> = bound
1925 .iter()
1926 .zip(&resolved.arguments)
1927 .map(|(&expr, ty)| self.checked_cast_to(expr, ty, false))
1928 .collect::<Result<_>>()?;
1929
1930 if resolved.function.answered_when_bound() {
1931 let Columns::Fixed(fields) = resolved.columns else {
1932 return Err(Error::internal("a pragma that resolved to a file"));
1933 };
1934 let [argument] = cast[..] else {
1935 return Err(Error::internal("a pragma that resolved to more than one name"));
1936 };
1937 return self.bind_pragma(ast, resolved.function, &fields, argument, alias, columns);
1938 }
1939 let mut measured = Stat::Unknown;
1942 let mut counted: Vec<(String, Stat<u64>)> = Vec::new();
1943 let mut bounded: Option<Arc<dyn Zones>> = None;
1944 let fields = match resolved.columns {
1945 Columns::Fixed(fields) => fields,
1946 columns => {
1947 let paths = self.file_paths(cast[0], resolved.function.name())?;
1952 let mut fields = match columns {
1953 Columns::Csv => csv_fields(&paths, options.given)?,
1956 _ => {
1957 let footers = parquet_footers(&paths)?;
1958 measured = footers.rows;
1959 counted = footers.distincts;
1960 bounded = footers.zones;
1961 footers.fields
1962 }
1963 };
1964 if options.all_varchar {
1965 for field in &mut fields {
1970 field.ty = LogicalType::Varchar;
1971 }
1972 }
1973 if options.binary_as_string {
1974 for field in &mut fields {
1979 if field.ty == LogicalType::Blob {
1980 field.ty = LogicalType::Varchar;
1981 }
1982 }
1983 }
1984 if options.file_row_number {
1985 if fields.iter().any(|field| field.name == FILE_ROW_NUMBER) {
1991 return Err(Error::binder(format!(
1992 "Duplicate column name \"{FILE_ROW_NUMBER}\": the file already has a \
1993 column of that name, so file_row_number cannot add one"
1994 )));
1995 }
1996 fields.push(Field::required(FILE_ROW_NUMBER.to_string(), LogicalType::BigInt));
1997 }
1998 cast = paths.iter().map(|path| self.path_constant(path)).collect();
1999 fields
2000 }
2001 };
2002 let label = if alias == NONE {
2003 resolved.function.name().to_string()
2004 } else {
2005 ast.string(alias).to_string()
2006 };
2007 let names: Vec<&str> = ast.name(columns).collect();
2008 self.table_function_source(
2009 resolved.function,
2010 &cast,
2011 &written_options,
2012 Read { fields, rows: measured, distincts: counted, zones: bounded },
2013 &label,
2014 &names,
2015 )
2016 }
2017
2018 fn bind_pragma(
2031 &mut self,
2032 ast: &Ast,
2033 function: TableFunction,
2034 fields: &[Field],
2035 argument: ExprRef,
2036 alias: ast::StrRef,
2037 columns: ast::Slice,
2038 ) -> Result<(NodeRef, Scope)> {
2039 let written = self.pragma_name(argument, function)?;
2040 let parts = identifier_parts(&written);
2041 let spelled: Vec<&str> = parts.iter().map(String::as_str).collect();
2042 let name = self.catalog.resolve(&spelled)?;
2043 let described = self.described(ast, &name)?;
2044 let mut rows = Vec::with_capacity(described.len());
2045 for (at, field) in described.iter().enumerate() {
2046 let items = if matches!(function, TableFunction::PragmaShow) {
2047 self.describing(field)
2048 } else {
2049 self.table_info(at, field)
2050 };
2051 rows.push(self.plan.add_expr_list(&items));
2052 }
2053 let rows = self.plan.add_rows(&rows);
2054 let held = self.plan.add_fields(fields);
2055 let index = self.fresh_index();
2056 let node = self.add_node(Node::Values { index, columns: held, rows });
2057 let label =
2058 if alias == NONE { function.name().to_string() } else { ast.string(alias).to_string() };
2059 let mut scope = Scope::empty();
2060 for (at, field) in fields.iter().enumerate() {
2061 scope.push(Visible {
2062 table: label.clone(),
2063 name: field.name.clone(),
2064 binding: ColumnBinding::new(index, at as u32),
2065 ty: field.ty.clone(),
2066 not_null: false,
2067 });
2068 }
2069 if !columns.is_empty() {
2070 let names: Vec<&str> = ast.name(columns).collect();
2071 scope.rename(&names, &label)?;
2072 }
2073 Ok((node, scope))
2074 }
2075
2076 fn pragma_name(&self, argument: ExprRef, function: TableFunction) -> Result<String> {
2086 let Expr::Constant(reference) = *self.plan.expr(argument) else {
2087 return Err(Error::not_implemented(format!(
2088 "{}() given a name that is not a constant",
2089 function.name()
2090 )));
2091 };
2092 match self.plan.value(reference) {
2093 Value::Varchar(name) => Ok(name.clone()),
2094 Value::Null => Ok("NULL".to_string()),
2095 other => {
2096 Err(Error::internal(format!("a pragma name bound as VARCHAR arrived as {other}")))
2097 }
2098 }
2099 }
2100
2101 fn described(&mut self, ast: &Ast, name: &QualifiedName) -> Result<Vec<Field>> {
2112 if self.catalog.entry(name)? == Entry::Table {
2113 return Ok(self.catalog.table(name)?.columns().to_vec());
2114 }
2115 let (_, scope) = self.bind_view(ast, name, NONE, ast::Slice::default())?;
2116 Ok(scope.fields())
2117 }
2118
2119 fn describing(&mut self, field: &Field) -> Vec<ExprRef> {
2121 let written = [
2122 field.name.clone(),
2123 field.ty.to_string(),
2124 if field.not_null { "NO" } else { "YES" }.to_owned(),
2125 ];
2126 let mut items: Vec<ExprRef> =
2127 written.into_iter().map(|text| self.plan.add_constant(Value::Varchar(text))).collect();
2128 for _ in 0..3 {
2129 let empty = self.plan.add_constant(Value::Null);
2130 items.push(self.cast_to(empty, &LogicalType::Varchar));
2131 }
2132 items
2133 }
2134
2135 fn table_info(&mut self, at: usize, field: &Field) -> Vec<ExprRef> {
2141 let cid = self.plan.add_constant(Value::Integer(i32::try_from(at).unwrap_or(i32::MAX)));
2142 let name = self.plan.add_constant(Value::Varchar(field.name.clone()));
2143 let ty = self.plan.add_constant(Value::Varchar(field.ty.to_string()));
2144 let not_null = self.plan.add_constant(Value::Boolean(field.not_null));
2145 let default = self.plan.add_constant(Value::Null);
2146 let default = self.cast_to(default, &LogicalType::Varchar);
2147 let key = self.plan.add_constant(Value::Boolean(false));
2148 vec![cid, name, ty, not_null, default, key]
2149 }
2150
2151 fn named_argument(
2165 &mut self,
2166 function: TableFunction,
2167 name: &str,
2168 expr: ExprRef,
2169 ) -> Result<(&'static str, Value)> {
2170 let known = function
2171 .parameters()
2172 .iter()
2173 .find(|(parameter, _)| parameter.eq_ignore_ascii_case(name));
2174 let Some((parameter, wanted)) = known else {
2175 let candidates: Vec<String> = function
2176 .parameters()
2177 .iter()
2178 .map(|(parameter, ty)| format!(" {parameter} {ty}"))
2179 .collect();
2180 return Err(Error::binder(format!(
2181 "Invalid named parameter \"{name}\" for function {}\nCandidates:\n{}\n",
2182 function.name(),
2183 candidates.join("\n")
2184 )));
2185 };
2186 let Expr::Constant(reference) = *self.plan.expr(expr) else {
2187 return Err(Error::not_implemented(format!(
2188 "the named parameter {parameter} with a value that is not a constant"
2189 )));
2190 };
2191 let value = self.plan.value(reference).clone();
2192 if value == Value::Null {
2193 return Err(Error::binder(null_parameter(function, parameter)));
2194 }
2195 let given = self.plan.expr_type(expr).clone();
2196 if given != *wanted {
2197 return Err(Error::not_implemented(format!(
2198 "the named parameter {parameter} given a {given} where a {wanted} was wanted"
2199 )));
2200 }
2201 Ok((parameter, value))
2202 }
2203
2204 fn bind_replacement_scan(
2215 &mut self,
2216 ast: &Ast,
2217 parts: &[&str],
2218 alias: ast::StrRef,
2219 columns: ast::Slice,
2220 missing: Error,
2221 ) -> Result<(NodeRef, Scope)> {
2222 let [path] = parts else { return Err(missing) };
2223 let path = *path;
2224 let extension = path.rsplit_once('.').map(|(_, after)| after).unwrap_or_default();
2225 let Some(function) = Self::reader_for(extension) else {
2226 if is_file(path) {
2227 return Err(Error::binder(format!(
2232 "No extension found that is capable of reading the file \"{path}\"\n* If this \
2233 file is a supported file format you can explicitly use the reader functions, \
2234 such as read_csv, read_json or read_parquet"
2235 )));
2236 }
2237 return Err(missing);
2238 };
2239 let paths = files(path)?;
2244 let read = match function {
2245 TableFunction::ReadParquet => {
2246 let footers = parquet_footers(&paths)?;
2247 Read {
2248 fields: footers.fields,
2249 rows: footers.rows,
2250 distincts: footers.distincts,
2251 zones: footers.zones,
2252 }
2253 }
2254 _ => Read::uncounted(csv_fields(&paths, Given::default())?),
2255 };
2256 let label = if alias == NONE {
2262 if is_pattern(path) {
2263 path.to_string()
2264 } else {
2265 let file = path.rsplit_once('/').map_or(path, |(_, file)| file);
2266 file.rsplit_once('.').map_or(file, |(stem, _)| stem).to_string()
2267 }
2268 } else {
2269 ast.string(alias).to_string()
2270 };
2271 let arguments: Vec<ExprRef> = paths.iter().map(|path| self.path_constant(path)).collect();
2272 let names: Vec<&str> = ast.name(columns).collect();
2273 self.table_function_source(function, &arguments, &[], read, &label, &names)
2274 }
2275
2276 fn path_constant(&mut self, path: &str) -> ExprRef {
2278 let value = self.plan.add_value(Value::Varchar(path.to_string()));
2279 self.plan.add_expr(Expr::Constant(value), LogicalType::Varchar)
2280 }
2281
2282 fn reader_for(extension: &str) -> Option<TableFunction> {
2289 if extension.eq_ignore_ascii_case("parquet") {
2290 return Some(TableFunction::ReadParquet);
2291 }
2292 if extension.eq_ignore_ascii_case("csv") || extension.eq_ignore_ascii_case("tsv") {
2293 return Some(TableFunction::ReadCsv);
2294 }
2295 None
2296 }
2297
2298 fn table_function_source(
2308 &mut self,
2309 function: TableFunction,
2310 args: &[ExprRef],
2311 written: &[(&'static str, Value, ExprRef)],
2312 read: Read,
2313 label: &str,
2314 names: &[&str],
2315 ) -> Result<(NodeRef, Scope)> {
2316 let Read { fields, rows, distincts, zones } = read;
2317 let index = self.fresh_index();
2318 if rows.is_known() {
2323 self.plan.measure(index, rows);
2324 }
2325 for (column, distinct) in distincts {
2326 self.plan.measure_distinct(index, &column, distinct);
2327 }
2328 if let Some(zones) = zones {
2329 self.plan.set_zones(index, zones);
2330 }
2331 let mut scope = Scope::empty();
2332 for (at, field) in fields.iter().enumerate() {
2333 scope.push(Visible {
2334 table: label.to_string(),
2335 name: field.name.clone(),
2336 binding: ColumnBinding::new(index, at as u32),
2337 ty: field.ty.clone(),
2338 not_null: false,
2341 });
2342 }
2343 if !names.is_empty() {
2344 scope.rename(names, label)?;
2345 }
2346 let function = self.plan.intern(function.name());
2347 let args = self.plan.add_expr_list(args);
2348 let named: Vec<u32> =
2349 written.iter().map(|(parameter, _, _)| self.plan.intern(parameter)).collect();
2350 let settings: Vec<ExprRef> = written.iter().map(|(_, _, expr)| *expr).collect();
2351 let options = self.plan.add_name_list(&named);
2352 let settings = self.plan.add_expr_list(&settings);
2353 let columns = self.plan.add_fields(&fields);
2354 let node = self.add_node(Node::TableFunction {
2355 index,
2356 function,
2357 args,
2358 options,
2359 settings,
2360 columns,
2361 });
2362 Ok((node, scope))
2363 }
2364
2365 fn file_paths(&self, expr: ExprRef, name: &str) -> Result<Vec<String>> {
2372 let mut paths = Vec::new();
2373 for pattern in self.file_patterns(expr, name)? {
2374 paths.extend(files(&pattern)?);
2375 }
2376 Ok(paths)
2377 }
2378
2379 fn file_patterns(&self, expr: ExprRef, name: &str) -> Result<Vec<String>> {
2391 let Expr::Constant(reference) = *self.plan.expr(expr) else {
2392 return Err(Error::not_implemented(
2393 "a table function file name that is not a constant",
2394 ));
2395 };
2396 match self.plan.value(reference) {
2397 Value::Varchar(path) => Ok(vec![path.clone()]),
2398 Value::Null => Err(Error::parser(format!("{name} cannot take NULL list as parameter"))),
2400 Value::List { values, .. } => values
2401 .iter()
2402 .map(|value| match value {
2403 Value::Varchar(path) => Ok(path.clone()),
2404 _ => Err(Error::parser(format!(
2405 "{name} reader cannot take NULL input as parameter"
2406 ))),
2407 })
2408 .collect(),
2409 other => {
2410 Err(Error::internal(format!("a file name bound as VARCHAR arrived as {other}")))
2411 }
2412 }
2413 }
2414
2415 fn side_of(
2433 &self,
2434 pending: &PendingSubquery,
2435 left_tables: &[u32],
2436 right_tables: &[u32],
2437 ) -> Option<Side> {
2438 let mut needs_left = false;
2439 let mut needs_right = false;
2440 let mut note = |binding: ColumnBinding| {
2441 needs_left |= left_tables.contains(&binding.table);
2442 needs_right |= right_tables.contains(&binding.table);
2443 };
2444 for &binding in &pending.reads {
2445 note(binding);
2446 }
2447 for &condition in &pending.conditions {
2452 self.plan.read_columns(condition, &mut |_, binding| note(binding));
2453 }
2454 match (needs_left, needs_right) {
2455 (true, true) => None,
2456 (_, true) => Some(Side::Right),
2457 _ => Some(Side::Left),
2458 }
2459 }
2460
2461 #[allow(clippy::too_many_arguments)]
2482 fn bind_pair_dependent_join(
2483 &mut self,
2484 kind: ast::JoinKind,
2485 independent: bool,
2486 left: NodeRef,
2487 right: NodeRef,
2488 pair: Vec<PendingSubquery>,
2489 conditions: Vec<ExprRef>,
2490 scope: Scope,
2491 ) -> Result<(NodeRef, Scope)> {
2492 if kind != ast::JoinKind::Inner {
2493 return Err(Error::not_implemented(
2494 "a subquery that reads both sides of that join, written in the condition of a join \
2495 that is not an inner join"
2496 .to_string(),
2497 ));
2498 }
2499 if !independent {
2502 return Err(Error::not_implemented(
2503 "a subquery that reads both sides of that join, written in the condition of a join \
2504 whose right side is lateral"
2505 .to_string(),
2506 ));
2507 }
2508 let mut node = self.add_node(Node::CrossProduct { left, right });
2509 for pending in pair {
2510 node = self.attach_subquery(node, pending);
2511 }
2512 let mut conditions = conditions.into_iter();
2516 let mut predicate = conditions.next().expect("a join condition was bound");
2517 for next in conditions {
2518 let children = self.plan.add_expr_list(&[predicate, next]);
2519 let conjunction = Expr::Conjunction { op: ConjunctionOp::And, children };
2520 predicate = self.plan.add_expr(conjunction, LogicalType::Boolean);
2521 }
2522 let node = self.add_node(Node::Filter { input: node, predicate });
2523 Ok((node, scope))
2524 }
2525
2526 #[allow(clippy::too_many_arguments)]
2527 fn bind_join(
2528 &mut self,
2529 ast: &Ast,
2530 left: ast::SourceRef,
2531 right: ast::SourceRef,
2532 kind: ast::JoinKind,
2533 natural: bool,
2534 on: ast::ExprRef,
2535 using: ast::Slice,
2536 ) -> Result<(NodeRef, Scope)> {
2537 let (left_node, left_scope) = self.bind_source(ast, left)?;
2538 let (right_node, right_scope, correlated) = self.bind_lateral(ast, right, &left_scope)?;
2539 if !correlated.is_empty()
2543 && !matches!(kind, ast::JoinKind::Inner | ast::JoinKind::Cross | ast::JoinKind::Left)
2544 {
2545 return Err(Error::binder(
2546 "The combining JOIN type must be INNER or LEFT for a LATERAL reference",
2547 ));
2548 }
2549 let split = left_scope.len();
2550 let left_tables: Vec<u32> =
2556 left_scope.columns.iter().map(|column| column.binding.table).collect();
2557 let right_tables: Vec<u32> =
2558 right_scope.columns.iter().map(|column| column.binding.table).collect();
2559 let mut scope = left_scope.concat(right_scope);
2560
2561 let merged: Vec<String> = if natural {
2564 let mut names = Vec::new();
2565 for (at, column) in scope.columns.iter().enumerate().take(split) {
2566 if scope.columns[split..].iter().any(|right| same_name(&right.name, &column.name))
2567 && !names.iter().any(|held: &String| same_name(held, &column.name))
2568 {
2569 let _ = at;
2570 names.push(column.name.clone());
2571 }
2572 }
2573 names
2574 } else {
2575 let mut names: Vec<String> = Vec::new();
2581 for name in ast.name(using) {
2582 if !names.iter().any(|held| same_name(held, name)) {
2583 names.push(name.to_string());
2584 }
2585 }
2586 names
2587 };
2588
2589 let mut conditions = Vec::new();
2590 let mut dropped = Vec::new();
2591 for name in &merged {
2592 let left_at = scope.columns[..split]
2593 .iter()
2594 .position(|column| same_name(&column.name, name))
2595 .ok_or_else(|| {
2596 Error::binder(format!(
2597 "column \"{name}\" specified in USING clause does not exist in left table"
2598 ))
2599 })?;
2600 let right_at = scope.columns[split..]
2601 .iter()
2602 .position(|column| same_name(&column.name, name))
2603 .map(|at| at + split)
2604 .ok_or_else(|| {
2605 Error::binder(format!(
2606 "column \"{name}\" specified in USING clause does not exist in right table"
2607 ))
2608 })?;
2609 let left_column = &scope.columns[left_at];
2610 let (left_binding, left_type) = (left_column.binding, left_column.ty.clone());
2611 let right_column = &scope.columns[right_at];
2612 let (right_binding, right_type) = (right_column.binding, right_column.ty.clone());
2613 let left_expr = self.plan.add_expr(Expr::Column(left_binding), left_type);
2614 let right_expr = self.plan.add_expr(Expr::Column(right_binding), right_type);
2615 conditions.push(self.compare(rudb_plan::CompareOp::Equal, left_expr, right_expr)?);
2616 dropped.push(right_at);
2617 }
2618 dropped.sort_unstable();
2621 for at in dropped.into_iter().rev() {
2622 scope.remove(at);
2623 }
2624
2625 let mut left_node = left_node;
2626 let mut right_node = right_node;
2627 let mut pair = Vec::new();
2628 if on != NONE {
2629 if !merged.is_empty() {
2630 return Err(Error::binder("a join cannot have both ON and USING"));
2631 }
2632 self.clause = "JOIN condition";
2633 let waiting = self.scalar_subqueries.len();
2634 let predicate = self.bind_expr(ast, on, &scope)?;
2635 conditions.push(self.as_boolean(predicate, "JOIN")?);
2636 for pending in self.scalar_subqueries.split_off(waiting) {
2637 match self.side_of(&pending, &left_tables, &right_tables) {
2638 Some(Side::Right) => right_node = self.attach_subquery(right_node, pending),
2639 Some(Side::Left) => left_node = self.attach_subquery(left_node, pending),
2640 None => pair.push(pending),
2641 }
2642 }
2643 }
2644
2645 if kind == ast::JoinKind::Cross && !conditions.is_empty() {
2646 return Err(Error::binder("a CROSS JOIN cannot have a condition"));
2647 }
2648 if !pair.is_empty() {
2649 return self.bind_pair_dependent_join(
2650 kind,
2651 correlated.is_empty(),
2652 left_node,
2653 right_node,
2654 pair,
2655 conditions,
2656 scope,
2657 );
2658 }
2659 if correlated.is_empty()
2663 && conditions.is_empty()
2664 && matches!(kind, ast::JoinKind::Cross | ast::JoinKind::Inner)
2665 {
2666 let node = self.add_node(Node::CrossProduct { left: left_node, right: right_node });
2667 return Ok((node, scope));
2668 }
2669 if matches!(kind, ast::JoinKind::Semi | ast::JoinKind::Anti) {
2678 scope.truncate(split);
2679 }
2680 let kind = match kind {
2681 ast::JoinKind::Inner | ast::JoinKind::Cross => JoinKind::Inner,
2682 ast::JoinKind::Left => JoinKind::Left,
2683 ast::JoinKind::Right => JoinKind::Right,
2684 ast::JoinKind::Full => JoinKind::Full,
2685 ast::JoinKind::Semi => JoinKind::Semi,
2686 ast::JoinKind::Anti => JoinKind::Anti,
2687 ast::JoinKind::Positional => JoinKind::Positional,
2688 };
2689 let conditions = self.plan.add_expr_list(&conditions);
2690 let node = if correlated.is_empty() {
2691 self.add_node(Node::Join {
2692 left: left_node,
2693 right: right_node,
2694 kind,
2695 conditions,
2696 build: BuildSide::default(),
2697 })
2698 } else {
2699 self.add_node(Node::DependentJoin {
2700 left: left_node,
2701 right: right_node,
2702 kind,
2703 conditions,
2704 })
2705 };
2706 Ok((node, scope))
2707 }
2708
2709 fn bind_filter(
2717 &mut self,
2718 ast: &Ast,
2719 filter: ast::ExprRef,
2720 scope: &Scope,
2721 ) -> Result<Option<ExprRef>> {
2722 if filter == NONE {
2723 return Ok(None);
2724 }
2725 let bound = self.bind_expr(ast, filter, scope)?;
2726 Ok(Some(self.checked_cast_to(bound, &LogicalType::Boolean, false)?))
2727 }
2728
2729 pub(crate) fn bind_aggregate(
2731 &mut self,
2732 ast: &Ast,
2733 name: &str,
2734 args: &[ast::ExprRef],
2735 distinct: bool,
2736 filter: ast::ExprRef,
2737 scope: &Scope,
2738 ) -> Result<ExprRef> {
2739 if self.in_filter {
2740 return Err(Error::binder("aggregate functions are not allowed in FILTER"));
2741 }
2742 if self.in_aggregate {
2743 return Err(Error::binder(format!(
2744 "aggregate function calls cannot be nested, and {name}() is inside one"
2745 )));
2746 }
2747 if self.aggregation.is_none() {
2748 return Err(Error::binder(format!(
2749 "aggregate function calls cannot be used in the {}",
2750 self.clause
2751 )));
2752 }
2753 self.in_aggregate = true;
2758 self.in_filter = true;
2759 let filter = self.bind_filter(ast, filter, scope);
2760 self.in_filter = false;
2761 self.in_aggregate = false;
2762 let filter = filter?;
2763
2764 self.in_aggregate = true;
2765 let mut bound = Vec::with_capacity(args.len());
2766 let mut failure = None;
2767 for &arg in args {
2768 match self.bind_expr(ast, arg, scope) {
2769 Ok(expr) => bound.push(expr),
2770 Err(error) => {
2771 failure = Some(error);
2772 break;
2773 }
2774 }
2775 }
2776 self.in_aggregate = false;
2777 if let Some(error) = failure {
2778 return Err(error);
2779 }
2780
2781 let types: Vec<LogicalType> =
2782 bound.iter().map(|&arg| self.plan.expr_type(arg).clone()).collect();
2783 let resolved = resolve(name, &types)?;
2784 let mut cast = Vec::with_capacity(bound.len());
2785 for (arg, wanted) in bound.iter().zip(&resolved.arguments) {
2786 cast.push(self.checked_cast_to(*arg, wanted, false)?);
2787 }
2788 let args = self.plan.add_expr_list(&cast);
2789 let name = self.plan.intern(resolved.name);
2790 let ty = resolved.returns;
2791 let call = self.plan.add_expr(Expr::Aggregate { name, args, distinct, filter }, ty.clone());
2792
2793 let existing = self.aggregation.as_ref().map(|held| held.aggregates.clone());
2796 let existing = existing.unwrap_or_default();
2797 let at = match existing.iter().position(|&held| self.same_expr(held, call)) {
2798 Some(at) => at,
2799 None => {
2800 let aggregation = self.aggregation.as_mut().expect("checked above");
2801 aggregation.aggregates.push(call);
2802 aggregation.aggregates.len() - 1
2803 }
2804 };
2805 let aggregation = self.aggregation.as_ref().expect("checked above");
2806 let (index, groups) = (aggregation.index, aggregation.groups.len());
2807 Ok(self.column(index, groups + at, ty))
2808 }
2809
2810 pub(crate) fn bind_window(
2818 &mut self,
2819 ast: &Ast,
2820 written: &WindowCall<'_>,
2821 scope: &Scope,
2822 ) -> Result<ExprRef> {
2823 let WindowCall { name, args, distinct, filter, ignore_nulls, spec, .. } = *written;
2824 if self.in_aggregate {
2825 return Err(Error::binder(
2826 "aggregate function calls cannot contain window function calls",
2827 ));
2828 }
2829 if self.in_window {
2830 return Err(Error::binder("window function calls cannot be nested"));
2831 }
2832 let clause = if self.clause == "JOIN condition" { "WHERE clause" } else { self.clause };
2836 if clause != "SELECT clause" && clause != "ORDER BY clause" {
2837 return Err(Error::binder(format!("{clause} cannot contain window functions!")));
2838 }
2839
2840 let starred = args.iter().any(|&arg| {
2844 matches!(ast.expr(arg), ast::Expr::Star { qualifier, replacements }
2845 if qualifier.is_empty() && replacements.is_empty())
2846 });
2847 let (name, args): (&str, &[ast::ExprRef]) = if starred {
2848 if !same_name(name, "count") || args.len() != 1 {
2849 return Err(Error::binder(format!("* is not allowed in {name}()")));
2850 }
2851 ("count_star", &[])
2852 } else if same_name(name, "count") && args.is_empty() {
2853 ("count_star", &[])
2856 } else {
2857 (name, args)
2858 };
2859
2860 let held = ast.window(spec);
2861 self.in_window = true;
2862 let parts = self.window_parts(ast, written, args, held, scope);
2863 let filter = if parts.is_ok() { self.bind_filter(ast, filter, scope) } else { Ok(None) };
2868 self.in_window = false;
2869 let parts = parts?;
2870 let filter = filter?;
2871 let offsets = [parts.frame.start, parts.frame.end]
2874 .iter()
2875 .any(|end| matches!(end, WindowBound::Preceding(_) | WindowBound::Following(_)));
2876 if parts.frame.unit == WindowUnit::Range && offsets && parts.order.len() != 1 {
2877 return Err(Error::binder("RANGE frames must have only one ORDER BY expression"));
2878 }
2879
2880 let types: Vec<LogicalType> =
2881 parts.args.iter().map(|&arg| self.plan.expr_type(arg).clone()).collect();
2882 let resolved = window_signature(name, &types)?;
2883 if resolved.name == "fill" {
2886 let keys: Vec<LogicalType> =
2887 parts.order.iter().map(|key| self.plan.expr_type(key.expr).clone()).collect();
2888 refuse_fill(&types[0], &keys, distinct, ignore_nulls)?;
2889 }
2890 if distinct && kind_of(resolved.name) == Some(FunctionKind::Window) {
2894 return Err(Error::binder(format!(
2895 "DISTINCT is not implemented for the window function \"\"{name}\"\""
2896 )));
2897 }
2898 if filter.is_some() && kind_of(resolved.name) == Some(FunctionKind::Window) {
2901 return Err(Error::binder(format!(
2902 "FILTER is not implemented for the window function \"\"{name}\"\""
2903 )));
2904 }
2905 if !parts.inner.is_empty() && kind_of(resolved.name) == Some(FunctionKind::Window) {
2913 let counts = matches!(resolved.name, "first_value" | "last_value" | "nth_value");
2914 if !counts {
2915 if parts.frame.exclude != WindowExclude::NoOthers {
2916 return Err(Error::binder(format!(
2917 "EXCLUDE is not supported for the window function \"\"{}\"\"",
2918 resolved.name
2919 )));
2920 }
2921 return Err(Error::not_implemented(format!(
2922 "ORDER BY inside the arguments of the window function \"{}\"",
2923 resolved.name
2924 )));
2925 }
2926 }
2927 let mut cast = Vec::with_capacity(parts.args.len());
2928 for (arg, wanted) in parts.args.iter().zip(&resolved.arguments) {
2929 cast.push(self.checked_cast_to(*arg, wanted, false)?);
2930 }
2931 let args = self.plan.add_expr_list(&cast);
2932 let order = self.plan.add_sort_keys(&parts.inner);
2933 let name = self.plan.intern(resolved.name);
2934 let ty = resolved.returns;
2935 let call = self.plan.add_expr(
2936 Expr::Window { name, args, distinct, filter, ignore_nulls, order },
2937 ty.clone(),
2938 );
2939
2940 let at = self.window_run(parts.partition, parts.order, parts.frame, call);
2941 let index = self.windows.last().expect("the run was just filed").index;
2942 Ok(self.column(index, at, ty))
2943 }
2944
2945 fn window_run(
2952 &mut self,
2953 partition: Vec<ExprRef>,
2954 order: Vec<SortKey>,
2955 frame: WindowFrame,
2956 call: ExprRef,
2957 ) -> usize {
2958 let matches = self.windows.last().is_some_and(|run| {
2959 run.frame == frame
2960 && run.partition.len() == partition.len()
2961 && run.order.len() == order.len()
2962 && run.partition.iter().zip(&partition).all(|(&l, &r)| self.same_expr(l, r))
2963 && run.order.iter().zip(&order).all(|(l, r)| {
2964 l.descending == r.descending
2965 && l.nulls_first == r.nulls_first
2966 && self.same_expr(l.expr, r.expr)
2967 })
2968 });
2969 if !matches {
2970 let index = self.fresh_index();
2971 self.windows.push(WindowRun { index, partition, order, frame, calls: Vec::new() });
2972 }
2973 let calls = self.windows.last().expect("a run is open").calls.clone();
2976 if let Some(at) = calls.iter().position(|&held| self.same_expr(held, call)) {
2977 return at;
2978 }
2979 let run = self.windows.last_mut().expect("a run is open");
2980 run.calls.push(call);
2981 run.calls.len() - 1
2982 }
2983
2984 fn window_parts(
2990 &mut self,
2991 ast: &Ast,
2992 written: &WindowCall<'_>,
2993 args: &[ast::ExprRef],
2994 held: ast::WindowSpec,
2995 scope: &Scope,
2996 ) -> Result<WindowParts> {
2997 let mut bound = Vec::with_capacity(args.len());
2998 for &arg in args {
2999 let expr = self.bind_expr(ast, arg, scope)?;
3000 bound.push(self.over_aggregate(expr, scope)?);
3001 }
3002 let mut inner = Vec::new();
3006 for item in ast.order_list(written.order).to_vec() {
3007 let expr = self.bind_expr(ast, item.expr, scope)?;
3008 let expr = self.over_aggregate(expr, scope)?;
3009 inner.push(self.sort_key(expr, item));
3010 }
3011 let mut partition = Vec::new();
3012 for &key in ast.expr_list(held.partition) {
3013 let expr = self.bind_expr(ast, key, scope)?;
3014 partition.push(self.over_aggregate(expr, scope)?);
3015 }
3016 let mut order = Vec::new();
3017 for item in ast.order_list(held.order).to_vec() {
3018 let expr = self.bind_expr(ast, item.expr, scope)?;
3019 let expr = self.over_aggregate(expr, scope)?;
3020 order.push(self.sort_key(expr, item));
3021 }
3022 let frame = WindowFrame {
3023 unit: match held.unit {
3024 ast::WindowUnit::Rows => WindowUnit::Rows,
3025 ast::WindowUnit::Range => WindowUnit::Range,
3026 ast::WindowUnit::Groups => WindowUnit::Groups,
3027 },
3028 start: self.window_bound(ast, held.start, scope)?,
3029 end: self.window_bound(ast, held.end, scope)?,
3030 exclude: match held.exclude {
3031 ast::WindowExclude::NoOthers => WindowExclude::NoOthers,
3032 ast::WindowExclude::CurrentRow => WindowExclude::CurrentRow,
3033 ast::WindowExclude::Group => WindowExclude::Group,
3034 ast::WindowExclude::Ties => WindowExclude::Ties,
3035 },
3036 };
3037 Ok(WindowParts { args: bound, partition, order, inner, frame })
3038 }
3039
3040 fn window_bound(
3042 &mut self,
3043 ast: &Ast,
3044 bound: ast::WindowBound,
3045 scope: &Scope,
3046 ) -> Result<WindowBound> {
3047 let offset = |binder: &mut Self, written| {
3048 let expr = binder.bind_expr(ast, written, scope)?;
3049 binder.over_aggregate(expr, scope)
3050 };
3051 Ok(match bound {
3052 ast::WindowBound::UnboundedPreceding => WindowBound::UnboundedPreceding,
3053 ast::WindowBound::CurrentRow => WindowBound::CurrentRow,
3054 ast::WindowBound::UnboundedFollowing => WindowBound::UnboundedFollowing,
3055 ast::WindowBound::Preceding(written) => WindowBound::Preceding(offset(self, written)?),
3056 ast::WindowBound::Following(written) => WindowBound::Following(offset(self, written)?),
3057 })
3058 }
3059
3060 fn is_pending_subquery(&self, binding: ColumnBinding) -> bool {
3062 self.scalar_subqueries.iter().any(|pending| pending.index == binding.table)
3063 }
3064
3065 fn is_window_output(&self, binding: ColumnBinding) -> bool {
3067 self.windows.iter().any(|run| run.index == binding.table)
3068 }
3069
3070 fn is_correlation(&self, binding: ColumnBinding) -> bool {
3076 self.correlations.last().is_some_and(|frame| frame.contains(&binding))
3077 }
3078
3079 fn name_of(&self, binding: ColumnBinding, scope: &Scope) -> String {
3085 std::iter::once(scope)
3086 .chain(self.outer_scopes.iter().rev())
3087 .flat_map(|visible| visible.columns.iter())
3088 .find(|column| column.binding == binding)
3089 .map_or_else(|| "a column".to_string(), |column| format!("\"{}\"", column.name))
3090 }
3091
3092 pub(crate) fn over_aggregate(&mut self, expr: ExprRef, scope: &Scope) -> Result<ExprRef> {
3098 let Some(aggregation) = self.aggregation.as_ref() else {
3099 return Ok(expr);
3100 };
3101 let index = aggregation.index;
3102 let groups = aggregation.groups.clone();
3103 for (at, group) in groups.iter().enumerate() {
3104 if self.same_expr(expr, *group) {
3105 let ty = self.plan.expr_type(*group).clone();
3106 return Ok(self.column(index, at, ty));
3107 }
3108 }
3109 let ty = self.plan.expr_type(expr).clone();
3110 match self.plan.expr(expr).clone() {
3111 Expr::Column(binding) if binding.table == index => Ok(expr),
3112 Expr::Column(binding) if self.is_window_output(binding) => Ok(expr),
3117 Expr::Column(binding) if self.joined_above.contains(&binding.table) => Ok(expr),
3122 Expr::Column(binding) if self.is_correlation(binding) => Ok(expr),
3128 Expr::Column(binding) if self.is_pending_subquery(binding) => Err(Error::binder(
3137 "a correlated subquery over a grouped query is not supported here yet",
3138 )),
3139 Expr::Column(binding) => {
3140 let name = self.name_of(binding, scope);
3141 Err(Error::binder(format!(
3142 "column {name} must appear in the GROUP BY clause or must be part of an aggregate function"
3143 )))
3144 }
3145 Expr::Constant(_) | Expr::Aggregate { .. } | Expr::Window { .. } => Ok(expr),
3146 Expr::Cast { input, try_cast } => {
3147 let input = self.over_aggregate(input, scope)?;
3148 Ok(self.plan.add_expr(Expr::Cast { input, try_cast }, ty))
3149 }
3150 Expr::Compare { op, left, right } => {
3151 let left = self.over_aggregate(left, scope)?;
3152 let right = self.over_aggregate(right, scope)?;
3153 Ok(self.plan.add_expr(Expr::Compare { op, left, right }, ty))
3154 }
3155 Expr::Conjunction { op, children } => {
3156 let written = self.plan.expr_list(children).to_vec();
3157 let mut rewritten = Vec::with_capacity(written.len());
3158 for child in written {
3159 rewritten.push(self.over_aggregate(child, scope)?);
3160 }
3161 let children = self.plan.add_expr_list(&rewritten);
3162 Ok(self.plan.add_expr(Expr::Conjunction { op, children }, ty))
3163 }
3164 Expr::Function { name, args } => {
3165 let written = self.plan.expr_list(args).to_vec();
3166 let mut rewritten = Vec::with_capacity(written.len());
3167 for arg in written {
3168 rewritten.push(self.over_aggregate(arg, scope)?);
3169 }
3170 let args = self.plan.add_expr_list(&rewritten);
3171 Ok(self.plan.add_expr(Expr::Function { name, args }, ty))
3172 }
3173 Expr::Case { arms, otherwise } => {
3174 let written = self.plan.arm_list(arms).to_vec();
3175 let mut rewritten = Vec::with_capacity(written.len());
3176 for arm in written {
3177 let when = self.over_aggregate(arm.when, scope)?;
3178 let then = self.over_aggregate(arm.then, scope)?;
3179 rewritten.push(rudb_plan::Arm { when, then });
3180 }
3181 let otherwise = match otherwise {
3182 Some(expr) => Some(self.over_aggregate(expr, scope)?),
3183 None => None,
3184 };
3185 let arms = self.plan.add_arms(&rewritten);
3186 Ok(self.plan.add_expr(Expr::Case { arms, otherwise }, ty))
3187 }
3188 }
3189 }
3190
3191 pub(crate) fn same_expr(&self, left: ExprRef, right: ExprRef) -> bool {
3193 same_expr(&self.plan, left, right)
3194 }
3195}
3196
3197#[derive(Debug, Default)]
3207struct Options {
3208 binary_as_string: bool,
3211 all_varchar: bool,
3213 file_row_number: bool,
3218 given: Given,
3220}
3221
3222impl Options {
3223 fn of(written: &[(&'static str, Value, ExprRef)]) -> Result<Self> {
3230 let mut options = Self::default();
3231 for (parameter, value, _) in written {
3232 match (*parameter, value) {
3233 ("binary_as_string", Value::Boolean(on)) => options.binary_as_string = *on,
3234 ("all_varchar", Value::Boolean(on)) => options.all_varchar = *on,
3235 ("file_row_number", Value::Boolean(on)) => options.file_row_number = *on,
3236 _ => {}
3237 }
3238 }
3239 let named: Vec<(&str, Value)> =
3240 written.iter().map(|(parameter, value, _)| (*parameter, value.clone())).collect();
3241 options.given = csv_given(&named)?;
3242 Ok(options)
3243 }
3244}
3245
3246#[derive(Clone, Copy)]
3248struct Operator {
3249 op: SetOp,
3251 quantifier: Quantifier,
3253 by_name: bool,
3255}
3256
3257struct Merged {
3259 name: String,
3261 ty: LogicalType,
3263 left: Option<usize>,
3265 right: Option<usize>,
3267}
3268
3269fn match_by_position(left: &Scope, right: &Scope) -> Result<Vec<Merged>> {
3273 if left.len() != right.len() {
3274 return Err(Error::binder(format!(
3275 "Set operations can only apply to expressions with the same number of result columns, but left side has {} and right side has {}",
3276 left.len(),
3277 right.len()
3278 )));
3279 }
3280 let mut merged = Vec::with_capacity(left.len());
3281 for (at, (held, other)) in left.columns.iter().zip(&right.columns).enumerate() {
3282 merged.push(Merged {
3283 name: held.name.clone(),
3284 ty: meet(&held.ty, &other.ty)?,
3285 left: Some(at),
3286 right: Some(at),
3287 });
3288 }
3289 Ok(merged)
3290}
3291
3292fn match_by_name(left: &Scope, right: &Scope) -> Result<Vec<Merged>> {
3300 named_once(left)?;
3301 named_once(right)?;
3302 let mut merged = Vec::with_capacity(left.len() + right.len());
3303 for (at, held) in left.columns.iter().enumerate() {
3304 let other = right.columns.iter().position(|column| same_name(&column.name, &held.name));
3305 let ty = match other {
3306 Some(other) => meet(&held.ty, &right.columns[other].ty)?,
3307 None => held.ty.clone(),
3308 };
3309 merged.push(Merged { name: held.name.clone(), ty, left: Some(at), right: other });
3310 }
3311 for (at, held) in right.columns.iter().enumerate() {
3312 if left.columns.iter().any(|column| same_name(&column.name, &held.name)) {
3313 continue;
3314 }
3315 merged.push(Merged {
3316 name: held.name.clone(),
3317 ty: held.ty.clone(),
3318 left: None,
3319 right: Some(at),
3320 });
3321 }
3322 Ok(merged)
3323}
3324
3325fn named_once(scope: &Scope) -> Result<()> {
3331 for (at, held) in scope.columns.iter().enumerate() {
3332 if scope.columns[..at].iter().any(|column| same_name(&column.name, &held.name)) {
3333 return Err(Error::binder(format!(
3334 "UNION (ALL) BY NAME operation doesn't support duplicate names in the SELECT list - the name \"\"{}\"\" occurs multiple times",
3335 held.name
3336 )));
3337 }
3338 }
3339 Ok(())
3340}
3341
3342fn meet(left: &LogicalType, right: &LogicalType) -> Result<LogicalType> {
3344 left.promote(right).ok_or_else(|| {
3345 Error::binder(format!(
3346 "Cannot combine a column of type {left} with a column of type {right} in a set operation"
3347 ))
3348 })
3349}
3350
3351fn null_parameter(function: TableFunction, parameter: &str) -> String {
3360 match parameter {
3361 "header" => format!("\"{parameter}\" expects a non-null boolean value (e.g. TRUE or 1)"),
3362 "all_varchar" => format!("{} \"{parameter}\" cannot be NULL", function.name()),
3363 _ => format!("Cannot use NULL as argument to \"{parameter}\""),
3364 }
3365}
3366
3367fn missing_replacement(name: &str, input: &Scope) -> Error {
3372 Error::binder(format!(
3373 "Column \"{name}\" in REPLACE list not found in FROM clause{}",
3374 input.candidates()
3375 ))
3376}
3377
3378fn subtractable(ty: &LogicalType, ordering: bool) -> bool {
3387 if ty.is_numeric() {
3388 return true;
3389 }
3390 match ty {
3391 LogicalType::Date
3392 | LogicalType::Time
3393 | LogicalType::Timestamp
3394 | LogicalType::TimestampS
3395 | LogicalType::TimestampMs
3396 | LogicalType::TimestampNs
3397 | LogicalType::TimestampTz => true,
3398 LogicalType::TimeTz => ordering,
3399 _ => false,
3400 }
3401}
3402
3403fn refuse_fill(
3412 argument: &LogicalType,
3413 order: &[LogicalType],
3414 distinct: bool,
3415 ignore_nulls: bool,
3416) -> Result<()> {
3417 if !subtractable(argument, false) {
3418 return Err(Error::binder("FILL argument must support subtraction"));
3419 }
3420 let [key] = order else {
3421 return Err(Error::binder("FILL functions must have only one ORDER BY expression"));
3422 };
3423 if !subtractable(key, true) {
3424 return Err(Error::binder("FILL ordering must support subtraction"));
3425 }
3426 if distinct {
3427 return Err(Error::binder(
3428 "DISTINCT is not implemented for the window function \"\"fill\"\"",
3429 ));
3430 }
3431 if ignore_nulls {
3432 return Err(Error::binder(
3433 "RESPECT/IGNORE NULLS is not supported for the window function \"fill\"",
3434 ));
3435 }
3436 Ok(())
3437}
3438
3439fn window_signature(name: &str, types: &[LogicalType]) -> Result<Resolved> {
3446 match kind_of(name) {
3447 Some(FunctionKind::Aggregate | FunctionKind::Window) => resolve(name, types),
3448 Some(FunctionKind::Scalar) => {
3449 Err(Error::catalog(format!("{name} is not an aggregate function")))
3450 }
3451 None => Err(Error::catalog(format!("Aggregate Function with name {name} does not exist!"))),
3452 }
3453}
3454
3455fn same_expr(plan: &Plan, left: ExprRef, right: ExprRef) -> bool {
3457 if left == right {
3458 return true;
3459 }
3460 if plan.expr_type(left) != plan.expr_type(right) {
3461 return false;
3462 }
3463 let lists = |left, right| {
3464 let left: &[ExprRef] = plan.expr_list(left);
3465 let right: &[ExprRef] = plan.expr_list(right);
3466 left.len() == right.len()
3467 && left.iter().zip(right).all(|(&left, &right)| same_expr(plan, left, right))
3468 };
3469 match (plan.expr(left), plan.expr(right)) {
3470 (Expr::Column(left), Expr::Column(right)) => left == right,
3471 (Expr::Constant(left), Expr::Constant(right)) => plan.value(*left) == plan.value(*right),
3472 (
3473 Expr::Cast { input: left, try_cast: left_try },
3474 Expr::Cast { input: right, try_cast: right_try },
3475 ) => left_try == right_try && same_expr(plan, *left, *right),
3476 (
3477 Expr::Compare { op: left_op, left: left_a, right: left_b },
3478 Expr::Compare { op: right_op, left: right_a, right: right_b },
3479 ) => {
3480 left_op == right_op
3481 && same_expr(plan, *left_a, *right_a)
3482 && same_expr(plan, *left_b, *right_b)
3483 }
3484 (
3485 Expr::Conjunction { op: left_op, children: left_children },
3486 Expr::Conjunction { op: right_op, children: right_children },
3487 ) => left_op == right_op && lists(*left_children, *right_children),
3488 (
3489 Expr::Function { name: left_name, args: left_args },
3490 Expr::Function { name: right_name, args: right_args },
3491 ) => plan.string(*left_name) == plan.string(*right_name) && lists(*left_args, *right_args),
3492 (
3493 Expr::Aggregate {
3494 name: left_name,
3495 args: left_args,
3496 distinct: left_distinct,
3497 filter: left_filter,
3498 },
3499 Expr::Aggregate {
3500 name: right_name,
3501 args: right_args,
3502 distinct: right_distinct,
3503 filter: right_filter,
3504 },
3505 ) => {
3506 plan.string(*left_name) == plan.string(*right_name)
3507 && left_distinct == right_distinct
3508 && match (left_filter, right_filter) {
3509 (None, None) => true,
3510 (Some(left), Some(right)) => same_expr(plan, *left, *right),
3511 _ => false,
3512 }
3513 && lists(*left_args, *right_args)
3514 }
3515 (
3519 Expr::Window {
3520 name: left_name,
3521 args: left_args,
3522 distinct: left_distinct,
3523 filter: left_filter,
3524 ignore_nulls: left_nulls,
3525 order: left_order,
3526 },
3527 Expr::Window {
3528 name: right_name,
3529 args: right_args,
3530 distinct: right_distinct,
3531 filter: right_filter,
3532 ignore_nulls: right_nulls,
3533 order: right_order,
3534 },
3535 ) => {
3536 let left_keys = plan.sort_key_list(*left_order);
3539 let right_keys = plan.sort_key_list(*right_order);
3540 plan.string(*left_name) == plan.string(*right_name)
3541 && left_distinct == right_distinct
3542 && left_nulls == right_nulls
3543 && left_keys.len() == right_keys.len()
3544 && left_keys.iter().zip(right_keys).all(|(left, right)| {
3545 left.descending == right.descending
3546 && left.nulls_first == right.nulls_first
3547 && same_expr(plan, left.expr, right.expr)
3548 })
3549 && match (left_filter, right_filter) {
3550 (None, None) => true,
3551 (Some(left), Some(right)) => same_expr(plan, *left, *right),
3552 _ => false,
3553 }
3554 && lists(*left_args, *right_args)
3555 }
3556 (
3557 Expr::Case { arms: left_arms, otherwise: left_otherwise },
3558 Expr::Case { arms: right_arms, otherwise: right_otherwise },
3559 ) => {
3560 let left_arms = plan.arm_list(*left_arms);
3561 let right_arms = plan.arm_list(*right_arms);
3562 left_arms.len() == right_arms.len()
3563 && left_arms.iter().zip(right_arms).all(|(left, right)| {
3564 same_expr(plan, left.when, right.when) && same_expr(plan, left.then, right.then)
3565 })
3566 && match (left_otherwise, right_otherwise) {
3567 (None, None) => true,
3568 (Some(left), Some(right)) => same_expr(plan, *left, *right),
3569 _ => false,
3570 }
3571 }
3572 _ => false,
3573 }
3574}