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::{cast_value, 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, 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) spec: ast::WindowRef,
147}
148
149struct WindowParts {
151 args: Vec<ExprRef>,
153 partition: Vec<ExprRef>,
155 order: Vec<SortKey>,
157 frame: WindowFrame,
159}
160
161#[derive(Debug)]
168struct Read {
169 fields: Vec<Field>,
171 rows: Stat<u64>,
173 distincts: Vec<(String, Stat<u64>)>,
175 zones: Option<Arc<dyn Zones>>,
177}
178
179impl Read {
180 fn uncounted(fields: Vec<Field>) -> Self {
182 Self { fields, rows: Stat::Unknown, distincts: Vec::new(), zones: None }
183 }
184}
185
186#[derive(Debug)]
188struct Materialized {
189 written: u32,
191 cte: u32,
193 name: String,
195 fields: Vec<Field>,
197}
198
199#[derive(Debug)]
200pub(crate) struct PendingSubquery {
201 pub(crate) node: NodeRef,
202 pub(crate) kind: JoinKind,
203 pub(crate) conditions: Vec<ExprRef>,
204 pub(crate) dependent: bool,
205 pub(crate) reads: Vec<ColumnBinding>,
211 pub(crate) index: u32,
217 pub(crate) inside_aggregate: bool,
224}
225
226#[derive(Debug, Clone, Copy, PartialEq, Eq)]
228enum Side {
229 Left,
230 Right,
231}
232
233#[derive(Debug)]
235pub(crate) struct Binder<'a> {
236 catalog: &'a Catalog,
237 pub(crate) parameters: &'a Parameters,
239 pub(crate) session: &'a Session,
241 pub(crate) semantics: Semantics,
243 plan: Plan,
244 next_index: u32,
245 pub(crate) current_span: Span,
247 pub(crate) aggregation: Option<Aggregation>,
249 pub(crate) in_aggregate: bool,
251 pub(crate) in_filter: bool,
253 pub(crate) windows: Vec<WindowRun>,
255 pub(crate) in_window: bool,
257 pub(crate) scalar_subqueries: Vec<PendingSubquery>,
259 pub(crate) joined_above: Vec<u32>,
265 pub(crate) outer_scopes: Vec<Scope>,
266 pub(crate) lateral_scopes: Vec<usize>,
273 pub(crate) correlations: Vec<Vec<ColumnBinding>>,
274 pub(crate) clause: &'static str,
276 expanding: Vec<String>,
278 materialized: Vec<Materialized>,
284 next_cte: u32,
286 started: Option<i64>,
288}
289
290impl<'a> Binder<'a> {
291 pub(crate) fn with(
292 catalog: &'a Catalog,
293 parameters: &'a Parameters,
294 session: &'a Session,
295 ) -> Self {
296 Self {
297 catalog,
298 parameters,
299 session,
300 semantics: session.semantics(),
301 plan: Plan::new(),
302 next_index: 0,
303 current_span: Span::new(0, 0),
304 aggregation: None,
305 in_aggregate: false,
306 in_filter: false,
307 windows: Vec::new(),
308 in_window: false,
309 scalar_subqueries: Vec::new(),
310 joined_above: Vec::new(),
311 outer_scopes: Vec::new(),
312 lateral_scopes: Vec::new(),
313 correlations: Vec::new(),
314 clause: "SELECT clause",
315 expanding: Vec::new(),
316 materialized: Vec::new(),
317 next_cte: 0,
318 started: None,
319 }
320 }
321
322 pub(crate) fn catalog(&self) -> &Catalog {
323 self.catalog
324 }
325
326 pub(crate) fn instant(&mut self) -> i64 {
333 *self.started.get_or_insert_with(crate::context::micros_now)
334 }
335
336 pub(crate) fn plan(&self) -> &Plan {
337 &self.plan
338 }
339
340 pub(crate) fn plan_mut(&mut self) -> &mut Plan {
341 &mut self.plan
342 }
343
344 pub(crate) fn add_expr(&mut self, expr: Expr, ty: LogicalType) -> ExprRef {
345 self.plan.add_expr_at(expr, ty, self.current_span)
346 }
347
348 pub(crate) fn add_constant(&mut self, value: Value) -> ExprRef {
349 let ty = value.logical_type();
350 let reference = self.plan.add_value(value);
351 self.plan.add_expr_at(Expr::Constant(reference), ty, self.current_span)
352 }
353
354 pub(crate) fn add_node(&mut self, node: Node) -> NodeRef {
355 self.plan.add_node_at(node, self.current_span)
356 }
357
358 pub(crate) fn into_plan(self) -> Plan {
359 self.plan
360 }
361
362 pub(crate) fn fresh_index(&mut self) -> u32 {
364 let index = self.next_index;
365 self.next_index += 1;
366 index
367 }
368
369 fn column(&mut self, index: u32, position: usize, ty: LogicalType) -> ExprRef {
371 let binding = ColumnBinding::new(index, position as u32);
372 self.plan.add_expr(Expr::Column(binding), ty)
373 }
374
375 fn attach_scalar_subqueries(&mut self, mut input: NodeRef) -> NodeRef {
377 let subqueries = std::mem::take(&mut self.scalar_subqueries);
378 for pending in subqueries {
379 input = self.attach_subquery(input, pending);
380 }
381 input
382 }
383
384 fn attach_subquery(&mut self, input: NodeRef, pending: PendingSubquery) -> NodeRef {
391 let PendingSubquery {
392 node: mut right,
393 kind,
394 conditions,
395 dependent,
396 reads: _,
397 index: _,
398 inside_aggregate: _,
399 } = pending;
400 if kind == JoinKind::Single && !self.semantics.scalar_subquery_error_on_multiple_rows() {
401 right = self.add_node(Node::Limit {
402 input: right,
403 count: Bound::Rows(1),
404 offset: Bound::Rows(0),
405 });
406 }
407 let conditions = self.plan.add_expr_list(&conditions);
408 if dependent {
409 self.add_node(Node::DependentJoin { left: input, right, kind, conditions })
410 } else {
411 self.add_node(Node::Join {
412 left: input,
413 right,
414 kind,
415 conditions,
416 build: BuildSide::default(),
417 })
418 }
419 }
420
421 pub(crate) fn bind_query(
424 &mut self,
425 ast: &Ast,
426 query: ast::QueryRef,
427 ) -> Result<(NodeRef, Scope)> {
428 let span = ast.query_span(query);
429 let outer = std::mem::replace(&mut self.current_span, span);
430 let result =
431 self.bind_query_inner(ast, query).map_err(|error| error.with_fallback_span(span));
432 self.current_span = outer;
433 result
434 }
435
436 fn bind_query_inner(&mut self, ast: &Ast, query: ast::QueryRef) -> Result<(NodeRef, Scope)> {
437 let written = ast.query(query);
438 if written.ctes.is_empty() {
439 return self.bind_body(ast, &written);
440 }
441 let depth = self.materialized.len();
445 let result = self.bind_materialized(ast, &written);
446 self.materialized.truncate(depth);
447 result
448 }
449
450 fn bind_materialized(&mut self, ast: &Ast, written: &ast::Query) -> Result<(NodeRef, Scope)> {
456 let depth = self.materialized.len();
457 let held = ast.cte_list(written.ctes).to_vec();
458 let mut definitions = Vec::with_capacity(held.len());
459 for &index in &held {
460 definitions.push(self.bind_definition(ast, index)?);
461 }
462 let (mut node, scope) = self.bind_body(ast, written)?;
463 for (at, definition) in definitions.into_iter().enumerate().rev() {
464 let entry = &self.materialized[depth + at];
465 let cte = entry.cte;
466 let name = entry.name.clone();
467 let fields = entry.fields.clone();
468 let name = self.plan.intern(&name);
469 let columns = self.plan.add_fields(&fields);
470 node =
471 self.add_node(Node::MaterializedCte { definition, body: node, name, cte, columns });
472 }
473 Ok((node, scope))
474 }
475
476 fn bind_definition(&mut self, ast: &Ast, index: u32) -> Result<NodeRef> {
486 let held = ast.cte(index);
487 let name = ast.string(held.name).to_string();
488 let (node, mut scope) = self.bind_query(ast, held.query)?;
489 if !held.columns.is_empty() {
490 let names: Vec<&str> = ast.name(held.columns).collect();
491 scope.rename_prefix(&names);
492 }
493 let table = self.fresh_index();
494 let mut exprs = Vec::with_capacity(scope.len());
495 let mut names = Vec::with_capacity(scope.len());
496 for column in &scope.columns {
497 exprs.push(self.plan.add_expr(Expr::Column(column.binding), column.ty.clone()));
498 names.push(self.plan.intern(&column.name));
499 }
500 let exprs = self.plan.add_expr_list(&exprs);
501 let names = self.plan.add_name_list(&names);
502 let node = self.add_node(Node::Project { input: node, index: table, exprs, names });
503 let cte = self.next_cte;
504 self.next_cte += 1;
505 self.materialized.push(Materialized { written: index, cte, name, fields: scope.fields() });
506 Ok(node)
507 }
508
509 fn bind_body(&mut self, ast: &Ast, written: &ast::Query) -> Result<(NodeRef, Scope)> {
510 match written.body {
511 ast::QueryBody::Select(select) => self.bind_select(ast, select, written),
512 ast::QueryBody::SetOp { op, quantifier, by_name, left, right } => {
513 let operator = Operator { op, quantifier, by_name };
514 self.bind_set_op(ast, written, operator, left, right)
515 }
516 ast::QueryBody::Values(rows) => self.bind_values(ast, written, rows),
517 ast::QueryBody::Describe(inner) => self.bind_describe(ast, written, inner),
518 ast::QueryBody::Show { name, relation } => self.bind_show(ast, written, name, relation),
519 }
520 }
521
522 fn bind_show(
524 &mut self,
525 ast: &Ast,
526 query: &ast::Query,
527 name: ast::Slice,
528 relation: ast::QueryRef,
529 ) -> Result<(NodeRef, Scope)> {
530 let text = ast.name_text(name);
531 let parts: Vec<&str> = ast.name(name).collect();
532 let table_exists = self.catalog.resolve(&parts).is_ok();
533 let as_table = match self.semantics.show_behavior() {
534 ShowBehavior::Auto => table_exists,
535 ShowBehavior::Setting => false,
536 ShowBehavior::Table => true,
537 };
538 if as_table {
539 return self.bind_describe(ast, query, relation);
540 }
541 let Some((_, value)) =
542 self.session.iter().find(|(name, _)| name.eq_ignore_ascii_case(&text))
543 else {
544 return Err(Error::catalog(format!("Setting with name \"{text}\" does not exist")));
545 };
546 let field = Field::new(text, LogicalType::Varchar);
547 let expr = self.plan.add_constant(Value::Varchar(value.to_string()));
548 let row = self.plan.add_expr_list(&[expr]);
549 let rows = self.plan.add_rows(&[row]);
550 let columns = self.plan.add_fields(std::slice::from_ref(&field));
551 let index = self.fresh_index();
552 let node = self.add_node(Node::Values { index, columns, rows });
553 let mut scope = Scope::empty();
554 scope.push(Visible {
555 table: String::new(),
556 name: field.name,
557 binding: ColumnBinding::new(index, 0),
558 ty: LogicalType::Varchar,
559 not_null: false,
560 });
561 Ok((node, scope))
562 }
563
564 fn bind_describe(
580 &mut self,
581 ast: &Ast,
582 query: &ast::Query,
583 inner: ast::QueryRef,
584 ) -> Result<(NodeRef, Scope)> {
585 let (_, described) = self.bind_query(ast, inner)?;
586 let fields: Vec<Field> = ["column_name", "column_type", "null", "key", "default", "extra"]
587 .iter()
588 .map(|name| Field::new(*name, LogicalType::Varchar))
589 .collect();
590 let mut slices = Vec::with_capacity(described.columns.len());
591 for column in described.columns.clone() {
592 let written = [
595 column.name.clone(),
596 column.ty.to_string(),
597 if column.not_null { "NO" } else { "YES" }.to_owned(),
598 ];
599 let mut items: Vec<ExprRef> = written
600 .into_iter()
601 .map(|text| self.plan.add_constant(Value::Varchar(text)))
602 .collect();
603 for _ in 0..3 {
604 let empty = self.plan.add_constant(Value::Null);
605 items.push(self.cast_to(empty, &LogicalType::Varchar));
606 }
607 slices.push(self.plan.add_expr_list(&items));
608 }
609 let rows = self.plan.add_rows(&slices);
610 let columns = self.plan.add_fields(&fields);
611 let index = self.fresh_index();
612 let mut node = self.add_node(Node::Values { index, columns, rows });
613 let mut scope = Scope::empty();
614 for (at, field) in fields.iter().enumerate() {
615 scope.push(Visible {
616 table: String::new(),
617 name: field.name.clone(),
618 binding: ColumnBinding::new(index, at as u32),
619 ty: field.ty.clone(),
620 not_null: false,
621 });
622 }
623 let keys = self.sort_keys(ast, query, &scope, &[])?;
624 if !keys.is_empty() {
625 let keys = self.plan.add_sort_keys(&keys);
626 node = self.add_node(Node::Sort { input: node, keys });
627 }
628 node = self.apply_limit(ast, query, node, &mut scope)?;
629 Ok((node, scope))
630 }
631
632 fn passes_through(&self, expr: ExprRef, input: &Scope) -> bool {
638 let Expr::Column(binding) = *self.plan.expr(expr) else { return false };
639 input.columns.iter().any(|column| column.binding == binding && column.not_null)
640 }
641
642 fn bind_values(
649 &mut self,
650 ast: &Ast,
651 query: &ast::Query,
652 rows: ast::Slice,
653 ) -> Result<(NodeRef, Scope)> {
654 let written = ast.rows(rows).to_vec();
655 let Some(first) = written.first() else {
656 return Err(Error::binder("VALUES needs at least one row"));
657 };
658 let width = first.len as usize;
659 for (at, row) in written.iter().enumerate() {
660 if row.len as usize != width {
661 return Err(Error::binder(format!(
662 "VALUES lists must all be the same length, expected {width} columns but row {} has {}",
663 at + 1,
664 row.len
665 )));
666 }
667 }
668 let empty = Scope::empty();
670 let previous = std::mem::replace(&mut self.clause, "VALUES clause");
671 let mut bound: Vec<Vec<ExprRef>> = Vec::with_capacity(written.len());
672 for row in &written {
673 let mut items = Vec::with_capacity(width);
674 for &expr in ast.expr_list(*row) {
675 items.push(self.bind_expr(ast, expr, &empty)?);
676 }
677 bound.push(items);
678 }
679 self.clause = previous;
680 let mut types = Vec::with_capacity(width);
681 for at in 0..width {
682 let mut ty = self.plan.expr_type(bound[0][at]).clone();
683 for row in &bound[1..] {
684 let other = self.plan.expr_type(row[at]).clone();
685 ty = ty.promote(&other).ok_or_else(|| {
686 Error::binder(format!(
687 "Cannot combine a value of type {ty} with a value of type {other} in column {} of a VALUES",
688 at + 1
689 ))
690 })?;
691 }
692 types.push(ty);
693 }
694 let mut slices = Vec::with_capacity(bound.len());
695 for row in &bound {
696 let items: Vec<ExprRef> = row
697 .iter()
698 .zip(&types)
699 .map(|(&expr, ty)| self.checked_cast_to(expr, ty, false))
700 .collect::<Result<_>>()?;
701 slices.push(self.plan.add_expr_list(&items));
702 }
703 let rows = self.plan.add_rows(&slices);
704 let fields: Vec<Field> = types
705 .iter()
706 .enumerate()
707 .map(|(at, ty)| Field::new(format!("col{at}"), ty.clone()))
708 .collect();
709 let columns = self.plan.add_fields(&fields);
710 let index = self.fresh_index();
711 let mut node = self.add_node(Node::Values { index, columns, rows });
712 let mut scope = Scope::empty();
713 for (at, field) in fields.iter().enumerate() {
714 scope.push(Visible {
715 table: String::new(),
716 name: field.name.clone(),
717 binding: ColumnBinding::new(index, at as u32),
718 ty: field.ty.clone(),
719 not_null: false,
720 });
721 }
722 let keys = self.sort_keys(ast, query, &scope, &[])?;
723 if !keys.is_empty() {
724 let keys = self.plan.add_sort_keys(&keys);
725 node = self.add_node(Node::Sort { input: node, keys });
726 }
727 node = self.apply_limit(ast, query, node, &mut scope)?;
728 Ok((node, scope))
729 }
730
731 fn bind_set_op(
732 &mut self,
733 ast: &Ast,
734 query: &ast::Query,
735 operator: Operator,
736 left: ast::QueryRef,
737 right: ast::QueryRef,
738 ) -> Result<(NodeRef, Scope)> {
739 let (left_node, left_scope) = self.bind_query(ast, left)?;
740 let (right_node, right_scope) = self.bind_query(ast, right)?;
741 let merged = if operator.by_name {
742 match_by_name(&left_scope, &right_scope)?
743 } else {
744 match_by_position(&left_scope, &right_scope)?
745 };
746 let left_node = self.conform(left_node, &left_scope, &merged, |column| column.left)?;
747 let right_node = self.conform(right_node, &right_scope, &merged, |column| column.right)?;
748 let index = self.fresh_index();
749 let kind = match operator.op {
750 SetOp::Union => SetOpKind::Union,
751 SetOp::Except => SetOpKind::Except,
752 SetOp::Intersect => SetOpKind::Intersect,
753 };
754 let all = operator.quantifier == Quantifier::All;
757 let mut node =
758 self.add_node(Node::SetOp { left: left_node, right: right_node, kind, all, index });
759 let mut scope = Scope::empty();
760 for (at, column) in merged.iter().enumerate() {
761 scope.push(Visible {
762 table: String::new(),
763 name: column.name.clone(),
764 binding: ColumnBinding::new(index, at as u32),
765 ty: column.ty.clone(),
766 not_null: false,
769 });
770 }
771 let keys = self.sort_keys(ast, query, &scope, &[])?;
775 if !keys.is_empty() {
776 let keys = self.plan.add_sort_keys(&keys);
777 node = self.add_node(Node::Sort { input: node, keys });
778 }
779 node = self.apply_limit(ast, query, node, &mut scope)?;
780 Ok((node, scope))
781 }
782
783 fn conform(
789 &mut self,
790 node: NodeRef,
791 scope: &Scope,
792 merged: &[Merged],
793 pick: impl Fn(&Merged) -> Option<usize>,
794 ) -> Result<NodeRef> {
795 let unchanged = merged.len() == scope.len()
796 && merged
797 .iter()
798 .enumerate()
799 .all(|(at, column)| pick(column) == Some(at) && column.ty == scope.columns[at].ty);
800 if unchanged {
801 return Ok(node);
802 }
803 let index = self.fresh_index();
804 let mut exprs = Vec::with_capacity(merged.len());
805 let mut names = Vec::with_capacity(merged.len());
806 for column in merged {
807 let expr = match pick(column) {
808 Some(at) => {
809 let held = &scope.columns[at];
810 self.plan.add_expr(Expr::Column(held.binding), held.ty.clone())
811 }
812 None => self.plan.add_constant(Value::Null),
813 };
814 exprs.push(self.checked_cast_to(expr, &column.ty, false)?);
815 names.push(self.plan.intern(&column.name));
816 }
817 let exprs = self.plan.add_expr_list(&exprs);
818 let names = self.plan.add_name_list(&names);
819 Ok(self.add_node(Node::Project { input: node, index, exprs, names }))
820 }
821
822 fn bind_select(
825 &mut self,
826 ast: &Ast,
827 select: ast::SelectRef,
828 query: &ast::Query,
829 ) -> Result<(NodeRef, Scope)> {
830 let written = ast.select(select);
831 let outer_windows = std::mem::take(&mut self.windows);
835 let outer_joined_above = std::mem::take(&mut self.joined_above);
840 let (mut node, input) = self.bind_from(ast, written.from)?;
841 node = self.attach_scalar_subqueries(node);
842
843 if written.filter != NONE {
844 self.clause = "WHERE clause";
845 let predicate = self.bind_expr(ast, written.filter, &input)?;
846 let predicate = self.as_boolean(predicate, "WHERE")?;
847 node = self.attach_scalar_subqueries(node);
848 node = self.add_node(Node::Filter { input: node, predicate });
849 }
850
851 let targets = ast.target_list(written.targets).to_vec();
852 if targets.is_empty() {
853 return Err(Error::binder("a SELECT needs at least one expression to select"));
854 }
855
856 let group_items = self.group_items(ast, &written, &targets)?;
857 let aggregating = !group_items.is_empty()
858 || written.having != NONE
859 || targets.iter().any(|target| has_aggregate(ast, target.expr));
860 if aggregating {
861 self.clause = "GROUP BY clause";
862 let mut groups = Vec::with_capacity(group_items.len());
863 for item in &group_items {
864 groups.push(self.bind_expr(ast, *item, &input)?);
865 }
866 let index = self.fresh_index();
867 self.aggregation = Some(Aggregation { index, groups, aggregates: Vec::new() });
868 }
869
870 let mut above = Vec::new();
877
878 self.clause = "SELECT clause";
879 let (mut exprs, mut names) = self.bind_targets(ast, &targets, &input, &mut above)?;
880 let visible = exprs.len();
881
882 let mut having = None;
883 if written.having != NONE {
884 self.clause = "HAVING clause";
885 let before = self.scalar_subqueries.len();
886 let predicate = self.bind_expr(ast, written.having, &input)?;
887 self.lift_over_aggregate(before, &mut above, &input)?;
888 let predicate = self.over_aggregate(predicate, &input)?;
889 having = Some(self.as_boolean(predicate, "HAVING")?);
890 }
891
892 let project = self.fresh_index();
895 let mut output = Scope::empty();
896 for (at, (expr, name)) in exprs.iter().zip(&names).enumerate() {
897 output.push(Visible {
898 table: String::new(),
899 name: name.clone(),
900 binding: ColumnBinding::new(project, at as u32),
901 ty: self.plan.expr_type(*expr).clone(),
902 not_null: self.passes_through(*expr, &input),
903 });
904 }
905
906 self.clause = "ORDER BY clause";
907 let mut extra = Vec::new();
908 let keys = self.select_sort_keys(
909 ast, query, &input, &output, project, &mut exprs, &mut names, &mut extra, &mut above,
910 )?;
911 self.joined_above = outer_joined_above;
912 if !extra.is_empty() && written.distinct != Distinct::No {
913 return Err(Error::binder(
914 "For SELECT DISTINCT, ORDER BY expressions must appear in the select list",
915 ));
916 }
917 let on = self.distinct_on(ast, written.distinct, &output)?;
918
919 node = self.attach_scalar_subqueries(node);
920
921 if let Some(aggregation) = self.aggregation.take() {
922 let index = aggregation.index;
923 let groups = self.plan.add_expr_list(&aggregation.groups);
924 let aggregates = self.plan.add_expr_list(&aggregation.aggregates);
925 node = self.add_node(Node::Aggregate { input: node, index, groups, aggregates });
926 }
927 if !above.is_empty() {
928 debug_assert!(self.scalar_subqueries.is_empty(), "a query is waiting to be joined");
929 self.scalar_subqueries = above;
930 node = self.attach_scalar_subqueries(node);
931 }
932 if let Some(predicate) = having {
933 node = self.add_node(Node::Filter { input: node, predicate });
934 }
935
936 for run in std::mem::replace(&mut self.windows, outer_windows) {
940 let partition = self.plan.add_expr_list(&run.partition);
941 let order = self.plan.add_sort_keys(&run.order);
942 let expressions = self.plan.add_expr_list(&run.calls);
943 node = self.add_node(Node::Window {
944 input: node,
945 index: run.index,
946 partition,
947 order,
948 frame: run.frame,
949 expressions,
950 });
951 }
952
953 let interned: Vec<u32> = names.iter().map(|name| self.plan.intern(name)).collect();
954 let exprs_slice = self.plan.add_expr_list(&exprs);
955 let names_slice = self.plan.add_name_list(&interned);
956 node = self.add_node(Node::Project {
957 input: node,
958 index: project,
959 exprs: exprs_slice,
960 names: names_slice,
961 });
962
963 if written.distinct != Distinct::No {
964 let on = self.plan.add_expr_list(&on);
965 node = self.add_node(Node::Distinct { input: node, on });
966 }
967 if !keys.is_empty() {
968 let keys = self.plan.add_sort_keys(&keys);
969 node = self.add_node(Node::Sort { input: node, keys });
970 }
971 node = self.apply_limit(ast, query, node, &mut output)?;
972
973 if extra.is_empty() {
974 output.columns.truncate(visible);
975 return Ok((node, output));
976 }
977 let index = self.fresh_index();
980 let mut kept = Vec::with_capacity(visible);
981 let mut kept_names = Vec::with_capacity(visible);
982 let mut scope = Scope::empty();
983 for (at, name) in names.iter().enumerate().take(visible) {
984 let ty = output.columns[at].ty.clone();
985 let binding = output.columns[at].binding;
989 kept.push(self.plan.add_expr(Expr::Column(binding), ty.clone()));
990 kept_names.push(self.plan.intern(name));
991 scope.push(Visible {
992 table: String::new(),
993 name: name.clone(),
994 binding: ColumnBinding::new(index, at as u32),
995 ty,
996 not_null: output.columns[at].not_null,
997 });
998 }
999 let exprs = self.plan.add_expr_list(&kept);
1000 let names = self.plan.add_name_list(&kept_names);
1001 node = self.add_node(Node::Project { input: node, index, exprs, names });
1002 Ok((node, scope))
1003 }
1004
1005 fn lift_over_aggregate(
1023 &mut self,
1024 before: usize,
1025 above: &mut Vec<PendingSubquery>,
1026 scope: &Scope,
1027 ) -> Result<()> {
1028 if self.aggregation.is_none() {
1029 return Ok(());
1030 }
1031 let mut lifted = Vec::new();
1032 for pending in self.scalar_subqueries.split_off(before) {
1033 if pending.dependent || pending.inside_aggregate {
1034 self.scalar_subqueries.push(pending);
1035 } else {
1036 self.joined_above.push(pending.index);
1037 lifted.push(pending);
1038 }
1039 }
1040 for pending in &mut lifted {
1045 let conditions = std::mem::take(&mut pending.conditions);
1046 let mut over = Vec::with_capacity(conditions.len());
1047 for condition in conditions {
1048 over.push(self.over_aggregate(condition, scope)?);
1049 }
1050 pending.conditions = over;
1051 }
1052 above.append(&mut lifted);
1053 Ok(())
1054 }
1055
1056 fn bind_targets(
1057 &mut self,
1058 ast: &Ast,
1059 targets: &[ast::Target],
1060 input: &Scope,
1061 above: &mut Vec<PendingSubquery>,
1062 ) -> Result<(Vec<ExprRef>, Vec<String>)> {
1063 let mut exprs = Vec::with_capacity(targets.len());
1064 let mut names = Vec::with_capacity(targets.len());
1065 for target in targets {
1066 if let ast::Expr::Star { qualifier, replacements } = ast.expr(target.expr) {
1067 let table = ast.name(qualifier).last().map(str::to_string);
1068 let expanded: Vec<Visible> =
1069 input.star(table.as_deref())?.into_iter().cloned().collect();
1070 let replacements = ast.target_list(replacements).to_vec();
1071 let mut used = vec![false; replacements.len()];
1072 for column in expanded {
1073 let found = replacements.iter().zip(&mut used).find(|(replacement, _)| {
1074 same_name(ast.string(replacement.alias), &column.name)
1075 });
1076 let before = self.scalar_subqueries.len();
1081 let (expr, name) = match found {
1082 Some((replacement, used)) => {
1083 *used = true;
1084 let expr = self.bind_expr(ast, replacement.expr, input)?;
1085 (expr, ast.string(replacement.alias).to_string())
1086 }
1087 None => (
1088 self.plan.add_expr(Expr::Column(column.binding), column.ty),
1089 column.name,
1090 ),
1091 };
1092 self.lift_over_aggregate(before, above, input)?;
1093 exprs.push(self.over_aggregate(expr, input)?);
1094 names.push(name);
1095 }
1096 if let Some((replacement, _)) =
1100 replacements.iter().zip(&used).find(|(_, used)| !**used)
1101 {
1102 return Err(missing_replacement(ast.string(replacement.alias), input));
1103 }
1104 continue;
1105 }
1106 let before = self.scalar_subqueries.len();
1107 let expr = self.bind_expr(ast, target.expr, input)?;
1108 self.lift_over_aggregate(before, above, input)?;
1109 exprs.push(self.over_aggregate(expr, input)?);
1110 names.push(if target.alias == NONE {
1111 self.output_name(ast, target.expr, input)
1112 } else {
1113 ast.string(target.alias).to_string()
1114 });
1115 }
1116 Ok((exprs, names))
1117 }
1118
1119 fn output_name(&self, ast: &Ast, target: ast::ExprRef, input: &Scope) -> String {
1125 if let ast::Expr::Column { name } = ast.expr(target) {
1126 let parts: Vec<&str> = ast.name(name).collect();
1127 if let Ok(found) = input.resolve(&parts) {
1128 return found.name.clone();
1129 }
1130 }
1131 describe(ast, target, self.semantics)
1132 }
1133
1134 fn group_items(
1136 &self,
1137 ast: &Ast,
1138 select: &ast::Select,
1139 targets: &[ast::Target],
1140 ) -> Result<Vec<ast::ExprRef>> {
1141 if select.group_by_all {
1142 return Ok(targets
1145 .iter()
1146 .filter(|target| !has_aggregate(ast, target.expr))
1147 .map(|target| target.expr)
1148 .collect());
1149 }
1150 let mut items = Vec::new();
1151 for &item in ast.expr_list(select.group_by) {
1152 items.push(self.output_reference(ast, item, targets, "GROUP BY")?.unwrap_or(item));
1153 }
1154 Ok(items)
1155 }
1156
1157 fn output_reference(
1159 &self,
1160 ast: &Ast,
1161 item: ast::ExprRef,
1162 targets: &[ast::Target],
1163 clause: &str,
1164 ) -> Result<Option<ast::ExprRef>> {
1165 match ast.expr(item) {
1166 ast::Expr::Literal { kind: LiteralKind::Number, text } => {
1167 let written = ast.string(text);
1168 let position: usize = written.parse().map_err(|_| {
1169 Error::binder(format!("{clause} term {written} is not a column"))
1170 })?;
1171 if position == 0 || position > targets.len() {
1172 return Err(Error::binder(format!(
1173 "{clause} term out of range - should be between 1 and {}",
1174 targets.len()
1175 )));
1176 }
1177 Ok(Some(targets[position - 1].expr))
1178 }
1179 ast::Expr::Column { name } => {
1180 let parts: Vec<&str> = ast.name(name).collect();
1181 let [written] = parts.as_slice() else { return Ok(None) };
1182 let mut found = None;
1183 for target in targets {
1184 if target.alias != NONE && same_name(ast.string(target.alias), written) {
1185 if found.is_some() {
1186 return Ok(None);
1187 }
1188 found = Some(target.expr);
1189 }
1190 }
1191 Ok(found)
1192 }
1193 _ => Ok(None),
1194 }
1195 }
1196
1197 #[allow(clippy::too_many_arguments)]
1201 fn select_sort_keys(
1202 &mut self,
1203 ast: &Ast,
1204 query: &ast::Query,
1205 input: &Scope,
1206 output: &Scope,
1207 project: u32,
1208 exprs: &mut Vec<ExprRef>,
1209 names: &mut Vec<String>,
1210 extra: &mut Vec<usize>,
1211 above: &mut Vec<PendingSubquery>,
1212 ) -> Result<Vec<SortKey>> {
1213 if query.order_by_all {
1214 return Ok(self.every_column(output));
1215 }
1216 let items = ast.order_list(query.order_by).to_vec();
1217 let mut keys = Vec::with_capacity(items.len());
1218 for item in items {
1219 self.check_order_literal(ast, item.expr)?;
1220 let position = match self.output_position(ast, item.expr, output)? {
1221 Some(position) => position,
1222 None => {
1223 let before = self.scalar_subqueries.len();
1224 let bound = self.bind_expr(ast, item.expr, input)?;
1225 self.lift_over_aggregate(before, above, input)?;
1226 let bound = self.over_aggregate(bound, input)?;
1227 match exprs.iter().position(|&held| self.same_expr(held, bound)) {
1228 Some(position) => position,
1229 None => {
1230 exprs.push(bound);
1231 names.push(describe(ast, item.expr, self.semantics));
1232 extra.push(exprs.len() - 1);
1233 exprs.len() - 1
1234 }
1235 }
1236 }
1237 };
1238 let ty = self.plan.expr_type(exprs[position]).clone();
1239 let expr = self.column(project, position, ty);
1240 keys.push(self.sort_key(expr, item));
1241 }
1242 Ok(keys)
1243 }
1244
1245 fn sort_keys(
1247 &mut self,
1248 ast: &Ast,
1249 query: &ast::Query,
1250 output: &Scope,
1251 targets: &[ast::Target],
1252 ) -> Result<Vec<SortKey>> {
1253 if query.order_by_all {
1254 return Ok(self.every_column(output));
1255 }
1256 let items = ast.order_list(query.order_by).to_vec();
1257 let mut keys = Vec::with_capacity(items.len());
1258 for item in items {
1259 self.check_order_literal(ast, item.expr)?;
1260 let expr = match self.output_position(ast, item.expr, output)? {
1261 Some(position) => {
1262 let column = &output.columns[position];
1263 let (binding, ty) = (column.binding, column.ty.clone());
1264 self.plan.add_expr(Expr::Column(binding), ty)
1265 }
1266 None => {
1267 let _ = targets;
1268 self.bind_expr(ast, item.expr, output)?
1269 }
1270 };
1271 keys.push(self.sort_key(expr, item));
1272 }
1273 Ok(keys)
1274 }
1275
1276 fn every_column(&mut self, output: &Scope) -> Vec<SortKey> {
1277 let columns: Vec<(ColumnBinding, LogicalType)> =
1278 output.columns.iter().map(|column| (column.binding, column.ty.clone())).collect();
1279 columns
1280 .into_iter()
1281 .map(|(binding, ty)| {
1282 let expr = self.plan.add_expr(Expr::Column(binding), ty);
1283 let descending = self.semantics.default_descending();
1284 SortKey { expr, descending, nulls_first: self.semantics.nulls_first(descending) }
1285 })
1286 .collect()
1287 }
1288
1289 fn sort_key(&self, expr: ExprRef, item: ast::OrderItem) -> SortKey {
1291 let descending = match item.order {
1292 Order::Unstated => self.semantics.default_descending(),
1293 Order::Ascending => false,
1294 Order::Descending => true,
1295 };
1296 let nulls_first = match item.nulls {
1297 Nulls::First => true,
1298 Nulls::Last => false,
1299 Nulls::Unstated => self.semantics.nulls_first(descending),
1300 };
1301 SortKey { expr, descending, nulls_first }
1302 }
1303
1304 fn output_position(
1306 &self,
1307 ast: &Ast,
1308 item: ast::ExprRef,
1309 output: &Scope,
1310 ) -> Result<Option<usize>> {
1311 match ast.expr(item) {
1312 ast::Expr::Literal { kind: LiteralKind::Number, text } => {
1313 let written = ast.string(text);
1314 if written.contains(['.', 'e', 'E']) {
1315 return Ok(None);
1316 }
1317 let position: usize = written.parse().map_err(|_| {
1318 Error::binder(format!("ORDER BY term {written} is not a column"))
1319 })?;
1320 if position == 0 || position > output.len() {
1321 return Err(Error::binder(format!(
1322 "ORDER BY term out of range - should be between 1 and {}",
1323 output.len()
1324 )));
1325 }
1326 Ok(Some(position - 1))
1327 }
1328 ast::Expr::Column { name } => {
1329 let parts: Vec<&str> = ast.name(name).collect();
1330 let [written] = parts.as_slice() else { return Ok(None) };
1331 Ok(output.position_of(None, written))
1332 }
1333 _ => Ok(None),
1334 }
1335 }
1336
1337 fn check_order_literal(&self, ast: &Ast, item: ast::ExprRef) -> Result<()> {
1339 if !self.semantics.order_by_non_integer_literal()
1340 && matches!(
1341 ast.expr(item),
1342 ast::Expr::Literal { kind, text }
1343 if kind != LiteralKind::Number
1344 || ast.string(text).contains(['.', 'e', 'E'])
1345 )
1346 {
1347 return Err(Error::binder(
1348 "ORDER BY non-integer literal has no effect.\n* SET order_by_non_integer_literal=true to allow this behavior.",
1349 ));
1350 }
1351 Ok(())
1352 }
1353
1354 fn distinct_on(
1356 &mut self,
1357 ast: &Ast,
1358 distinct: Distinct,
1359 output: &Scope,
1360 ) -> Result<Vec<ExprRef>> {
1361 let Distinct::On(items) = distinct else {
1362 return Ok(Vec::new());
1363 };
1364 let items = ast.expr_list(items).to_vec();
1365 let mut on = Vec::with_capacity(items.len());
1366 for item in items {
1367 let Some(position) = self.output_position(ast, item, output)? else {
1368 return Err(Error::not_implemented(
1369 "DISTINCT ON an expression that is not in the select list",
1370 ));
1371 };
1372 let column = &output.columns[position];
1373 let (binding, ty) = (column.binding, column.ty.clone());
1374 on.push(self.plan.add_expr(Expr::Column(binding), ty));
1375 }
1376 Ok(on)
1377 }
1378
1379 fn apply_limit(
1386 &mut self,
1387 ast: &Ast,
1388 query: &ast::Query,
1389 input: NodeRef,
1390 scope: &mut Scope,
1391 ) -> Result<NodeRef> {
1392 let waiting = self.scalar_subqueries.len();
1393 if query.limit_percent {
1394 let percent = self.constant_percent(ast, query.limit)?;
1395 let offset = self.count_bound(ast, query.offset, "OFFSET")?;
1396 let offset = self.settled(offset, "OFFSET")?;
1397 return Ok(match percent {
1398 Some(percent) => self.add_node(Node::LimitPercent { input, percent, offset }),
1399 None => self.limited(input, Bound::All, Bound::Rows(offset)),
1402 });
1403 }
1404 let count = self.count_bound(ast, query.limit, "LIMIT")?;
1405 let offset = match self.count_bound(ast, query.offset, "OFFSET")? {
1408 Bound::All => Bound::Rows(0),
1409 named => named,
1410 };
1411 let joined = self.scalar_subqueries.split_off(waiting);
1412 if joined.is_empty() {
1413 return Ok(self.limited(input, count, offset));
1414 }
1415 let mut input = input;
1416 for pending in joined {
1417 input = self.attach_subquery(input, pending);
1418 }
1419 let limit = self.add_node(Node::Limit { input, count, offset });
1420 Ok(self.reproject(limit, scope))
1421 }
1422
1423 fn limited(&mut self, input: NodeRef, count: Bound, offset: Bound) -> NodeRef {
1426 if count == Bound::All && offset == Bound::Rows(0) {
1427 return input;
1428 }
1429 self.add_node(Node::Limit { input, count, offset })
1430 }
1431
1432 fn settled(&self, bound: Bound, clause: &str) -> Result<u64> {
1438 match bound {
1439 Bound::Rows(rows) => Ok(rows),
1440 Bound::All => Ok(0),
1441 Bound::Read(_) => Err(Error::not_implemented(format!(
1442 "{clause} holding a subquery beside a LIMIT written as a percentage"
1443 ))),
1444 }
1445 }
1446
1447 fn reproject(&mut self, node: NodeRef, scope: &mut Scope) -> NodeRef {
1453 let index = self.fresh_index();
1454 let mut exprs = Vec::with_capacity(scope.columns.len());
1455 let mut names = Vec::with_capacity(scope.columns.len());
1456 for column in &scope.columns {
1457 exprs.push(self.plan.add_expr(Expr::Column(column.binding), column.ty.clone()));
1458 names.push(self.plan.intern(&column.name));
1459 }
1460 for (at, column) in scope.columns.iter_mut().enumerate() {
1461 column.binding = ColumnBinding::new(index, at as u32);
1462 }
1463 let exprs = self.plan.add_expr_list(&exprs);
1464 let names = self.plan.add_name_list(&names);
1465 self.add_node(Node::Project { input: node, index, exprs, names })
1466 }
1467
1468 fn constant_percent(&mut self, ast: &Ast, written: ast::ExprRef) -> Result<Option<f64>> {
1479 if written == NONE {
1480 return Ok(None);
1481 }
1482 self.clause = "LIMIT clause";
1483 let scope = Scope::empty();
1484 let bound = self.bind_expr(ast, written, &scope)?;
1485 let Some(value) = fold::value_of(&self.plan, bound)? else {
1486 return Err(Error::not_implemented("a LIMIT holding a subquery"));
1487 };
1488 if value.is_null() {
1489 return Ok(None);
1490 }
1491 let cast = cast_value(&value, &LogicalType::Double, false)?;
1492 let Value::Double(percent) = cast else {
1493 return Err(Error::binder(format!(
1494 "LIMIT takes a percentage, not a value of type {}",
1495 value.logical_type()
1496 )));
1497 };
1498 if !(0.0..=100.0).contains(&percent) {
1499 return Err(Error::out_of_range(
1500 "Limit percent out of range, should be between 0% and 100%",
1501 ));
1502 }
1503 Ok(Some(percent))
1504 }
1505
1506 fn count_bound(&mut self, ast: &Ast, written: ast::ExprRef, clause: &str) -> Result<Bound> {
1525 if written == NONE {
1526 return Ok(Bound::All);
1527 }
1528 self.clause = "LIMIT clause";
1529 let scope = Scope::empty();
1530 let bound = self.bind_expr(ast, written, &scope)?;
1531 let Some(value) = fold::value_of(&self.plan, bound)? else {
1532 return Ok(Bound::Read(bound));
1533 };
1534 if value.is_null() {
1537 return Ok(Bound::All);
1538 }
1539 row_count(&value, clause).map(Bound::Rows)
1540 }
1541
1542 fn bind_from(&mut self, ast: &Ast, from: ast::Slice) -> Result<(NodeRef, Scope)> {
1545 let sources = ast.source_list(from).to_vec();
1546 let Some((first, rest)) = sources.split_first() else {
1547 return Ok((self.add_node(Node::Dummy), Scope::empty()));
1550 };
1551 let (mut node, mut scope) = self.bind_source(ast, *first)?;
1552 for source in rest {
1553 let (right, right_scope, correlations) = self.bind_lateral(ast, *source, &scope)?;
1554 node = if correlations.is_empty() {
1555 self.add_node(Node::CrossProduct { left: node, right })
1556 } else {
1557 let conditions = self.plan.add_expr_list(&[]);
1558 self.add_node(Node::DependentJoin {
1559 left: node,
1560 right,
1561 kind: JoinKind::Inner,
1562 conditions,
1563 })
1564 };
1565 scope = scope.concat(right_scope);
1566 }
1567 Ok((node, scope))
1568 }
1569
1570 fn bind_lateral(
1582 &mut self,
1583 ast: &Ast,
1584 source: ast::SourceRef,
1585 left: &Scope,
1586 ) -> Result<(NodeRef, Scope, Vec<ColumnBinding>)> {
1587 self.lateral_scopes.push(self.outer_scopes.len());
1588 self.outer_scopes.push(left.clone());
1589 self.correlations.push(Vec::new());
1590 let bound = self.bind_source(ast, source);
1591 let read = self.correlations.pop().expect("correlation frame");
1592 self.outer_scopes.pop();
1593 self.lateral_scopes.pop();
1594 let (node, scope) = bound?;
1595
1596 let mut here = Vec::new();
1597 for binding in read {
1598 if left.columns.iter().any(|column| column.binding == binding) {
1599 here.push(binding);
1600 } else if let Some(enclosing) = self.correlations.last_mut() {
1601 if !enclosing.contains(&binding) {
1602 enclosing.push(binding);
1603 }
1604 }
1605 }
1606 Ok((node, scope, here))
1616 }
1617
1618 fn bind_source(&mut self, ast: &Ast, source: ast::SourceRef) -> Result<(NodeRef, Scope)> {
1619 match ast.source(source) {
1620 ast::Source::Table { name, alias, columns } => {
1621 self.bind_table(ast, name, alias, columns)
1622 }
1623 ast::Source::Function { name, args, alias, columns, pragma } => {
1624 self.bind_table_function(ast, name, args, alias, columns, pragma)
1625 }
1626 ast::Source::Subquery { query, alias, columns } => {
1627 let (node, mut scope) = self.bind_query(ast, query)?;
1628 let label = if alias == NONE {
1629 "unnamed_subquery".to_string()
1630 } else {
1631 ast.string(alias).to_string()
1632 };
1633 scope.relabel(&label);
1634 if !columns.is_empty() {
1635 let names: Vec<&str> = ast.name(columns).collect();
1636 scope.rename(&names, &label)?;
1637 }
1638 Ok((node, scope))
1639 }
1640 ast::Source::Values { rows, alias, columns } => {
1641 let bare = ast::Query::bare(ast::QueryBody::Values(rows));
1642 let (node, mut scope) = self.bind_values(ast, &bare, rows)?;
1643 let label =
1644 if alias == NONE { String::new() } else { ast.string(alias).to_string() };
1645 scope.relabel(&label);
1646 if !columns.is_empty() {
1647 let names: Vec<&str> = ast.name(columns).collect();
1648 scope.rename(&names, &label)?;
1649 }
1650 Ok((node, scope))
1651 }
1652 ast::Source::Cte { cte, alias, columns } => {
1653 self.bind_cte_scan(ast, cte, alias, columns)
1654 }
1655 ast::Source::Join { left, right, kind, natural, on, using } => {
1656 self.bind_join(ast, left, right, kind, natural, on, using)
1657 }
1658 }
1659 }
1660
1661 fn bind_cte_scan(
1668 &mut self,
1669 ast: &Ast,
1670 written: u32,
1671 alias: ast::StrRef,
1672 columns: ast::Slice,
1673 ) -> Result<(NodeRef, Scope)> {
1674 let Some(held) = self.materialized.iter().rev().find(|held| held.written == written) else {
1675 let name = ast.string(ast.cte(written).name);
1676 return Err(Error::binder(format!("Table with name {name} does not exist!")));
1677 };
1678 let cte = held.cte;
1679 let fields = held.fields.clone();
1680 let text = held.name.clone();
1681 let label = if alias == NONE { text.clone() } else { ast.string(alias).to_string() };
1682 let name = self.plan.intern(&text);
1683 let index = self.fresh_index();
1684 let mut scope = Scope::empty();
1685 for (at, field) in fields.iter().enumerate() {
1686 scope.push(Visible {
1687 table: label.clone(),
1688 name: field.name.clone(),
1689 binding: ColumnBinding::new(index, at as u32),
1690 ty: field.ty.clone(),
1691 not_null: field.not_null,
1692 });
1693 }
1694 if !columns.is_empty() {
1695 let names: Vec<&str> = ast.name(columns).collect();
1696 scope.rename(&names, &label)?;
1697 }
1698 let columns = self.plan.add_fields(&fields);
1699 let node = self.add_node(Node::CteScan { index, cte, name, columns });
1700 Ok((node, scope))
1701 }
1702
1703 fn bind_table(
1704 &mut self,
1705 ast: &Ast,
1706 name: ast::Slice,
1707 alias: ast::StrRef,
1708 columns: ast::Slice,
1709 ) -> Result<(NodeRef, Scope)> {
1710 let parts: Vec<&str> = ast.name(name).collect();
1711 let catalog = self.catalog;
1712 let resolved = match catalog.resolve(&parts) {
1715 Ok(resolved) => resolved,
1716 Err(missing) => {
1717 return self.bind_replacement_scan(ast, &parts, alias, columns, missing);
1718 }
1719 };
1720 if catalog.entry(&resolved)? == Entry::View {
1721 return self.bind_view(ast, &resolved, alias, columns);
1722 }
1723 let table = catalog.table(&resolved)?;
1724 let fields: Vec<Field> = table.columns().to_vec();
1725 let label =
1726 if alias == NONE { resolved.table.clone() } else { ast.string(alias).to_string() };
1727 let index = self.fresh_index();
1728 let mut scope = Scope::empty();
1729 for (at, field) in fields.iter().enumerate() {
1730 scope.push(Visible {
1731 table: label.clone(),
1732 name: field.name.clone(),
1733 binding: ColumnBinding::new(index, at as u32),
1734 ty: field.ty.clone(),
1735 not_null: field.not_null,
1736 });
1737 }
1738 if !columns.is_empty() {
1739 let names: Vec<&str> = ast.name(columns).collect();
1740 scope.rename(&names, &label)?;
1741 }
1742 let catalog_name = self.plan.intern(&resolved.catalog);
1743 let schema = self.plan.intern(&resolved.schema);
1744 let table_name = self.plan.intern(&resolved.table);
1745 let alias = self.plan.intern(&label);
1746 let columns = self.plan.add_fields(&fields);
1747 if let Some(zones) = table.rows().zones() {
1752 self.plan.set_zones(index, zones);
1753 }
1754 if let Some(frequencies) = table.rows().frequencies() {
1755 self.plan.set_frequencies(index, frequencies);
1756 }
1757 for (column, distinct) in table.distincts() {
1758 self.plan.measure_distinct(index, &column, distinct);
1759 }
1760 let node = self.add_node(Node::Get {
1761 catalog: catalog_name,
1762 schema,
1763 table: table_name,
1764 alias,
1765 index,
1766 columns,
1767 });
1768 Ok((node, scope))
1769 }
1770
1771 fn bind_view(
1783 &mut self,
1784 ast: &Ast,
1785 name: &QualifiedName,
1786 alias: ast::StrRef,
1787 columns: ast::Slice,
1788 ) -> Result<(NodeRef, Scope)> {
1789 let view = self.catalog.view(name)?;
1790 let full = name.to_string();
1791 if self.expanding.contains(&full) {
1792 return Err(Error::binder(format!(
1796 "infinite recursion detected: attempting to recursively bind view \"\"{}\"\"",
1797 name.table
1798 )));
1799 }
1800 let body = parse_ast_with_case(view.sql(), self.semantics.identifier_case())?;
1801 let query = match body.statements.as_slice() {
1802 [ast::Statement::Query(query)] => *query,
1803 _ => return Err(Error::binder(format!("view \"{}\" is not a query", name.table))),
1806 };
1807 self.expanding.push(full);
1808 let bound = self.bind_query(&body, query);
1809 self.expanding.pop();
1810 let (node, mut scope) = bound?;
1811
1812 let aliases: Vec<&str> = view.aliases().iter().map(String::as_str).collect();
1813 if !aliases.is_empty() {
1814 scope.rename(&aliases, "unnamed_subquery")?;
1815 }
1816 view.remember(scope.fields());
1823 let label = if alias == NONE { name.table.clone() } else { ast.string(alias).to_string() };
1824 scope.relabel(&label);
1825 if !columns.is_empty() {
1826 let names: Vec<&str> = ast.name(columns).collect();
1827 scope.rename(&names, &label)?;
1828 }
1829 Ok((node, scope))
1830 }
1831
1832 fn bind_table_function(
1840 &mut self,
1841 ast: &Ast,
1842 name: ast::Slice,
1843 args: ast::Slice,
1844 alias: ast::StrRef,
1845 columns: ast::Slice,
1846 pragma: bool,
1847 ) -> Result<(NodeRef, Scope)> {
1848 let parts: Vec<&str> = ast.name(name).collect();
1849 let function_name = *parts.last().unwrap_or(&"");
1853 if let Some(schema) = parts.iter().rev().nth(1) {
1854 if !schema.eq_ignore_ascii_case("main") && !schema.eq_ignore_ascii_case("system") {
1855 return Err(Error::catalog(format!(
1856 "Table Function with name {} does not exist!",
1857 parts.join(".")
1858 )));
1859 }
1860 }
1861 let Some(called) = TableFunction::lookup(function_name) else {
1865 if pragma {
1866 if args.is_empty() && self.catalog.resolve(&parts).is_ok() {
1872 return self.bind_table(ast, name, alias, columns);
1873 }
1874 let spelled = function_name.strip_prefix("pragma_").unwrap_or(function_name);
1875 return Err(Error::catalog(format!(
1876 "Pragma Function with name {spelled} does not exist!"
1877 )));
1878 }
1879 return Err(Error::catalog(format!(
1880 "Table Function with name {function_name} does not exist!"
1881 )));
1882 };
1883 let written = ast.target_list(args).to_vec();
1884 let empty = Scope::empty();
1885 let previous = std::mem::replace(&mut self.clause, "table function arguments");
1886 let mut bound = Vec::new();
1887 let mut written_options = Vec::new();
1888 for argument in written {
1889 let expr = self.bind_expr(ast, argument.expr, &empty)?;
1890 if argument.alias == NONE {
1891 bound.push(expr);
1892 } else {
1893 let name = ast.string(argument.alias).to_string();
1894 let (parameter, value) = self.named_argument(called, &name, expr)?;
1895 written_options.push((parameter, value, expr));
1896 }
1897 }
1898 self.clause = previous;
1899 let options = Options::of(&written_options)?;
1900
1901 let given: Vec<LogicalType> =
1904 bound.iter().map(|&expr| self.plan.expr_type(expr).clone()).collect();
1905 let resolved = if pragma {
1906 resolve_pragma(function_name, &given)?
1907 } else {
1908 resolve_table(function_name, &given)?
1909 };
1910 let mut cast: Vec<ExprRef> = bound
1911 .iter()
1912 .zip(&resolved.arguments)
1913 .map(|(&expr, ty)| self.checked_cast_to(expr, ty, false))
1914 .collect::<Result<_>>()?;
1915
1916 if resolved.function.takes_a_name() {
1917 let Columns::Fixed(fields) = resolved.columns else {
1918 return Err(Error::internal("a pragma that resolved to a file"));
1919 };
1920 let [argument] = cast[..] else {
1921 return Err(Error::internal("a pragma that resolved to more than one name"));
1922 };
1923 return self.bind_pragma(ast, resolved.function, &fields, argument, alias, columns);
1924 }
1925 let mut measured = Stat::Unknown;
1928 let mut counted: Vec<(String, Stat<u64>)> = Vec::new();
1929 let mut bounded: Option<Arc<dyn Zones>> = None;
1930 let fields = match resolved.columns {
1931 Columns::Fixed(fields) => fields,
1932 columns => {
1933 let paths = self.file_paths(cast[0], resolved.function.name())?;
1938 let mut fields = match columns {
1939 Columns::Csv => csv_fields(&paths, options.given)?,
1942 _ => {
1943 let footers = parquet_footers(&paths)?;
1944 measured = footers.rows;
1945 counted = footers.distincts;
1946 bounded = footers.zones;
1947 footers.fields
1948 }
1949 };
1950 if options.all_varchar {
1951 for field in &mut fields {
1956 field.ty = LogicalType::Varchar;
1957 }
1958 }
1959 if options.binary_as_string {
1960 for field in &mut fields {
1965 if field.ty == LogicalType::Blob {
1966 field.ty = LogicalType::Varchar;
1967 }
1968 }
1969 }
1970 if options.file_row_number {
1971 if fields.iter().any(|field| field.name == FILE_ROW_NUMBER) {
1977 return Err(Error::binder(format!(
1978 "Duplicate column name \"{FILE_ROW_NUMBER}\": the file already has a \
1979 column of that name, so file_row_number cannot add one"
1980 )));
1981 }
1982 fields.push(Field::required(FILE_ROW_NUMBER.to_string(), LogicalType::BigInt));
1983 }
1984 cast = paths.iter().map(|path| self.path_constant(path)).collect();
1985 fields
1986 }
1987 };
1988 let label = if alias == NONE {
1989 resolved.function.name().to_string()
1990 } else {
1991 ast.string(alias).to_string()
1992 };
1993 let names: Vec<&str> = ast.name(columns).collect();
1994 self.table_function_source(
1995 resolved.function,
1996 &cast,
1997 &written_options,
1998 Read { fields, rows: measured, distincts: counted, zones: bounded },
1999 &label,
2000 &names,
2001 )
2002 }
2003
2004 fn bind_pragma(
2017 &mut self,
2018 ast: &Ast,
2019 function: TableFunction,
2020 fields: &[Field],
2021 argument: ExprRef,
2022 alias: ast::StrRef,
2023 columns: ast::Slice,
2024 ) -> Result<(NodeRef, Scope)> {
2025 let written = self.pragma_name(argument, function)?;
2026 let parts = identifier_parts(&written);
2027 let spelled: Vec<&str> = parts.iter().map(String::as_str).collect();
2028 let name = self.catalog.resolve(&spelled)?;
2029 let described = self.described(ast, &name)?;
2030 let mut rows = Vec::with_capacity(described.len());
2031 for (at, field) in described.iter().enumerate() {
2032 let items = if matches!(function, TableFunction::PragmaShow) {
2033 self.describing(field)
2034 } else {
2035 self.table_info(at, field)
2036 };
2037 rows.push(self.plan.add_expr_list(&items));
2038 }
2039 let rows = self.plan.add_rows(&rows);
2040 let held = self.plan.add_fields(fields);
2041 let index = self.fresh_index();
2042 let node = self.add_node(Node::Values { index, columns: held, rows });
2043 let label =
2044 if alias == NONE { function.name().to_string() } else { ast.string(alias).to_string() };
2045 let mut scope = Scope::empty();
2046 for (at, field) in fields.iter().enumerate() {
2047 scope.push(Visible {
2048 table: label.clone(),
2049 name: field.name.clone(),
2050 binding: ColumnBinding::new(index, at as u32),
2051 ty: field.ty.clone(),
2052 not_null: false,
2053 });
2054 }
2055 if !columns.is_empty() {
2056 let names: Vec<&str> = ast.name(columns).collect();
2057 scope.rename(&names, &label)?;
2058 }
2059 Ok((node, scope))
2060 }
2061
2062 fn pragma_name(&self, argument: ExprRef, function: TableFunction) -> Result<String> {
2072 let Expr::Constant(reference) = *self.plan.expr(argument) else {
2073 return Err(Error::not_implemented(format!(
2074 "{}() given a name that is not a constant",
2075 function.name()
2076 )));
2077 };
2078 match self.plan.value(reference) {
2079 Value::Varchar(name) => Ok(name.clone()),
2080 Value::Null => Ok("NULL".to_string()),
2081 other => {
2082 Err(Error::internal(format!("a pragma name bound as VARCHAR arrived as {other}")))
2083 }
2084 }
2085 }
2086
2087 fn described(&mut self, ast: &Ast, name: &QualifiedName) -> Result<Vec<Field>> {
2098 if self.catalog.entry(name)? == Entry::Table {
2099 return Ok(self.catalog.table(name)?.columns().to_vec());
2100 }
2101 let (_, scope) = self.bind_view(ast, name, NONE, ast::Slice::default())?;
2102 Ok(scope.fields())
2103 }
2104
2105 fn describing(&mut self, field: &Field) -> Vec<ExprRef> {
2107 let written = [
2108 field.name.clone(),
2109 field.ty.to_string(),
2110 if field.not_null { "NO" } else { "YES" }.to_owned(),
2111 ];
2112 let mut items: Vec<ExprRef> =
2113 written.into_iter().map(|text| self.plan.add_constant(Value::Varchar(text))).collect();
2114 for _ in 0..3 {
2115 let empty = self.plan.add_constant(Value::Null);
2116 items.push(self.cast_to(empty, &LogicalType::Varchar));
2117 }
2118 items
2119 }
2120
2121 fn table_info(&mut self, at: usize, field: &Field) -> Vec<ExprRef> {
2127 let cid = self.plan.add_constant(Value::Integer(i32::try_from(at).unwrap_or(i32::MAX)));
2128 let name = self.plan.add_constant(Value::Varchar(field.name.clone()));
2129 let ty = self.plan.add_constant(Value::Varchar(field.ty.to_string()));
2130 let not_null = self.plan.add_constant(Value::Boolean(field.not_null));
2131 let default = self.plan.add_constant(Value::Null);
2132 let default = self.cast_to(default, &LogicalType::Varchar);
2133 let key = self.plan.add_constant(Value::Boolean(false));
2134 vec![cid, name, ty, not_null, default, key]
2135 }
2136
2137 fn named_argument(
2151 &mut self,
2152 function: TableFunction,
2153 name: &str,
2154 expr: ExprRef,
2155 ) -> Result<(&'static str, Value)> {
2156 let known = function
2157 .parameters()
2158 .iter()
2159 .find(|(parameter, _)| parameter.eq_ignore_ascii_case(name));
2160 let Some((parameter, wanted)) = known else {
2161 let candidates: Vec<String> = function
2162 .parameters()
2163 .iter()
2164 .map(|(parameter, ty)| format!(" {parameter} {ty}"))
2165 .collect();
2166 return Err(Error::binder(format!(
2167 "Invalid named parameter \"{name}\" for function {}\nCandidates:\n{}\n",
2168 function.name(),
2169 candidates.join("\n")
2170 )));
2171 };
2172 let Expr::Constant(reference) = *self.plan.expr(expr) else {
2173 return Err(Error::not_implemented(format!(
2174 "the named parameter {parameter} with a value that is not a constant"
2175 )));
2176 };
2177 let value = self.plan.value(reference).clone();
2178 if value == Value::Null {
2179 return Err(Error::binder(null_parameter(function, parameter)));
2180 }
2181 let given = self.plan.expr_type(expr).clone();
2182 if given != *wanted {
2183 return Err(Error::not_implemented(format!(
2184 "the named parameter {parameter} given a {given} where a {wanted} was wanted"
2185 )));
2186 }
2187 Ok((parameter, value))
2188 }
2189
2190 fn bind_replacement_scan(
2201 &mut self,
2202 ast: &Ast,
2203 parts: &[&str],
2204 alias: ast::StrRef,
2205 columns: ast::Slice,
2206 missing: Error,
2207 ) -> Result<(NodeRef, Scope)> {
2208 let [path] = parts else { return Err(missing) };
2209 let path = *path;
2210 let extension = path.rsplit_once('.').map(|(_, after)| after).unwrap_or_default();
2211 let Some(function) = Self::reader_for(extension) else {
2212 if is_file(path) {
2213 return Err(Error::binder(format!(
2218 "No extension found that is capable of reading the file \"{path}\"\n* If this \
2219 file is a supported file format you can explicitly use the reader functions, \
2220 such as read_csv, read_json or read_parquet"
2221 )));
2222 }
2223 return Err(missing);
2224 };
2225 let paths = files(path)?;
2230 let read = match function {
2231 TableFunction::ReadParquet => {
2232 let footers = parquet_footers(&paths)?;
2233 Read {
2234 fields: footers.fields,
2235 rows: footers.rows,
2236 distincts: footers.distincts,
2237 zones: footers.zones,
2238 }
2239 }
2240 _ => Read::uncounted(csv_fields(&paths, Given::default())?),
2241 };
2242 let label = if alias == NONE {
2248 if is_pattern(path) {
2249 path.to_string()
2250 } else {
2251 let file = path.rsplit_once('/').map_or(path, |(_, file)| file);
2252 file.rsplit_once('.').map_or(file, |(stem, _)| stem).to_string()
2253 }
2254 } else {
2255 ast.string(alias).to_string()
2256 };
2257 let arguments: Vec<ExprRef> = paths.iter().map(|path| self.path_constant(path)).collect();
2258 let names: Vec<&str> = ast.name(columns).collect();
2259 self.table_function_source(function, &arguments, &[], read, &label, &names)
2260 }
2261
2262 fn path_constant(&mut self, path: &str) -> ExprRef {
2264 let value = self.plan.add_value(Value::Varchar(path.to_string()));
2265 self.plan.add_expr(Expr::Constant(value), LogicalType::Varchar)
2266 }
2267
2268 fn reader_for(extension: &str) -> Option<TableFunction> {
2275 if extension.eq_ignore_ascii_case("parquet") {
2276 return Some(TableFunction::ReadParquet);
2277 }
2278 if extension.eq_ignore_ascii_case("csv") || extension.eq_ignore_ascii_case("tsv") {
2279 return Some(TableFunction::ReadCsv);
2280 }
2281 None
2282 }
2283
2284 fn table_function_source(
2294 &mut self,
2295 function: TableFunction,
2296 args: &[ExprRef],
2297 written: &[(&'static str, Value, ExprRef)],
2298 read: Read,
2299 label: &str,
2300 names: &[&str],
2301 ) -> Result<(NodeRef, Scope)> {
2302 let Read { fields, rows, distincts, zones } = read;
2303 let index = self.fresh_index();
2304 if rows.is_known() {
2309 self.plan.measure(index, rows);
2310 }
2311 for (column, distinct) in distincts {
2312 self.plan.measure_distinct(index, &column, distinct);
2313 }
2314 if let Some(zones) = zones {
2315 self.plan.set_zones(index, zones);
2316 }
2317 let mut scope = Scope::empty();
2318 for (at, field) in fields.iter().enumerate() {
2319 scope.push(Visible {
2320 table: label.to_string(),
2321 name: field.name.clone(),
2322 binding: ColumnBinding::new(index, at as u32),
2323 ty: field.ty.clone(),
2324 not_null: false,
2327 });
2328 }
2329 if !names.is_empty() {
2330 scope.rename(names, label)?;
2331 }
2332 let function = self.plan.intern(function.name());
2333 let args = self.plan.add_expr_list(args);
2334 let named: Vec<u32> =
2335 written.iter().map(|(parameter, _, _)| self.plan.intern(parameter)).collect();
2336 let settings: Vec<ExprRef> = written.iter().map(|(_, _, expr)| *expr).collect();
2337 let options = self.plan.add_name_list(&named);
2338 let settings = self.plan.add_expr_list(&settings);
2339 let columns = self.plan.add_fields(&fields);
2340 let node = self.add_node(Node::TableFunction {
2341 index,
2342 function,
2343 args,
2344 options,
2345 settings,
2346 columns,
2347 });
2348 Ok((node, scope))
2349 }
2350
2351 fn file_paths(&self, expr: ExprRef, name: &str) -> Result<Vec<String>> {
2358 let mut paths = Vec::new();
2359 for pattern in self.file_patterns(expr, name)? {
2360 paths.extend(files(&pattern)?);
2361 }
2362 Ok(paths)
2363 }
2364
2365 fn file_patterns(&self, expr: ExprRef, name: &str) -> Result<Vec<String>> {
2377 let Expr::Constant(reference) = *self.plan.expr(expr) else {
2378 return Err(Error::not_implemented(
2379 "a table function file name that is not a constant",
2380 ));
2381 };
2382 match self.plan.value(reference) {
2383 Value::Varchar(path) => Ok(vec![path.clone()]),
2384 Value::Null => Err(Error::parser(format!("{name} cannot take NULL list as parameter"))),
2386 Value::List { values, .. } => values
2387 .iter()
2388 .map(|value| match value {
2389 Value::Varchar(path) => Ok(path.clone()),
2390 _ => Err(Error::parser(format!(
2391 "{name} reader cannot take NULL input as parameter"
2392 ))),
2393 })
2394 .collect(),
2395 other => {
2396 Err(Error::internal(format!("a file name bound as VARCHAR arrived as {other}")))
2397 }
2398 }
2399 }
2400
2401 fn side_of(
2419 &self,
2420 pending: &PendingSubquery,
2421 left_tables: &[u32],
2422 right_tables: &[u32],
2423 ) -> Option<Side> {
2424 let mut needs_left = false;
2425 let mut needs_right = false;
2426 let mut note = |binding: ColumnBinding| {
2427 needs_left |= left_tables.contains(&binding.table);
2428 needs_right |= right_tables.contains(&binding.table);
2429 };
2430 for &binding in &pending.reads {
2431 note(binding);
2432 }
2433 for &condition in &pending.conditions {
2438 self.plan.read_columns(condition, &mut |_, binding| note(binding));
2439 }
2440 match (needs_left, needs_right) {
2441 (true, true) => None,
2442 (_, true) => Some(Side::Right),
2443 _ => Some(Side::Left),
2444 }
2445 }
2446
2447 #[allow(clippy::too_many_arguments)]
2468 fn bind_pair_dependent_join(
2469 &mut self,
2470 kind: ast::JoinKind,
2471 independent: bool,
2472 left: NodeRef,
2473 right: NodeRef,
2474 pair: Vec<PendingSubquery>,
2475 conditions: Vec<ExprRef>,
2476 scope: Scope,
2477 ) -> Result<(NodeRef, Scope)> {
2478 if kind != ast::JoinKind::Inner {
2479 return Err(Error::not_implemented(
2480 "a subquery that reads both sides of that join, written in the condition of a join \
2481 that is not an inner join"
2482 .to_string(),
2483 ));
2484 }
2485 if !independent {
2488 return Err(Error::not_implemented(
2489 "a subquery that reads both sides of that join, written in the condition of a join \
2490 whose right side is lateral"
2491 .to_string(),
2492 ));
2493 }
2494 let mut node = self.add_node(Node::CrossProduct { left, right });
2495 for pending in pair {
2496 node = self.attach_subquery(node, pending);
2497 }
2498 let mut conditions = conditions.into_iter();
2502 let mut predicate = conditions.next().expect("a join condition was bound");
2503 for next in conditions {
2504 let children = self.plan.add_expr_list(&[predicate, next]);
2505 let conjunction = Expr::Conjunction { op: ConjunctionOp::And, children };
2506 predicate = self.plan.add_expr(conjunction, LogicalType::Boolean);
2507 }
2508 let node = self.add_node(Node::Filter { input: node, predicate });
2509 Ok((node, scope))
2510 }
2511
2512 #[allow(clippy::too_many_arguments)]
2513 fn bind_join(
2514 &mut self,
2515 ast: &Ast,
2516 left: ast::SourceRef,
2517 right: ast::SourceRef,
2518 kind: ast::JoinKind,
2519 natural: bool,
2520 on: ast::ExprRef,
2521 using: ast::Slice,
2522 ) -> Result<(NodeRef, Scope)> {
2523 let (left_node, left_scope) = self.bind_source(ast, left)?;
2524 let (right_node, right_scope, correlated) = self.bind_lateral(ast, right, &left_scope)?;
2525 if !correlated.is_empty()
2529 && !matches!(kind, ast::JoinKind::Inner | ast::JoinKind::Cross | ast::JoinKind::Left)
2530 {
2531 return Err(Error::binder(
2532 "The combining JOIN type must be INNER or LEFT for a LATERAL reference",
2533 ));
2534 }
2535 let split = left_scope.len();
2536 let left_tables: Vec<u32> =
2542 left_scope.columns.iter().map(|column| column.binding.table).collect();
2543 let right_tables: Vec<u32> =
2544 right_scope.columns.iter().map(|column| column.binding.table).collect();
2545 let mut scope = left_scope.concat(right_scope);
2546
2547 let merged: Vec<String> = if natural {
2550 let mut names = Vec::new();
2551 for (at, column) in scope.columns.iter().enumerate().take(split) {
2552 if scope.columns[split..].iter().any(|right| same_name(&right.name, &column.name))
2553 && !names.iter().any(|held: &String| same_name(held, &column.name))
2554 {
2555 let _ = at;
2556 names.push(column.name.clone());
2557 }
2558 }
2559 names
2560 } else {
2561 let mut names: Vec<String> = Vec::new();
2567 for name in ast.name(using) {
2568 if !names.iter().any(|held| same_name(held, name)) {
2569 names.push(name.to_string());
2570 }
2571 }
2572 names
2573 };
2574
2575 let mut conditions = Vec::new();
2576 let mut dropped = Vec::new();
2577 for name in &merged {
2578 let left_at = scope.columns[..split]
2579 .iter()
2580 .position(|column| same_name(&column.name, name))
2581 .ok_or_else(|| {
2582 Error::binder(format!(
2583 "column \"{name}\" specified in USING clause does not exist in left table"
2584 ))
2585 })?;
2586 let right_at = scope.columns[split..]
2587 .iter()
2588 .position(|column| same_name(&column.name, name))
2589 .map(|at| at + split)
2590 .ok_or_else(|| {
2591 Error::binder(format!(
2592 "column \"{name}\" specified in USING clause does not exist in right table"
2593 ))
2594 })?;
2595 let left_column = &scope.columns[left_at];
2596 let (left_binding, left_type) = (left_column.binding, left_column.ty.clone());
2597 let right_column = &scope.columns[right_at];
2598 let (right_binding, right_type) = (right_column.binding, right_column.ty.clone());
2599 let left_expr = self.plan.add_expr(Expr::Column(left_binding), left_type);
2600 let right_expr = self.plan.add_expr(Expr::Column(right_binding), right_type);
2601 conditions.push(self.compare(rudb_plan::CompareOp::Equal, left_expr, right_expr)?);
2602 dropped.push(right_at);
2603 }
2604 dropped.sort_unstable();
2607 for at in dropped.into_iter().rev() {
2608 scope.remove(at);
2609 }
2610
2611 let mut left_node = left_node;
2612 let mut right_node = right_node;
2613 let mut pair = Vec::new();
2614 if on != NONE {
2615 if !merged.is_empty() {
2616 return Err(Error::binder("a join cannot have both ON and USING"));
2617 }
2618 self.clause = "JOIN condition";
2619 let waiting = self.scalar_subqueries.len();
2620 let predicate = self.bind_expr(ast, on, &scope)?;
2621 conditions.push(self.as_boolean(predicate, "JOIN")?);
2622 for pending in self.scalar_subqueries.split_off(waiting) {
2623 match self.side_of(&pending, &left_tables, &right_tables) {
2624 Some(Side::Right) => right_node = self.attach_subquery(right_node, pending),
2625 Some(Side::Left) => left_node = self.attach_subquery(left_node, pending),
2626 None => pair.push(pending),
2627 }
2628 }
2629 }
2630
2631 if kind == ast::JoinKind::Cross && !conditions.is_empty() {
2632 return Err(Error::binder("a CROSS JOIN cannot have a condition"));
2633 }
2634 if !pair.is_empty() {
2635 return self.bind_pair_dependent_join(
2636 kind,
2637 correlated.is_empty(),
2638 left_node,
2639 right_node,
2640 pair,
2641 conditions,
2642 scope,
2643 );
2644 }
2645 if correlated.is_empty()
2649 && conditions.is_empty()
2650 && matches!(kind, ast::JoinKind::Cross | ast::JoinKind::Inner)
2651 {
2652 let node = self.add_node(Node::CrossProduct { left: left_node, right: right_node });
2653 return Ok((node, scope));
2654 }
2655 if matches!(kind, ast::JoinKind::Semi | ast::JoinKind::Anti) {
2664 scope.truncate(split);
2665 }
2666 let kind = match kind {
2667 ast::JoinKind::Inner | ast::JoinKind::Cross => JoinKind::Inner,
2668 ast::JoinKind::Left => JoinKind::Left,
2669 ast::JoinKind::Right => JoinKind::Right,
2670 ast::JoinKind::Full => JoinKind::Full,
2671 ast::JoinKind::Semi => JoinKind::Semi,
2672 ast::JoinKind::Anti => JoinKind::Anti,
2673 ast::JoinKind::Positional => JoinKind::Positional,
2674 };
2675 let conditions = self.plan.add_expr_list(&conditions);
2676 let node = if correlated.is_empty() {
2677 self.add_node(Node::Join {
2678 left: left_node,
2679 right: right_node,
2680 kind,
2681 conditions,
2682 build: BuildSide::default(),
2683 })
2684 } else {
2685 self.add_node(Node::DependentJoin {
2686 left: left_node,
2687 right: right_node,
2688 kind,
2689 conditions,
2690 })
2691 };
2692 Ok((node, scope))
2693 }
2694
2695 fn bind_filter(
2703 &mut self,
2704 ast: &Ast,
2705 filter: ast::ExprRef,
2706 scope: &Scope,
2707 ) -> Result<Option<ExprRef>> {
2708 if filter == NONE {
2709 return Ok(None);
2710 }
2711 let bound = self.bind_expr(ast, filter, scope)?;
2712 Ok(Some(self.checked_cast_to(bound, &LogicalType::Boolean, false)?))
2713 }
2714
2715 pub(crate) fn bind_aggregate(
2717 &mut self,
2718 ast: &Ast,
2719 name: &str,
2720 args: &[ast::ExprRef],
2721 distinct: bool,
2722 filter: ast::ExprRef,
2723 scope: &Scope,
2724 ) -> Result<ExprRef> {
2725 if self.in_filter {
2726 return Err(Error::binder("aggregate functions are not allowed in FILTER"));
2727 }
2728 if self.in_aggregate {
2729 return Err(Error::binder(format!(
2730 "aggregate function calls cannot be nested, and {name}() is inside one"
2731 )));
2732 }
2733 if self.aggregation.is_none() {
2734 return Err(Error::binder(format!(
2735 "aggregate function calls cannot be used in the {}",
2736 self.clause
2737 )));
2738 }
2739 self.in_aggregate = true;
2744 self.in_filter = true;
2745 let filter = self.bind_filter(ast, filter, scope);
2746 self.in_filter = false;
2747 self.in_aggregate = false;
2748 let filter = filter?;
2749
2750 self.in_aggregate = true;
2751 let mut bound = Vec::with_capacity(args.len());
2752 let mut failure = None;
2753 for &arg in args {
2754 match self.bind_expr(ast, arg, scope) {
2755 Ok(expr) => bound.push(expr),
2756 Err(error) => {
2757 failure = Some(error);
2758 break;
2759 }
2760 }
2761 }
2762 self.in_aggregate = false;
2763 if let Some(error) = failure {
2764 return Err(error);
2765 }
2766
2767 let types: Vec<LogicalType> =
2768 bound.iter().map(|&arg| self.plan.expr_type(arg).clone()).collect();
2769 let resolved = resolve(name, &types)?;
2770 let mut cast = Vec::with_capacity(bound.len());
2771 for (arg, wanted) in bound.iter().zip(&resolved.arguments) {
2772 cast.push(self.checked_cast_to(*arg, wanted, false)?);
2773 }
2774 let args = self.plan.add_expr_list(&cast);
2775 let name = self.plan.intern(resolved.name);
2776 let ty = resolved.returns;
2777 let call = self.plan.add_expr(Expr::Aggregate { name, args, distinct, filter }, ty.clone());
2778
2779 let existing = self.aggregation.as_ref().map(|held| held.aggregates.clone());
2782 let existing = existing.unwrap_or_default();
2783 let at = match existing.iter().position(|&held| self.same_expr(held, call)) {
2784 Some(at) => at,
2785 None => {
2786 let aggregation = self.aggregation.as_mut().expect("checked above");
2787 aggregation.aggregates.push(call);
2788 aggregation.aggregates.len() - 1
2789 }
2790 };
2791 let aggregation = self.aggregation.as_ref().expect("checked above");
2792 let (index, groups) = (aggregation.index, aggregation.groups.len());
2793 Ok(self.column(index, groups + at, ty))
2794 }
2795
2796 pub(crate) fn bind_window(
2804 &mut self,
2805 ast: &Ast,
2806 written: &WindowCall<'_>,
2807 scope: &Scope,
2808 ) -> Result<ExprRef> {
2809 let WindowCall { name, args, distinct, filter, ignore_nulls, spec } = *written;
2810 if self.in_aggregate {
2811 return Err(Error::binder(
2812 "aggregate function calls cannot contain window function calls",
2813 ));
2814 }
2815 if self.in_window {
2816 return Err(Error::binder("window function calls cannot be nested"));
2817 }
2818 let clause = if self.clause == "JOIN condition" { "WHERE clause" } else { self.clause };
2822 if clause != "SELECT clause" && clause != "ORDER BY clause" {
2823 return Err(Error::binder(format!("{clause} cannot contain window functions!")));
2824 }
2825
2826 let starred = args.iter().any(|&arg| {
2830 matches!(ast.expr(arg), ast::Expr::Star { qualifier, replacements }
2831 if qualifier.is_empty() && replacements.is_empty())
2832 });
2833 let (name, args): (&str, &[ast::ExprRef]) = if starred {
2834 if !same_name(name, "count") || args.len() != 1 {
2835 return Err(Error::binder(format!("* is not allowed in {name}()")));
2836 }
2837 ("count_star", &[])
2838 } else if same_name(name, "count") && args.is_empty() {
2839 ("count_star", &[])
2842 } else {
2843 (name, args)
2844 };
2845
2846 let held = ast.window(spec);
2847 self.in_window = true;
2848 let parts = self.window_parts(ast, args, held, scope);
2849 let filter = if parts.is_ok() { self.bind_filter(ast, filter, scope) } else { Ok(None) };
2854 self.in_window = false;
2855 let parts = parts?;
2856 let filter = filter?;
2857 let offsets = [parts.frame.start, parts.frame.end]
2860 .iter()
2861 .any(|end| matches!(end, WindowBound::Preceding(_) | WindowBound::Following(_)));
2862 if parts.frame.unit == WindowUnit::Range && offsets && parts.order.len() != 1 {
2863 return Err(Error::binder("RANGE frames must have only one ORDER BY expression"));
2864 }
2865
2866 let types: Vec<LogicalType> =
2867 parts.args.iter().map(|&arg| self.plan.expr_type(arg).clone()).collect();
2868 let resolved = window_signature(name, &types)?;
2869 if resolved.name == "fill" {
2872 let keys: Vec<LogicalType> =
2873 parts.order.iter().map(|key| self.plan.expr_type(key.expr).clone()).collect();
2874 refuse_fill(&types[0], &keys, distinct, ignore_nulls)?;
2875 }
2876 if distinct && kind_of(resolved.name) == Some(FunctionKind::Window) {
2880 return Err(Error::binder(format!(
2881 "DISTINCT is not implemented for the window function \"\"{name}\"\""
2882 )));
2883 }
2884 if filter.is_some() && kind_of(resolved.name) == Some(FunctionKind::Window) {
2887 return Err(Error::binder(format!(
2888 "FILTER is not implemented for the window function \"\"{name}\"\""
2889 )));
2890 }
2891 let mut cast = Vec::with_capacity(parts.args.len());
2892 for (arg, wanted) in parts.args.iter().zip(&resolved.arguments) {
2893 cast.push(self.checked_cast_to(*arg, wanted, false)?);
2894 }
2895 let args = self.plan.add_expr_list(&cast);
2896 let name = self.plan.intern(resolved.name);
2897 let ty = resolved.returns;
2898 let call = self
2899 .plan
2900 .add_expr(Expr::Window { name, args, distinct, filter, ignore_nulls }, ty.clone());
2901
2902 let at = self.window_run(parts.partition, parts.order, parts.frame, call);
2903 let index = self.windows.last().expect("the run was just filed").index;
2904 Ok(self.column(index, at, ty))
2905 }
2906
2907 fn window_run(
2914 &mut self,
2915 partition: Vec<ExprRef>,
2916 order: Vec<SortKey>,
2917 frame: WindowFrame,
2918 call: ExprRef,
2919 ) -> usize {
2920 let matches = self.windows.last().is_some_and(|run| {
2921 run.frame == frame
2922 && run.partition.len() == partition.len()
2923 && run.order.len() == order.len()
2924 && run.partition.iter().zip(&partition).all(|(&l, &r)| self.same_expr(l, r))
2925 && run.order.iter().zip(&order).all(|(l, r)| {
2926 l.descending == r.descending
2927 && l.nulls_first == r.nulls_first
2928 && self.same_expr(l.expr, r.expr)
2929 })
2930 });
2931 if !matches {
2932 let index = self.fresh_index();
2933 self.windows.push(WindowRun { index, partition, order, frame, calls: Vec::new() });
2934 }
2935 let calls = self.windows.last().expect("a run is open").calls.clone();
2938 if let Some(at) = calls.iter().position(|&held| self.same_expr(held, call)) {
2939 return at;
2940 }
2941 let run = self.windows.last_mut().expect("a run is open");
2942 run.calls.push(call);
2943 run.calls.len() - 1
2944 }
2945
2946 fn window_parts(
2952 &mut self,
2953 ast: &Ast,
2954 args: &[ast::ExprRef],
2955 held: ast::WindowSpec,
2956 scope: &Scope,
2957 ) -> Result<WindowParts> {
2958 let mut bound = Vec::with_capacity(args.len());
2959 for &arg in args {
2960 let expr = self.bind_expr(ast, arg, scope)?;
2961 bound.push(self.over_aggregate(expr, scope)?);
2962 }
2963 let mut partition = Vec::new();
2964 for &key in ast.expr_list(held.partition) {
2965 let expr = self.bind_expr(ast, key, scope)?;
2966 partition.push(self.over_aggregate(expr, scope)?);
2967 }
2968 let mut order = Vec::new();
2969 for item in ast.order_list(held.order).to_vec() {
2970 let expr = self.bind_expr(ast, item.expr, scope)?;
2971 let expr = self.over_aggregate(expr, scope)?;
2972 order.push(self.sort_key(expr, item));
2973 }
2974 let frame = WindowFrame {
2975 unit: match held.unit {
2976 ast::WindowUnit::Rows => WindowUnit::Rows,
2977 ast::WindowUnit::Range => WindowUnit::Range,
2978 ast::WindowUnit::Groups => WindowUnit::Groups,
2979 },
2980 start: self.window_bound(ast, held.start, scope)?,
2981 end: self.window_bound(ast, held.end, scope)?,
2982 exclude: match held.exclude {
2983 ast::WindowExclude::NoOthers => WindowExclude::NoOthers,
2984 ast::WindowExclude::CurrentRow => WindowExclude::CurrentRow,
2985 ast::WindowExclude::Group => WindowExclude::Group,
2986 ast::WindowExclude::Ties => WindowExclude::Ties,
2987 },
2988 };
2989 Ok(WindowParts { args: bound, partition, order, frame })
2990 }
2991
2992 fn window_bound(
2994 &mut self,
2995 ast: &Ast,
2996 bound: ast::WindowBound,
2997 scope: &Scope,
2998 ) -> Result<WindowBound> {
2999 let offset = |binder: &mut Self, written| {
3000 let expr = binder.bind_expr(ast, written, scope)?;
3001 binder.over_aggregate(expr, scope)
3002 };
3003 Ok(match bound {
3004 ast::WindowBound::UnboundedPreceding => WindowBound::UnboundedPreceding,
3005 ast::WindowBound::CurrentRow => WindowBound::CurrentRow,
3006 ast::WindowBound::UnboundedFollowing => WindowBound::UnboundedFollowing,
3007 ast::WindowBound::Preceding(written) => WindowBound::Preceding(offset(self, written)?),
3008 ast::WindowBound::Following(written) => WindowBound::Following(offset(self, written)?),
3009 })
3010 }
3011
3012 fn is_pending_subquery(&self, binding: ColumnBinding) -> bool {
3014 self.scalar_subqueries.iter().any(|pending| pending.index == binding.table)
3015 }
3016
3017 fn is_window_output(&self, binding: ColumnBinding) -> bool {
3019 self.windows.iter().any(|run| run.index == binding.table)
3020 }
3021
3022 fn is_correlation(&self, binding: ColumnBinding) -> bool {
3028 self.correlations.last().is_some_and(|frame| frame.contains(&binding))
3029 }
3030
3031 fn name_of(&self, binding: ColumnBinding, scope: &Scope) -> String {
3037 std::iter::once(scope)
3038 .chain(self.outer_scopes.iter().rev())
3039 .flat_map(|visible| visible.columns.iter())
3040 .find(|column| column.binding == binding)
3041 .map_or_else(|| "a column".to_string(), |column| format!("\"{}\"", column.name))
3042 }
3043
3044 pub(crate) fn over_aggregate(&mut self, expr: ExprRef, scope: &Scope) -> Result<ExprRef> {
3050 let Some(aggregation) = self.aggregation.as_ref() else {
3051 return Ok(expr);
3052 };
3053 let index = aggregation.index;
3054 let groups = aggregation.groups.clone();
3055 for (at, group) in groups.iter().enumerate() {
3056 if self.same_expr(expr, *group) {
3057 let ty = self.plan.expr_type(*group).clone();
3058 return Ok(self.column(index, at, ty));
3059 }
3060 }
3061 let ty = self.plan.expr_type(expr).clone();
3062 match self.plan.expr(expr).clone() {
3063 Expr::Column(binding) if binding.table == index => Ok(expr),
3064 Expr::Column(binding) if self.is_window_output(binding) => Ok(expr),
3069 Expr::Column(binding) if self.joined_above.contains(&binding.table) => Ok(expr),
3074 Expr::Column(binding) if self.is_correlation(binding) => Ok(expr),
3080 Expr::Column(binding) if self.is_pending_subquery(binding) => Err(Error::binder(
3089 "a correlated subquery over a grouped query is not supported here yet",
3090 )),
3091 Expr::Column(binding) => {
3092 let name = self.name_of(binding, scope);
3093 Err(Error::binder(format!(
3094 "column {name} must appear in the GROUP BY clause or must be part of an aggregate function"
3095 )))
3096 }
3097 Expr::Constant(_) | Expr::Aggregate { .. } | Expr::Window { .. } => Ok(expr),
3098 Expr::Cast { input, try_cast } => {
3099 let input = self.over_aggregate(input, scope)?;
3100 Ok(self.plan.add_expr(Expr::Cast { input, try_cast }, ty))
3101 }
3102 Expr::Compare { op, left, right } => {
3103 let left = self.over_aggregate(left, scope)?;
3104 let right = self.over_aggregate(right, scope)?;
3105 Ok(self.plan.add_expr(Expr::Compare { op, left, right }, ty))
3106 }
3107 Expr::Conjunction { op, children } => {
3108 let written = self.plan.expr_list(children).to_vec();
3109 let mut rewritten = Vec::with_capacity(written.len());
3110 for child in written {
3111 rewritten.push(self.over_aggregate(child, scope)?);
3112 }
3113 let children = self.plan.add_expr_list(&rewritten);
3114 Ok(self.plan.add_expr(Expr::Conjunction { op, children }, ty))
3115 }
3116 Expr::Function { name, args } => {
3117 let written = self.plan.expr_list(args).to_vec();
3118 let mut rewritten = Vec::with_capacity(written.len());
3119 for arg in written {
3120 rewritten.push(self.over_aggregate(arg, scope)?);
3121 }
3122 let args = self.plan.add_expr_list(&rewritten);
3123 Ok(self.plan.add_expr(Expr::Function { name, args }, ty))
3124 }
3125 Expr::Case { arms, otherwise } => {
3126 let written = self.plan.arm_list(arms).to_vec();
3127 let mut rewritten = Vec::with_capacity(written.len());
3128 for arm in written {
3129 let when = self.over_aggregate(arm.when, scope)?;
3130 let then = self.over_aggregate(arm.then, scope)?;
3131 rewritten.push(rudb_plan::Arm { when, then });
3132 }
3133 let otherwise = match otherwise {
3134 Some(expr) => Some(self.over_aggregate(expr, scope)?),
3135 None => None,
3136 };
3137 let arms = self.plan.add_arms(&rewritten);
3138 Ok(self.plan.add_expr(Expr::Case { arms, otherwise }, ty))
3139 }
3140 }
3141 }
3142
3143 pub(crate) fn same_expr(&self, left: ExprRef, right: ExprRef) -> bool {
3145 same_expr(&self.plan, left, right)
3146 }
3147}
3148
3149#[derive(Debug, Default)]
3159struct Options {
3160 binary_as_string: bool,
3163 all_varchar: bool,
3165 file_row_number: bool,
3170 given: Given,
3172}
3173
3174impl Options {
3175 fn of(written: &[(&'static str, Value, ExprRef)]) -> Result<Self> {
3182 let mut options = Self::default();
3183 for (parameter, value, _) in written {
3184 match (*parameter, value) {
3185 ("binary_as_string", Value::Boolean(on)) => options.binary_as_string = *on,
3186 ("all_varchar", Value::Boolean(on)) => options.all_varchar = *on,
3187 ("file_row_number", Value::Boolean(on)) => options.file_row_number = *on,
3188 _ => {}
3189 }
3190 }
3191 let named: Vec<(&str, Value)> =
3192 written.iter().map(|(parameter, value, _)| (*parameter, value.clone())).collect();
3193 options.given = csv_given(&named)?;
3194 Ok(options)
3195 }
3196}
3197
3198#[derive(Clone, Copy)]
3200struct Operator {
3201 op: SetOp,
3203 quantifier: Quantifier,
3205 by_name: bool,
3207}
3208
3209struct Merged {
3211 name: String,
3213 ty: LogicalType,
3215 left: Option<usize>,
3217 right: Option<usize>,
3219}
3220
3221fn match_by_position(left: &Scope, right: &Scope) -> Result<Vec<Merged>> {
3225 if left.len() != right.len() {
3226 return Err(Error::binder(format!(
3227 "Set operations can only apply to expressions with the same number of result columns, but left side has {} and right side has {}",
3228 left.len(),
3229 right.len()
3230 )));
3231 }
3232 let mut merged = Vec::with_capacity(left.len());
3233 for (at, (held, other)) in left.columns.iter().zip(&right.columns).enumerate() {
3234 merged.push(Merged {
3235 name: held.name.clone(),
3236 ty: meet(&held.ty, &other.ty)?,
3237 left: Some(at),
3238 right: Some(at),
3239 });
3240 }
3241 Ok(merged)
3242}
3243
3244fn match_by_name(left: &Scope, right: &Scope) -> Result<Vec<Merged>> {
3252 named_once(left)?;
3253 named_once(right)?;
3254 let mut merged = Vec::with_capacity(left.len() + right.len());
3255 for (at, held) in left.columns.iter().enumerate() {
3256 let other = right.columns.iter().position(|column| same_name(&column.name, &held.name));
3257 let ty = match other {
3258 Some(other) => meet(&held.ty, &right.columns[other].ty)?,
3259 None => held.ty.clone(),
3260 };
3261 merged.push(Merged { name: held.name.clone(), ty, left: Some(at), right: other });
3262 }
3263 for (at, held) in right.columns.iter().enumerate() {
3264 if left.columns.iter().any(|column| same_name(&column.name, &held.name)) {
3265 continue;
3266 }
3267 merged.push(Merged {
3268 name: held.name.clone(),
3269 ty: held.ty.clone(),
3270 left: None,
3271 right: Some(at),
3272 });
3273 }
3274 Ok(merged)
3275}
3276
3277fn named_once(scope: &Scope) -> Result<()> {
3283 for (at, held) in scope.columns.iter().enumerate() {
3284 if scope.columns[..at].iter().any(|column| same_name(&column.name, &held.name)) {
3285 return Err(Error::binder(format!(
3286 "UNION (ALL) BY NAME operation doesn't support duplicate names in the SELECT list - the name \"\"{}\"\" occurs multiple times",
3287 held.name
3288 )));
3289 }
3290 }
3291 Ok(())
3292}
3293
3294fn meet(left: &LogicalType, right: &LogicalType) -> Result<LogicalType> {
3296 left.promote(right).ok_or_else(|| {
3297 Error::binder(format!(
3298 "Cannot combine a column of type {left} with a column of type {right} in a set operation"
3299 ))
3300 })
3301}
3302
3303fn null_parameter(function: TableFunction, parameter: &str) -> String {
3312 match parameter {
3313 "header" => format!("\"{parameter}\" expects a non-null boolean value (e.g. TRUE or 1)"),
3314 "all_varchar" => format!("{} \"{parameter}\" cannot be NULL", function.name()),
3315 _ => format!("Cannot use NULL as argument to \"{parameter}\""),
3316 }
3317}
3318
3319fn missing_replacement(name: &str, input: &Scope) -> Error {
3324 Error::binder(format!(
3325 "Column \"{name}\" in REPLACE list not found in FROM clause{}",
3326 input.candidates()
3327 ))
3328}
3329
3330fn subtractable(ty: &LogicalType, ordering: bool) -> bool {
3339 if ty.is_numeric() {
3340 return true;
3341 }
3342 match ty {
3343 LogicalType::Date
3344 | LogicalType::Time
3345 | LogicalType::Timestamp
3346 | LogicalType::TimestampS
3347 | LogicalType::TimestampMs
3348 | LogicalType::TimestampNs
3349 | LogicalType::TimestampTz => true,
3350 LogicalType::TimeTz => ordering,
3351 _ => false,
3352 }
3353}
3354
3355fn refuse_fill(
3364 argument: &LogicalType,
3365 order: &[LogicalType],
3366 distinct: bool,
3367 ignore_nulls: bool,
3368) -> Result<()> {
3369 if !subtractable(argument, false) {
3370 return Err(Error::binder("FILL argument must support subtraction"));
3371 }
3372 let [key] = order else {
3373 return Err(Error::binder("FILL functions must have only one ORDER BY expression"));
3374 };
3375 if !subtractable(key, true) {
3376 return Err(Error::binder("FILL ordering must support subtraction"));
3377 }
3378 if distinct {
3379 return Err(Error::binder(
3380 "DISTINCT is not implemented for the window function \"\"fill\"\"",
3381 ));
3382 }
3383 if ignore_nulls {
3384 return Err(Error::binder(
3385 "RESPECT/IGNORE NULLS is not supported for the window function \"fill\"",
3386 ));
3387 }
3388 Ok(())
3389}
3390
3391fn window_signature(name: &str, types: &[LogicalType]) -> Result<Resolved> {
3398 match kind_of(name) {
3399 Some(FunctionKind::Aggregate | FunctionKind::Window) => resolve(name, types),
3400 Some(FunctionKind::Scalar) => {
3401 Err(Error::catalog(format!("{name} is not an aggregate function")))
3402 }
3403 None => Err(Error::catalog(format!("Aggregate Function with name {name} does not exist!"))),
3404 }
3405}
3406
3407fn same_expr(plan: &Plan, left: ExprRef, right: ExprRef) -> bool {
3409 if left == right {
3410 return true;
3411 }
3412 if plan.expr_type(left) != plan.expr_type(right) {
3413 return false;
3414 }
3415 let lists = |left, right| {
3416 let left: &[ExprRef] = plan.expr_list(left);
3417 let right: &[ExprRef] = plan.expr_list(right);
3418 left.len() == right.len()
3419 && left.iter().zip(right).all(|(&left, &right)| same_expr(plan, left, right))
3420 };
3421 match (plan.expr(left), plan.expr(right)) {
3422 (Expr::Column(left), Expr::Column(right)) => left == right,
3423 (Expr::Constant(left), Expr::Constant(right)) => plan.value(*left) == plan.value(*right),
3424 (
3425 Expr::Cast { input: left, try_cast: left_try },
3426 Expr::Cast { input: right, try_cast: right_try },
3427 ) => left_try == right_try && same_expr(plan, *left, *right),
3428 (
3429 Expr::Compare { op: left_op, left: left_a, right: left_b },
3430 Expr::Compare { op: right_op, left: right_a, right: right_b },
3431 ) => {
3432 left_op == right_op
3433 && same_expr(plan, *left_a, *right_a)
3434 && same_expr(plan, *left_b, *right_b)
3435 }
3436 (
3437 Expr::Conjunction { op: left_op, children: left_children },
3438 Expr::Conjunction { op: right_op, children: right_children },
3439 ) => left_op == right_op && lists(*left_children, *right_children),
3440 (
3441 Expr::Function { name: left_name, args: left_args },
3442 Expr::Function { name: right_name, args: right_args },
3443 ) => plan.string(*left_name) == plan.string(*right_name) && lists(*left_args, *right_args),
3444 (
3445 Expr::Aggregate {
3446 name: left_name,
3447 args: left_args,
3448 distinct: left_distinct,
3449 filter: left_filter,
3450 },
3451 Expr::Aggregate {
3452 name: right_name,
3453 args: right_args,
3454 distinct: right_distinct,
3455 filter: right_filter,
3456 },
3457 ) => {
3458 plan.string(*left_name) == plan.string(*right_name)
3459 && left_distinct == right_distinct
3460 && match (left_filter, right_filter) {
3461 (None, None) => true,
3462 (Some(left), Some(right)) => same_expr(plan, *left, *right),
3463 _ => false,
3464 }
3465 && lists(*left_args, *right_args)
3466 }
3467 (
3471 Expr::Window {
3472 name: left_name,
3473 args: left_args,
3474 distinct: left_distinct,
3475 filter: left_filter,
3476 ignore_nulls: left_nulls,
3477 },
3478 Expr::Window {
3479 name: right_name,
3480 args: right_args,
3481 distinct: right_distinct,
3482 filter: right_filter,
3483 ignore_nulls: right_nulls,
3484 },
3485 ) => {
3486 plan.string(*left_name) == plan.string(*right_name)
3487 && left_distinct == right_distinct
3488 && left_nulls == right_nulls
3489 && match (left_filter, right_filter) {
3490 (None, None) => true,
3491 (Some(left), Some(right)) => same_expr(plan, *left, *right),
3492 _ => false,
3493 }
3494 && lists(*left_args, *right_args)
3495 }
3496 (
3497 Expr::Case { arms: left_arms, otherwise: left_otherwise },
3498 Expr::Case { arms: right_arms, otherwise: right_otherwise },
3499 ) => {
3500 let left_arms = plan.arm_list(*left_arms);
3501 let right_arms = plan.arm_list(*right_arms);
3502 left_arms.len() == right_arms.len()
3503 && left_arms.iter().zip(right_arms).all(|(left, right)| {
3504 same_expr(plan, left.when, right.when) && same_expr(plan, left.then, right.then)
3505 })
3506 && match (left_otherwise, right_otherwise) {
3507 (None, None) => true,
3508 (Some(left), Some(right)) => same_expr(plan, *left, *right),
3509 _ => false,
3510 }
3511 }
3512 _ => false,
3513 }
3514}