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_parse::ast::{self, Ast, Distinct, LiteralKind, Nulls, Order, Quantifier, SetOp};
27use rudb_parse::{NONE, identifier_parts, parse_ast_with_case};
28use rudb_plan::{
29 BuildSide, ColumnBinding, Expr, ExprRef, JoinKind, Node, NodeRef, Plan, SetOpKind, SortKey,
30 WindowBound, WindowExclude, WindowFrame, WindowUnit,
31};
32
33use crate::expr::{describe, has_aggregate};
34use crate::parameters::Parameters;
35use crate::scope::{Scope, Visible};
36
37pub fn bind(ast: &Ast, catalog: &Catalog) -> Result<Plan> {
44 bind_with(ast, catalog, &Parameters::new(), &Session::new())
45}
46
47pub fn bind_with(
56 ast: &Ast,
57 catalog: &Catalog,
58 parameters: &Parameters,
59 session: &Session,
60) -> Result<Plan> {
61 let query = match ast.statements.as_slice() {
62 [ast::Statement::Query(query)] => *query,
63 [] => return Err(Error::binder("no statement to bind")),
64 [_] => return Err(Error::not_implemented("a statement that is not a query")),
67 _ => return Err(Error::not_implemented("a script of more than one statement")),
68 };
69 let mut binder = Binder::with(catalog, parameters, session);
70 let (root, _) = binder.bind_query(ast, query)?;
71 let mut plan = binder.into_plan();
72 plan.set_root(root);
73 plan.validate()?;
74 Ok(plan)
75}
76
77pub fn bind_sql(query: &str, catalog: &Catalog) -> Result<Plan> {
83 bind_sql_with(query, catalog, &Session::new())
84}
85
86pub fn bind_sql_with(query: &str, catalog: &Catalog, session: &Session) -> Result<Plan> {
92 let ast = parse_ast_with_case(query, session.semantics().identifier_case())?;
93 bind_with(&ast, catalog, &Parameters::new(), session)
94}
95
96#[derive(Debug)]
98pub(crate) struct Aggregation {
99 pub(crate) index: u32,
101 pub(crate) groups: Vec<ExprRef>,
103 pub(crate) aggregates: Vec<ExprRef>,
105}
106
107#[derive(Debug)]
115pub(crate) struct WindowRun {
116 index: u32,
118 partition: Vec<ExprRef>,
120 order: Vec<SortKey>,
122 frame: WindowFrame,
124 calls: Vec<ExprRef>,
126}
127
128pub(crate) struct WindowCall<'a> {
133 pub(crate) name: &'a str,
135 pub(crate) args: &'a [ast::ExprRef],
137 pub(crate) distinct: bool,
139 pub(crate) filter: ast::ExprRef,
141 pub(crate) ignore_nulls: bool,
143 pub(crate) spec: ast::WindowRef,
145}
146
147struct WindowParts {
149 args: Vec<ExprRef>,
151 partition: Vec<ExprRef>,
153 order: Vec<SortKey>,
155 frame: WindowFrame,
157}
158
159#[derive(Debug)]
166struct Read {
167 fields: Vec<Field>,
169 rows: Stat<u64>,
171 distincts: Vec<(String, u64)>,
173 zones: Option<Arc<dyn Zones>>,
175}
176
177impl Read {
178 fn uncounted(fields: Vec<Field>) -> Self {
180 Self { fields, rows: Stat::Unknown, distincts: Vec::new(), zones: None }
181 }
182}
183
184#[derive(Debug)]
186struct Materialized {
187 written: u32,
189 cte: u32,
191 name: String,
193 fields: Vec<Field>,
195}
196
197#[derive(Debug)]
198pub(crate) struct PendingSubquery {
199 pub(crate) node: NodeRef,
200 pub(crate) kind: JoinKind,
201 pub(crate) conditions: Vec<ExprRef>,
202 pub(crate) dependent: bool,
203 pub(crate) index: u32,
209}
210
211#[derive(Debug)]
213pub(crate) struct Binder<'a> {
214 catalog: &'a Catalog,
215 pub(crate) parameters: &'a Parameters,
217 pub(crate) session: &'a Session,
219 pub(crate) semantics: Semantics,
221 plan: Plan,
222 next_index: u32,
223 pub(crate) current_span: Span,
225 pub(crate) aggregation: Option<Aggregation>,
227 pub(crate) in_aggregate: bool,
229 pub(crate) in_filter: bool,
231 pub(crate) windows: Vec<WindowRun>,
233 pub(crate) in_window: bool,
235 pub(crate) scalar_subqueries: Vec<PendingSubquery>,
237 pub(crate) joined_above: Vec<u32>,
243 pub(crate) outer_scopes: Vec<Scope>,
244 pub(crate) lateral_scopes: Vec<usize>,
251 pub(crate) correlations: Vec<Vec<ColumnBinding>>,
252 pub(crate) clause: &'static str,
254 expanding: Vec<String>,
256 materialized: Vec<Materialized>,
262 next_cte: u32,
264 started: Option<i64>,
266}
267
268impl<'a> Binder<'a> {
269 pub(crate) fn with(
270 catalog: &'a Catalog,
271 parameters: &'a Parameters,
272 session: &'a Session,
273 ) -> Self {
274 Self {
275 catalog,
276 parameters,
277 session,
278 semantics: session.semantics(),
279 plan: Plan::new(),
280 next_index: 0,
281 current_span: Span::new(0, 0),
282 aggregation: None,
283 in_aggregate: false,
284 in_filter: false,
285 windows: Vec::new(),
286 in_window: false,
287 scalar_subqueries: Vec::new(),
288 joined_above: Vec::new(),
289 outer_scopes: Vec::new(),
290 lateral_scopes: Vec::new(),
291 correlations: Vec::new(),
292 clause: "SELECT clause",
293 expanding: Vec::new(),
294 materialized: Vec::new(),
295 next_cte: 0,
296 started: None,
297 }
298 }
299
300 pub(crate) fn catalog(&self) -> &Catalog {
301 self.catalog
302 }
303
304 pub(crate) fn instant(&mut self) -> i64 {
311 *self.started.get_or_insert_with(crate::context::micros_now)
312 }
313
314 pub(crate) fn plan(&self) -> &Plan {
315 &self.plan
316 }
317
318 pub(crate) fn plan_mut(&mut self) -> &mut Plan {
319 &mut self.plan
320 }
321
322 pub(crate) fn add_expr(&mut self, expr: Expr, ty: LogicalType) -> ExprRef {
323 self.plan.add_expr_at(expr, ty, self.current_span)
324 }
325
326 pub(crate) fn add_constant(&mut self, value: Value) -> ExprRef {
327 let ty = value.logical_type();
328 let reference = self.plan.add_value(value);
329 self.plan.add_expr_at(Expr::Constant(reference), ty, self.current_span)
330 }
331
332 pub(crate) fn add_node(&mut self, node: Node) -> NodeRef {
333 self.plan.add_node_at(node, self.current_span)
334 }
335
336 pub(crate) fn into_plan(self) -> Plan {
337 self.plan
338 }
339
340 pub(crate) fn fresh_index(&mut self) -> u32 {
342 let index = self.next_index;
343 self.next_index += 1;
344 index
345 }
346
347 fn column(&mut self, index: u32, position: usize, ty: LogicalType) -> ExprRef {
349 let binding = ColumnBinding::new(index, position as u32);
350 self.plan.add_expr(Expr::Column(binding), ty)
351 }
352
353 fn attach_scalar_subqueries(&mut self, mut input: NodeRef) -> NodeRef {
355 let subqueries = std::mem::take(&mut self.scalar_subqueries);
356 for pending in subqueries {
357 let PendingSubquery { node: mut right, kind, conditions, dependent, index: _ } =
358 pending;
359 if kind == JoinKind::Single && !self.semantics.scalar_subquery_error_on_multiple_rows()
360 {
361 right = self.add_node(Node::Limit { input: right, count: Some(1), offset: 0 });
362 }
363 let conditions = self.plan.add_expr_list(&conditions);
364 input = if dependent {
365 self.add_node(Node::DependentJoin { left: input, right, kind, conditions })
366 } else {
367 self.add_node(Node::Join {
368 left: input,
369 right,
370 kind,
371 conditions,
372 build: BuildSide::default(),
373 })
374 };
375 }
376 input
377 }
378
379 pub(crate) fn bind_query(
382 &mut self,
383 ast: &Ast,
384 query: ast::QueryRef,
385 ) -> Result<(NodeRef, Scope)> {
386 let span = ast.query_span(query);
387 let outer = std::mem::replace(&mut self.current_span, span);
388 let result =
389 self.bind_query_inner(ast, query).map_err(|error| error.with_fallback_span(span));
390 self.current_span = outer;
391 result
392 }
393
394 fn bind_query_inner(&mut self, ast: &Ast, query: ast::QueryRef) -> Result<(NodeRef, Scope)> {
395 let written = ast.query(query);
396 if written.ctes.is_empty() {
397 return self.bind_body(ast, &written);
398 }
399 let depth = self.materialized.len();
403 let result = self.bind_materialized(ast, &written);
404 self.materialized.truncate(depth);
405 result
406 }
407
408 fn bind_materialized(&mut self, ast: &Ast, written: &ast::Query) -> Result<(NodeRef, Scope)> {
414 let depth = self.materialized.len();
415 let held = ast.cte_list(written.ctes).to_vec();
416 let mut definitions = Vec::with_capacity(held.len());
417 for &index in &held {
418 definitions.push(self.bind_definition(ast, index)?);
419 }
420 let (mut node, scope) = self.bind_body(ast, written)?;
421 for (at, definition) in definitions.into_iter().enumerate().rev() {
422 let entry = &self.materialized[depth + at];
423 let cte = entry.cte;
424 let name = entry.name.clone();
425 let fields = entry.fields.clone();
426 let name = self.plan.intern(&name);
427 let columns = self.plan.add_fields(&fields);
428 node =
429 self.add_node(Node::MaterializedCte { definition, body: node, name, cte, columns });
430 }
431 Ok((node, scope))
432 }
433
434 fn bind_definition(&mut self, ast: &Ast, index: u32) -> Result<NodeRef> {
444 let held = ast.cte(index);
445 let name = ast.string(held.name).to_string();
446 let (node, mut scope) = self.bind_query(ast, held.query)?;
447 if !held.columns.is_empty() {
448 let names: Vec<&str> = ast.name(held.columns).collect();
449 scope.rename_prefix(&names);
450 }
451 let table = self.fresh_index();
452 let mut exprs = Vec::with_capacity(scope.len());
453 let mut names = Vec::with_capacity(scope.len());
454 for column in &scope.columns {
455 exprs.push(self.plan.add_expr(Expr::Column(column.binding), column.ty.clone()));
456 names.push(self.plan.intern(&column.name));
457 }
458 let exprs = self.plan.add_expr_list(&exprs);
459 let names = self.plan.add_name_list(&names);
460 let node = self.add_node(Node::Project { input: node, index: table, exprs, names });
461 let cte = self.next_cte;
462 self.next_cte += 1;
463 self.materialized.push(Materialized { written: index, cte, name, fields: scope.fields() });
464 Ok(node)
465 }
466
467 fn bind_body(&mut self, ast: &Ast, written: &ast::Query) -> Result<(NodeRef, Scope)> {
468 match written.body {
469 ast::QueryBody::Select(select) => self.bind_select(ast, select, written),
470 ast::QueryBody::SetOp { op, quantifier, by_name, left, right } => {
471 if by_name {
472 return Err(Error::not_implemented("UNION BY NAME"));
473 }
474 self.bind_set_op(ast, written, op, quantifier, left, right)
475 }
476 ast::QueryBody::Values(rows) => self.bind_values(ast, written, rows),
477 ast::QueryBody::Describe(inner) => self.bind_describe(ast, written, inner),
478 ast::QueryBody::Show { name, relation } => self.bind_show(ast, written, name, relation),
479 }
480 }
481
482 fn bind_show(
484 &mut self,
485 ast: &Ast,
486 query: &ast::Query,
487 name: ast::Slice,
488 relation: ast::QueryRef,
489 ) -> Result<(NodeRef, Scope)> {
490 let text = ast.name_text(name);
491 let parts: Vec<&str> = ast.name(name).collect();
492 let table_exists = self.catalog.resolve(&parts).is_ok();
493 let as_table = match self.semantics.show_behavior() {
494 ShowBehavior::Auto => table_exists,
495 ShowBehavior::Setting => false,
496 ShowBehavior::Table => true,
497 };
498 if as_table {
499 return self.bind_describe(ast, query, relation);
500 }
501 let Some((_, value)) =
502 self.session.iter().find(|(name, _)| name.eq_ignore_ascii_case(&text))
503 else {
504 return Err(Error::catalog(format!("Setting with name \"{text}\" does not exist")));
505 };
506 let field = Field::new(text, LogicalType::Varchar);
507 let expr = self.plan.add_constant(Value::Varchar(value.to_string()));
508 let row = self.plan.add_expr_list(&[expr]);
509 let rows = self.plan.add_rows(&[row]);
510 let columns = self.plan.add_fields(std::slice::from_ref(&field));
511 let index = self.fresh_index();
512 let node = self.add_node(Node::Values { index, columns, rows });
513 let mut scope = Scope::empty();
514 scope.push(Visible {
515 table: String::new(),
516 name: field.name,
517 binding: ColumnBinding::new(index, 0),
518 ty: LogicalType::Varchar,
519 not_null: false,
520 });
521 Ok((node, scope))
522 }
523
524 fn bind_describe(
540 &mut self,
541 ast: &Ast,
542 query: &ast::Query,
543 inner: ast::QueryRef,
544 ) -> Result<(NodeRef, Scope)> {
545 let (_, described) = self.bind_query(ast, inner)?;
546 let fields: Vec<Field> = ["column_name", "column_type", "null", "key", "default", "extra"]
547 .iter()
548 .map(|name| Field::new(*name, LogicalType::Varchar))
549 .collect();
550 let mut slices = Vec::with_capacity(described.columns.len());
551 for column in described.columns.clone() {
552 let written = [
555 column.name.clone(),
556 column.ty.to_string(),
557 if column.not_null { "NO" } else { "YES" }.to_owned(),
558 ];
559 let mut items: Vec<ExprRef> = written
560 .into_iter()
561 .map(|text| self.plan.add_constant(Value::Varchar(text)))
562 .collect();
563 for _ in 0..3 {
564 let empty = self.plan.add_constant(Value::Null);
565 items.push(self.cast_to(empty, &LogicalType::Varchar));
566 }
567 slices.push(self.plan.add_expr_list(&items));
568 }
569 let rows = self.plan.add_rows(&slices);
570 let columns = self.plan.add_fields(&fields);
571 let index = self.fresh_index();
572 let mut node = self.add_node(Node::Values { index, columns, rows });
573 let mut scope = Scope::empty();
574 for (at, field) in fields.iter().enumerate() {
575 scope.push(Visible {
576 table: String::new(),
577 name: field.name.clone(),
578 binding: ColumnBinding::new(index, at as u32),
579 ty: field.ty.clone(),
580 not_null: false,
581 });
582 }
583 let keys = self.sort_keys(ast, query, &scope, &[])?;
584 if !keys.is_empty() {
585 let keys = self.plan.add_sort_keys(&keys);
586 node = self.add_node(Node::Sort { input: node, keys });
587 }
588 node = self.apply_limit(ast, query, node)?;
589 Ok((node, scope))
590 }
591
592 fn passes_through(&self, expr: ExprRef, input: &Scope) -> bool {
598 let Expr::Column(binding) = *self.plan.expr(expr) else { return false };
599 input.columns.iter().any(|column| column.binding == binding && column.not_null)
600 }
601
602 fn bind_values(
609 &mut self,
610 ast: &Ast,
611 query: &ast::Query,
612 rows: ast::Slice,
613 ) -> Result<(NodeRef, Scope)> {
614 let written = ast.rows(rows).to_vec();
615 let Some(first) = written.first() else {
616 return Err(Error::binder("VALUES needs at least one row"));
617 };
618 let width = first.len as usize;
619 for (at, row) in written.iter().enumerate() {
620 if row.len as usize != width {
621 return Err(Error::binder(format!(
622 "VALUES lists must all be the same length, expected {width} columns but row {} has {}",
623 at + 1,
624 row.len
625 )));
626 }
627 }
628 let empty = Scope::empty();
630 let previous = std::mem::replace(&mut self.clause, "VALUES clause");
631 let mut bound: Vec<Vec<ExprRef>> = Vec::with_capacity(written.len());
632 for row in &written {
633 let mut items = Vec::with_capacity(width);
634 for &expr in ast.expr_list(*row) {
635 items.push(self.bind_expr(ast, expr, &empty)?);
636 }
637 bound.push(items);
638 }
639 self.clause = previous;
640 let mut types = Vec::with_capacity(width);
641 for at in 0..width {
642 let mut ty = self.plan.expr_type(bound[0][at]).clone();
643 for row in &bound[1..] {
644 let other = self.plan.expr_type(row[at]).clone();
645 ty = ty.promote(&other).ok_or_else(|| {
646 Error::binder(format!(
647 "Cannot combine a value of type {ty} with a value of type {other} in column {} of a VALUES",
648 at + 1
649 ))
650 })?;
651 }
652 types.push(ty);
653 }
654 let mut slices = Vec::with_capacity(bound.len());
655 for row in &bound {
656 let items: Vec<ExprRef> = row
657 .iter()
658 .zip(&types)
659 .map(|(&expr, ty)| self.checked_cast_to(expr, ty, false))
660 .collect::<Result<_>>()?;
661 slices.push(self.plan.add_expr_list(&items));
662 }
663 let rows = self.plan.add_rows(&slices);
664 let fields: Vec<Field> = types
665 .iter()
666 .enumerate()
667 .map(|(at, ty)| Field::new(format!("col{at}"), ty.clone()))
668 .collect();
669 let columns = self.plan.add_fields(&fields);
670 let index = self.fresh_index();
671 let mut node = self.add_node(Node::Values { index, columns, rows });
672 let mut scope = Scope::empty();
673 for (at, field) in fields.iter().enumerate() {
674 scope.push(Visible {
675 table: String::new(),
676 name: field.name.clone(),
677 binding: ColumnBinding::new(index, at as u32),
678 ty: field.ty.clone(),
679 not_null: false,
680 });
681 }
682 let keys = self.sort_keys(ast, query, &scope, &[])?;
683 if !keys.is_empty() {
684 let keys = self.plan.add_sort_keys(&keys);
685 node = self.add_node(Node::Sort { input: node, keys });
686 }
687 node = self.apply_limit(ast, query, node)?;
688 Ok((node, scope))
689 }
690
691 fn bind_set_op(
692 &mut self,
693 ast: &Ast,
694 query: &ast::Query,
695 op: SetOp,
696 quantifier: Quantifier,
697 left: ast::QueryRef,
698 right: ast::QueryRef,
699 ) -> Result<(NodeRef, Scope)> {
700 let (left_node, left_scope) = self.bind_query(ast, left)?;
701 let (right_node, right_scope) = self.bind_query(ast, right)?;
702 if left_scope.len() != right_scope.len() {
703 return Err(Error::binder(format!(
704 "Set operations can only apply to expressions with the same number of result columns, but left side has {} and right side has {}",
705 left_scope.len(),
706 right_scope.len()
707 )));
708 }
709 let mut types = Vec::with_capacity(left_scope.len());
711 for (left, right) in left_scope.columns.iter().zip(&right_scope.columns) {
712 let common = left.ty.promote(&right.ty).ok_or_else(|| {
713 Error::binder(format!(
714 "Cannot combine a column of type {} with a column of type {} in a set operation",
715 left.ty, right.ty
716 ))
717 })?;
718 types.push(common);
719 }
720 let left_node = self.conform(left_node, &left_scope, &types)?;
721 let right_node = self.conform(right_node, &right_scope, &types)?;
722 let index = self.fresh_index();
723 let kind = match op {
724 SetOp::Union => SetOpKind::Union,
725 SetOp::Except => SetOpKind::Except,
726 SetOp::Intersect => SetOpKind::Intersect,
727 };
728 let all = quantifier == Quantifier::All;
731 let mut node =
732 self.add_node(Node::SetOp { left: left_node, right: right_node, kind, all, index });
733 let mut scope = Scope::empty();
734 for (at, (column, ty)) in left_scope.columns.iter().zip(&types).enumerate() {
735 scope.push(Visible {
736 table: String::new(),
737 name: column.name.clone(),
738 binding: ColumnBinding::new(index, at as u32),
739 ty: ty.clone(),
740 not_null: false,
743 });
744 }
745 let keys = self.sort_keys(ast, query, &scope, &[])?;
749 if !keys.is_empty() {
750 let keys = self.plan.add_sort_keys(&keys);
751 node = self.add_node(Node::Sort { input: node, keys });
752 }
753 node = self.apply_limit(ast, query, node)?;
754 Ok((node, scope))
755 }
756
757 fn conform(&mut self, node: NodeRef, scope: &Scope, types: &[LogicalType]) -> Result<NodeRef> {
759 if scope.columns.iter().zip(types).all(|(column, ty)| &column.ty == ty) {
760 return Ok(node);
761 }
762 let index = self.fresh_index();
763 let mut exprs = Vec::with_capacity(types.len());
764 let mut names = Vec::with_capacity(types.len());
765 for (column, ty) in scope.columns.iter().zip(types) {
766 let expr = self.plan.add_expr(Expr::Column(column.binding), column.ty.clone());
767 exprs.push(self.checked_cast_to(expr, ty, false)?);
768 names.push(self.plan.intern(&column.name));
769 }
770 let exprs = self.plan.add_expr_list(&exprs);
771 let names = self.plan.add_name_list(&names);
772 Ok(self.add_node(Node::Project { input: node, index, exprs, names }))
773 }
774
775 fn bind_select(
778 &mut self,
779 ast: &Ast,
780 select: ast::SelectRef,
781 query: &ast::Query,
782 ) -> Result<(NodeRef, Scope)> {
783 let written = ast.select(select);
784 let outer_windows = std::mem::take(&mut self.windows);
788 let (mut node, input) = self.bind_from(ast, written.from)?;
789 node = self.attach_scalar_subqueries(node);
790
791 if written.filter != NONE {
792 self.clause = "WHERE clause";
793 let predicate = self.bind_expr(ast, written.filter, &input)?;
794 let predicate = self.as_boolean(predicate, "WHERE")?;
795 node = self.attach_scalar_subqueries(node);
796 node = self.add_node(Node::Filter { input: node, predicate });
797 }
798
799 let targets = ast.target_list(written.targets).to_vec();
800 if targets.is_empty() {
801 return Err(Error::binder("a SELECT needs at least one expression to select"));
802 }
803
804 let group_items = self.group_items(ast, &written, &targets)?;
805 let aggregating = !group_items.is_empty()
806 || written.having != NONE
807 || targets.iter().any(|target| has_aggregate(ast, target.expr));
808 if aggregating {
809 self.clause = "GROUP BY clause";
810 let mut groups = Vec::with_capacity(group_items.len());
811 for item in &group_items {
812 groups.push(self.bind_expr(ast, *item, &input)?);
813 }
814 let index = self.fresh_index();
815 self.aggregation = Some(Aggregation { index, groups, aggregates: Vec::new() });
816 }
817
818 self.clause = "SELECT clause";
819 let (mut exprs, mut names) = self.bind_targets(ast, &targets, &input)?;
820 let visible = exprs.len();
821
822 let mut having = None;
823 let mut above = Vec::new();
830 if written.having != NONE {
831 self.clause = "HAVING clause";
832 let before = self.scalar_subqueries.len();
833 let predicate = self.bind_expr(ast, written.having, &input)?;
834 for pending in self.scalar_subqueries.split_off(before) {
837 if pending.dependent {
838 self.scalar_subqueries.push(pending);
839 } else {
840 above.push(pending);
841 }
842 }
843 self.joined_above = above.iter().map(|pending| pending.index).collect();
844 let predicate = self.over_aggregate(predicate, &input)?;
845 let mut rewritten = Vec::with_capacity(above.len());
848 for mut pending in above {
849 let conditions = std::mem::take(&mut pending.conditions);
850 let mut over = Vec::with_capacity(conditions.len());
851 for condition in conditions {
852 over.push(self.over_aggregate(condition, &input)?);
853 }
854 pending.conditions = over;
855 rewritten.push(pending);
856 }
857 above = rewritten;
858 self.joined_above.clear();
859 having = Some(self.as_boolean(predicate, "HAVING")?);
860 }
861
862 let project = self.fresh_index();
865 let mut output = Scope::empty();
866 for (at, (expr, name)) in exprs.iter().zip(&names).enumerate() {
867 output.push(Visible {
868 table: String::new(),
869 name: name.clone(),
870 binding: ColumnBinding::new(project, at as u32),
871 ty: self.plan.expr_type(*expr).clone(),
872 not_null: self.passes_through(*expr, &input),
873 });
874 }
875
876 self.clause = "ORDER BY clause";
877 let mut extra = Vec::new();
878 let keys = self.select_sort_keys(
879 ast, query, &input, &output, project, &mut exprs, &mut names, &mut extra,
880 )?;
881 if !extra.is_empty() && written.distinct != Distinct::No {
882 return Err(Error::binder(
883 "For SELECT DISTINCT, ORDER BY expressions must appear in the select list",
884 ));
885 }
886 let on = self.distinct_on(ast, written.distinct, &output)?;
887
888 node = self.attach_scalar_subqueries(node);
889
890 if let Some(aggregation) = self.aggregation.take() {
891 let index = aggregation.index;
892 let groups = self.plan.add_expr_list(&aggregation.groups);
893 let aggregates = self.plan.add_expr_list(&aggregation.aggregates);
894 node = self.add_node(Node::Aggregate { input: node, index, groups, aggregates });
895 }
896 if !above.is_empty() {
897 debug_assert!(self.scalar_subqueries.is_empty(), "a query is waiting to be joined");
898 self.scalar_subqueries = above;
899 node = self.attach_scalar_subqueries(node);
900 }
901 if let Some(predicate) = having {
902 node = self.add_node(Node::Filter { input: node, predicate });
903 }
904
905 for run in std::mem::replace(&mut self.windows, outer_windows) {
909 let partition = self.plan.add_expr_list(&run.partition);
910 let order = self.plan.add_sort_keys(&run.order);
911 let expressions = self.plan.add_expr_list(&run.calls);
912 node = self.add_node(Node::Window {
913 input: node,
914 index: run.index,
915 partition,
916 order,
917 frame: run.frame,
918 expressions,
919 });
920 }
921
922 let interned: Vec<u32> = names.iter().map(|name| self.plan.intern(name)).collect();
923 let exprs_slice = self.plan.add_expr_list(&exprs);
924 let names_slice = self.plan.add_name_list(&interned);
925 node = self.add_node(Node::Project {
926 input: node,
927 index: project,
928 exprs: exprs_slice,
929 names: names_slice,
930 });
931
932 if written.distinct != Distinct::No {
933 let on = self.plan.add_expr_list(&on);
934 node = self.add_node(Node::Distinct { input: node, on });
935 }
936 if !keys.is_empty() {
937 let keys = self.plan.add_sort_keys(&keys);
938 node = self.add_node(Node::Sort { input: node, keys });
939 }
940 node = self.apply_limit(ast, query, node)?;
941
942 if extra.is_empty() {
943 output.columns.truncate(visible);
944 return Ok((node, output));
945 }
946 let index = self.fresh_index();
949 let mut kept = Vec::with_capacity(visible);
950 let mut kept_names = Vec::with_capacity(visible);
951 let mut scope = Scope::empty();
952 for (at, name) in names.iter().enumerate().take(visible) {
953 let ty = output.columns[at].ty.clone();
954 kept.push(self.column(project, at, ty.clone()));
955 kept_names.push(self.plan.intern(name));
956 scope.push(Visible {
957 table: String::new(),
958 name: name.clone(),
959 binding: ColumnBinding::new(index, at as u32),
960 ty,
961 not_null: output.columns[at].not_null,
962 });
963 }
964 let exprs = self.plan.add_expr_list(&kept);
965 let names = self.plan.add_name_list(&kept_names);
966 node = self.add_node(Node::Project { input: node, index, exprs, names });
967 Ok((node, scope))
968 }
969
970 fn bind_targets(
972 &mut self,
973 ast: &Ast,
974 targets: &[ast::Target],
975 input: &Scope,
976 ) -> Result<(Vec<ExprRef>, Vec<String>)> {
977 let mut exprs = Vec::with_capacity(targets.len());
978 let mut names = Vec::with_capacity(targets.len());
979 for target in targets {
980 if let ast::Expr::Star { qualifier, replacements } = ast.expr(target.expr) {
981 let table = ast.name(qualifier).last().map(str::to_string);
982 let expanded: Vec<Visible> =
983 input.star(table.as_deref())?.into_iter().cloned().collect();
984 let replacements = ast.target_list(replacements).to_vec();
985 let mut used = vec![false; replacements.len()];
986 for column in expanded {
987 let found = replacements.iter().zip(&mut used).find(|(replacement, _)| {
988 same_name(ast.string(replacement.alias), &column.name)
989 });
990 let (expr, name) = match found {
995 Some((replacement, used)) => {
996 *used = true;
997 let expr = self.bind_expr(ast, replacement.expr, input)?;
998 (expr, ast.string(replacement.alias).to_string())
999 }
1000 None => (
1001 self.plan.add_expr(Expr::Column(column.binding), column.ty),
1002 column.name,
1003 ),
1004 };
1005 exprs.push(self.over_aggregate(expr, input)?);
1006 names.push(name);
1007 }
1008 if let Some((replacement, _)) =
1012 replacements.iter().zip(&used).find(|(_, used)| !**used)
1013 {
1014 return Err(missing_replacement(ast.string(replacement.alias), input));
1015 }
1016 continue;
1017 }
1018 let expr = self.bind_expr(ast, target.expr, input)?;
1019 exprs.push(self.over_aggregate(expr, input)?);
1020 names.push(if target.alias == NONE {
1021 self.output_name(ast, target.expr, input)
1022 } else {
1023 ast.string(target.alias).to_string()
1024 });
1025 }
1026 Ok((exprs, names))
1027 }
1028
1029 fn output_name(&self, ast: &Ast, target: ast::ExprRef, input: &Scope) -> String {
1035 if let ast::Expr::Column { name } = ast.expr(target) {
1036 let parts: Vec<&str> = ast.name(name).collect();
1037 if let Ok(found) = input.resolve(&parts) {
1038 return found.name.clone();
1039 }
1040 }
1041 describe(ast, target, self.semantics)
1042 }
1043
1044 fn group_items(
1046 &self,
1047 ast: &Ast,
1048 select: &ast::Select,
1049 targets: &[ast::Target],
1050 ) -> Result<Vec<ast::ExprRef>> {
1051 if select.group_by_all {
1052 return Ok(targets
1055 .iter()
1056 .filter(|target| !has_aggregate(ast, target.expr))
1057 .map(|target| target.expr)
1058 .collect());
1059 }
1060 let mut items = Vec::new();
1061 for &item in ast.expr_list(select.group_by) {
1062 items.push(self.output_reference(ast, item, targets, "GROUP BY")?.unwrap_or(item));
1063 }
1064 Ok(items)
1065 }
1066
1067 fn output_reference(
1069 &self,
1070 ast: &Ast,
1071 item: ast::ExprRef,
1072 targets: &[ast::Target],
1073 clause: &str,
1074 ) -> Result<Option<ast::ExprRef>> {
1075 match ast.expr(item) {
1076 ast::Expr::Literal { kind: LiteralKind::Number, text } => {
1077 let written = ast.string(text);
1078 let position: usize = written.parse().map_err(|_| {
1079 Error::binder(format!("{clause} term {written} is not a column"))
1080 })?;
1081 if position == 0 || position > targets.len() {
1082 return Err(Error::binder(format!(
1083 "{clause} term out of range - should be between 1 and {}",
1084 targets.len()
1085 )));
1086 }
1087 Ok(Some(targets[position - 1].expr))
1088 }
1089 ast::Expr::Column { name } => {
1090 let parts: Vec<&str> = ast.name(name).collect();
1091 let [written] = parts.as_slice() else { return Ok(None) };
1092 let mut found = None;
1093 for target in targets {
1094 if target.alias != NONE && same_name(ast.string(target.alias), written) {
1095 if found.is_some() {
1096 return Ok(None);
1097 }
1098 found = Some(target.expr);
1099 }
1100 }
1101 Ok(found)
1102 }
1103 _ => Ok(None),
1104 }
1105 }
1106
1107 #[allow(clippy::too_many_arguments)]
1111 fn select_sort_keys(
1112 &mut self,
1113 ast: &Ast,
1114 query: &ast::Query,
1115 input: &Scope,
1116 output: &Scope,
1117 project: u32,
1118 exprs: &mut Vec<ExprRef>,
1119 names: &mut Vec<String>,
1120 extra: &mut Vec<usize>,
1121 ) -> Result<Vec<SortKey>> {
1122 if query.order_by_all {
1123 return Ok(self.every_column(output));
1124 }
1125 let items = ast.order_list(query.order_by).to_vec();
1126 let mut keys = Vec::with_capacity(items.len());
1127 for item in items {
1128 self.check_order_literal(ast, item.expr)?;
1129 let position = match self.output_position(ast, item.expr, output)? {
1130 Some(position) => position,
1131 None => {
1132 let bound = self.bind_expr(ast, item.expr, input)?;
1133 let bound = self.over_aggregate(bound, input)?;
1134 match exprs.iter().position(|&held| self.same_expr(held, bound)) {
1135 Some(position) => position,
1136 None => {
1137 exprs.push(bound);
1138 names.push(describe(ast, item.expr, self.semantics));
1139 extra.push(exprs.len() - 1);
1140 exprs.len() - 1
1141 }
1142 }
1143 }
1144 };
1145 let ty = self.plan.expr_type(exprs[position]).clone();
1146 let expr = self.column(project, position, ty);
1147 keys.push(self.sort_key(expr, item));
1148 }
1149 Ok(keys)
1150 }
1151
1152 fn sort_keys(
1154 &mut self,
1155 ast: &Ast,
1156 query: &ast::Query,
1157 output: &Scope,
1158 targets: &[ast::Target],
1159 ) -> Result<Vec<SortKey>> {
1160 if query.order_by_all {
1161 return Ok(self.every_column(output));
1162 }
1163 let items = ast.order_list(query.order_by).to_vec();
1164 let mut keys = Vec::with_capacity(items.len());
1165 for item in items {
1166 self.check_order_literal(ast, item.expr)?;
1167 let expr = match self.output_position(ast, item.expr, output)? {
1168 Some(position) => {
1169 let column = &output.columns[position];
1170 let (binding, ty) = (column.binding, column.ty.clone());
1171 self.plan.add_expr(Expr::Column(binding), ty)
1172 }
1173 None => {
1174 let _ = targets;
1175 self.bind_expr(ast, item.expr, output)?
1176 }
1177 };
1178 keys.push(self.sort_key(expr, item));
1179 }
1180 Ok(keys)
1181 }
1182
1183 fn every_column(&mut self, output: &Scope) -> Vec<SortKey> {
1184 let columns: Vec<(ColumnBinding, LogicalType)> =
1185 output.columns.iter().map(|column| (column.binding, column.ty.clone())).collect();
1186 columns
1187 .into_iter()
1188 .map(|(binding, ty)| {
1189 let expr = self.plan.add_expr(Expr::Column(binding), ty);
1190 let descending = self.semantics.default_descending();
1191 SortKey { expr, descending, nulls_first: self.semantics.nulls_first(descending) }
1192 })
1193 .collect()
1194 }
1195
1196 fn sort_key(&self, expr: ExprRef, item: ast::OrderItem) -> SortKey {
1198 let descending = match item.order {
1199 Order::Unstated => self.semantics.default_descending(),
1200 Order::Ascending => false,
1201 Order::Descending => true,
1202 };
1203 let nulls_first = match item.nulls {
1204 Nulls::First => true,
1205 Nulls::Last => false,
1206 Nulls::Unstated => self.semantics.nulls_first(descending),
1207 };
1208 SortKey { expr, descending, nulls_first }
1209 }
1210
1211 fn output_position(
1213 &self,
1214 ast: &Ast,
1215 item: ast::ExprRef,
1216 output: &Scope,
1217 ) -> Result<Option<usize>> {
1218 match ast.expr(item) {
1219 ast::Expr::Literal { kind: LiteralKind::Number, text } => {
1220 let written = ast.string(text);
1221 if written.contains(['.', 'e', 'E']) {
1222 return Ok(None);
1223 }
1224 let position: usize = written.parse().map_err(|_| {
1225 Error::binder(format!("ORDER BY term {written} is not a column"))
1226 })?;
1227 if position == 0 || position > output.len() {
1228 return Err(Error::binder(format!(
1229 "ORDER BY term out of range - should be between 1 and {}",
1230 output.len()
1231 )));
1232 }
1233 Ok(Some(position - 1))
1234 }
1235 ast::Expr::Column { name } => {
1236 let parts: Vec<&str> = ast.name(name).collect();
1237 let [written] = parts.as_slice() else { return Ok(None) };
1238 Ok(output.position_of(None, written))
1239 }
1240 _ => Ok(None),
1241 }
1242 }
1243
1244 fn check_order_literal(&self, ast: &Ast, item: ast::ExprRef) -> Result<()> {
1246 if !self.semantics.order_by_non_integer_literal()
1247 && matches!(
1248 ast.expr(item),
1249 ast::Expr::Literal { kind, text }
1250 if kind != LiteralKind::Number
1251 || ast.string(text).contains(['.', 'e', 'E'])
1252 )
1253 {
1254 return Err(Error::binder(
1255 "ORDER BY non-integer literal has no effect.\n* SET order_by_non_integer_literal=true to allow this behavior.",
1256 ));
1257 }
1258 Ok(())
1259 }
1260
1261 fn distinct_on(
1263 &mut self,
1264 ast: &Ast,
1265 distinct: Distinct,
1266 output: &Scope,
1267 ) -> Result<Vec<ExprRef>> {
1268 let Distinct::On(items) = distinct else {
1269 return Ok(Vec::new());
1270 };
1271 let items = ast.expr_list(items).to_vec();
1272 let mut on = Vec::with_capacity(items.len());
1273 for item in items {
1274 let Some(position) = self.output_position(ast, item, output)? else {
1275 return Err(Error::not_implemented(
1276 "DISTINCT ON an expression that is not in the select list",
1277 ));
1278 };
1279 let column = &output.columns[position];
1280 let (binding, ty) = (column.binding, column.ty.clone());
1281 on.push(self.plan.add_expr(Expr::Column(binding), ty));
1282 }
1283 Ok(on)
1284 }
1285
1286 fn apply_limit(&mut self, ast: &Ast, query: &ast::Query, input: NodeRef) -> Result<NodeRef> {
1287 if query.limit_percent {
1288 return Err(Error::not_implemented("LIMIT with a percentage"));
1289 }
1290 let count = self.constant_count(ast, query.limit, "LIMIT")?;
1291 let offset = self.constant_count(ast, query.offset, "OFFSET")?.unwrap_or(0);
1292 if count.is_none() && offset == 0 {
1293 return Ok(input);
1294 }
1295 Ok(self.add_node(Node::Limit { input, count, offset }))
1296 }
1297
1298 fn constant_count(
1300 &mut self,
1301 ast: &Ast,
1302 written: ast::ExprRef,
1303 clause: &str,
1304 ) -> Result<Option<u64>> {
1305 if written == NONE {
1306 return Ok(None);
1307 }
1308 self.clause = "LIMIT clause";
1309 let scope = Scope::empty();
1310 let bound = self.bind_expr(ast, written, &scope)?;
1311 let Expr::Constant(value) = *self.plan.expr(bound) else {
1312 return Err(Error::not_implemented(format!("a {clause} that is not a constant")));
1313 };
1314 let count = match self.plan.value(value) {
1315 Value::Null => return Ok(None),
1316 Value::TinyInt(count) => i128::from(*count),
1317 Value::SmallInt(count) => i128::from(*count),
1318 Value::Integer(count) => i128::from(*count),
1319 Value::BigInt(count) => i128::from(*count),
1320 Value::HugeInt(count) => *count,
1321 other => {
1322 return Err(Error::binder(format!(
1323 "{clause} takes a whole number of rows, not a value of type {}",
1324 other.logical_type()
1325 )));
1326 }
1327 };
1328 u64::try_from(count)
1329 .map(Some)
1330 .map_err(|_| Error::binder(format!("{clause} must not be negative")))
1331 }
1332
1333 fn bind_from(&mut self, ast: &Ast, from: ast::Slice) -> Result<(NodeRef, Scope)> {
1336 let sources = ast.source_list(from).to_vec();
1337 let Some((first, rest)) = sources.split_first() else {
1338 return Ok((self.add_node(Node::Dummy), Scope::empty()));
1341 };
1342 let (mut node, mut scope) = self.bind_source(ast, *first)?;
1343 for source in rest {
1344 let (right, right_scope, correlations) = self.bind_lateral(ast, *source, &scope)?;
1345 node = if correlations.is_empty() {
1346 self.add_node(Node::CrossProduct { left: node, right })
1347 } else {
1348 let conditions = self.plan.add_expr_list(&[]);
1349 self.add_node(Node::DependentJoin {
1350 left: node,
1351 right,
1352 kind: JoinKind::Inner,
1353 conditions,
1354 })
1355 };
1356 scope = scope.concat(right_scope);
1357 }
1358 Ok((node, scope))
1359 }
1360
1361 fn bind_lateral(
1373 &mut self,
1374 ast: &Ast,
1375 source: ast::SourceRef,
1376 left: &Scope,
1377 ) -> Result<(NodeRef, Scope, Vec<ColumnBinding>)> {
1378 self.lateral_scopes.push(self.outer_scopes.len());
1379 self.outer_scopes.push(left.clone());
1380 self.correlations.push(Vec::new());
1381 let bound = self.bind_source(ast, source);
1382 let read = self.correlations.pop().expect("correlation frame");
1383 self.outer_scopes.pop();
1384 self.lateral_scopes.pop();
1385 let (node, scope) = bound?;
1386
1387 let mut here = Vec::new();
1388 for binding in read {
1389 if left.columns.iter().any(|column| column.binding == binding) {
1390 here.push(binding);
1391 } else if let Some(enclosing) = self.correlations.last_mut() {
1392 if !enclosing.contains(&binding) {
1393 enclosing.push(binding);
1394 }
1395 }
1396 }
1397 Ok((node, scope, here))
1407 }
1408
1409 fn bind_source(&mut self, ast: &Ast, source: ast::SourceRef) -> Result<(NodeRef, Scope)> {
1410 match ast.source(source) {
1411 ast::Source::Table { name, alias, columns } => {
1412 self.bind_table(ast, name, alias, columns)
1413 }
1414 ast::Source::Function { name, args, alias, columns, pragma } => {
1415 self.bind_table_function(ast, name, args, alias, columns, pragma)
1416 }
1417 ast::Source::Subquery { query, alias, columns } => {
1418 let (node, mut scope) = self.bind_query(ast, query)?;
1419 let label = if alias == NONE {
1420 "unnamed_subquery".to_string()
1421 } else {
1422 ast.string(alias).to_string()
1423 };
1424 scope.relabel(&label);
1425 if !columns.is_empty() {
1426 let names: Vec<&str> = ast.name(columns).collect();
1427 scope.rename(&names, &label)?;
1428 }
1429 Ok((node, scope))
1430 }
1431 ast::Source::Values { rows, alias, columns } => {
1432 let bare = ast::Query::bare(ast::QueryBody::Values(rows));
1433 let (node, mut scope) = self.bind_values(ast, &bare, rows)?;
1434 let label =
1435 if alias == NONE { String::new() } else { ast.string(alias).to_string() };
1436 scope.relabel(&label);
1437 if !columns.is_empty() {
1438 let names: Vec<&str> = ast.name(columns).collect();
1439 scope.rename(&names, &label)?;
1440 }
1441 Ok((node, scope))
1442 }
1443 ast::Source::Cte { cte, alias, columns } => {
1444 self.bind_cte_scan(ast, cte, alias, columns)
1445 }
1446 ast::Source::Join { left, right, kind, natural, on, using } => {
1447 self.bind_join(ast, left, right, kind, natural, on, using)
1448 }
1449 }
1450 }
1451
1452 fn bind_cte_scan(
1459 &mut self,
1460 ast: &Ast,
1461 written: u32,
1462 alias: ast::StrRef,
1463 columns: ast::Slice,
1464 ) -> Result<(NodeRef, Scope)> {
1465 let Some(held) = self.materialized.iter().rev().find(|held| held.written == written) else {
1466 let name = ast.string(ast.cte(written).name);
1467 return Err(Error::binder(format!("Table with name {name} does not exist!")));
1468 };
1469 let cte = held.cte;
1470 let fields = held.fields.clone();
1471 let text = held.name.clone();
1472 let label = if alias == NONE { text.clone() } else { ast.string(alias).to_string() };
1473 let name = self.plan.intern(&text);
1474 let index = self.fresh_index();
1475 let mut scope = Scope::empty();
1476 for (at, field) in fields.iter().enumerate() {
1477 scope.push(Visible {
1478 table: label.clone(),
1479 name: field.name.clone(),
1480 binding: ColumnBinding::new(index, at as u32),
1481 ty: field.ty.clone(),
1482 not_null: field.not_null,
1483 });
1484 }
1485 if !columns.is_empty() {
1486 let names: Vec<&str> = ast.name(columns).collect();
1487 scope.rename(&names, &label)?;
1488 }
1489 let columns = self.plan.add_fields(&fields);
1490 let node = self.add_node(Node::CteScan { index, cte, name, columns });
1491 Ok((node, scope))
1492 }
1493
1494 fn bind_table(
1495 &mut self,
1496 ast: &Ast,
1497 name: ast::Slice,
1498 alias: ast::StrRef,
1499 columns: ast::Slice,
1500 ) -> Result<(NodeRef, Scope)> {
1501 let parts: Vec<&str> = ast.name(name).collect();
1502 let catalog = self.catalog;
1503 let resolved = match catalog.resolve(&parts) {
1506 Ok(resolved) => resolved,
1507 Err(missing) => {
1508 return self.bind_replacement_scan(ast, &parts, alias, columns, missing);
1509 }
1510 };
1511 if catalog.entry(&resolved)? == Entry::View {
1512 return self.bind_view(ast, &resolved, alias, columns);
1513 }
1514 let table = catalog.table(&resolved)?;
1515 let fields: Vec<Field> = table.columns().to_vec();
1516 let label =
1517 if alias == NONE { resolved.table.clone() } else { ast.string(alias).to_string() };
1518 let index = self.fresh_index();
1519 let mut scope = Scope::empty();
1520 for (at, field) in fields.iter().enumerate() {
1521 scope.push(Visible {
1522 table: label.clone(),
1523 name: field.name.clone(),
1524 binding: ColumnBinding::new(index, at as u32),
1525 ty: field.ty.clone(),
1526 not_null: field.not_null,
1527 });
1528 }
1529 if !columns.is_empty() {
1530 let names: Vec<&str> = ast.name(columns).collect();
1531 scope.rename(&names, &label)?;
1532 }
1533 let catalog_name = self.plan.intern(&resolved.catalog);
1534 let schema = self.plan.intern(&resolved.schema);
1535 let table_name = self.plan.intern(&resolved.table);
1536 let alias = self.plan.intern(&label);
1537 let columns = self.plan.add_fields(&fields);
1538 let node = self.add_node(Node::Get {
1539 catalog: catalog_name,
1540 schema,
1541 table: table_name,
1542 alias,
1543 index,
1544 columns,
1545 });
1546 Ok((node, scope))
1547 }
1548
1549 fn bind_view(
1561 &mut self,
1562 ast: &Ast,
1563 name: &QualifiedName,
1564 alias: ast::StrRef,
1565 columns: ast::Slice,
1566 ) -> Result<(NodeRef, Scope)> {
1567 let view = self.catalog.view(name)?;
1568 let full = name.to_string();
1569 if self.expanding.contains(&full) {
1570 return Err(Error::binder(format!(
1574 "infinite recursion detected: attempting to recursively bind view \"\"{}\"\"",
1575 name.table
1576 )));
1577 }
1578 let body = parse_ast_with_case(view.sql(), self.semantics.identifier_case())?;
1579 let query = match body.statements.as_slice() {
1580 [ast::Statement::Query(query)] => *query,
1581 _ => return Err(Error::binder(format!("view \"{}\" is not a query", name.table))),
1584 };
1585 self.expanding.push(full);
1586 let bound = self.bind_query(&body, query);
1587 self.expanding.pop();
1588 let (node, mut scope) = bound?;
1589
1590 let aliases: Vec<&str> = view.aliases().iter().map(String::as_str).collect();
1591 if !aliases.is_empty() {
1592 scope.rename(&aliases, "unnamed_subquery")?;
1593 }
1594 view.remember(scope.fields());
1601 let label = if alias == NONE { name.table.clone() } else { ast.string(alias).to_string() };
1602 scope.relabel(&label);
1603 if !columns.is_empty() {
1604 let names: Vec<&str> = ast.name(columns).collect();
1605 scope.rename(&names, &label)?;
1606 }
1607 Ok((node, scope))
1608 }
1609
1610 fn bind_table_function(
1618 &mut self,
1619 ast: &Ast,
1620 name: ast::Slice,
1621 args: ast::Slice,
1622 alias: ast::StrRef,
1623 columns: ast::Slice,
1624 pragma: bool,
1625 ) -> Result<(NodeRef, Scope)> {
1626 let parts: Vec<&str> = ast.name(name).collect();
1627 let function_name = *parts.last().unwrap_or(&"");
1631 if let Some(schema) = parts.iter().rev().nth(1) {
1632 if !schema.eq_ignore_ascii_case("main") && !schema.eq_ignore_ascii_case("system") {
1633 return Err(Error::catalog(format!(
1634 "Table Function with name {} does not exist!",
1635 parts.join(".")
1636 )));
1637 }
1638 }
1639 let Some(called) = TableFunction::lookup(function_name) else {
1643 if pragma {
1644 if args.is_empty() && self.catalog.resolve(&parts).is_ok() {
1650 return self.bind_table(ast, name, alias, columns);
1651 }
1652 let spelled = function_name.strip_prefix("pragma_").unwrap_or(function_name);
1653 return Err(Error::catalog(format!(
1654 "Pragma Function with name {spelled} does not exist!"
1655 )));
1656 }
1657 return Err(Error::catalog(format!(
1658 "Table Function with name {function_name} does not exist!"
1659 )));
1660 };
1661 let written = ast.target_list(args).to_vec();
1662 let empty = Scope::empty();
1663 let previous = std::mem::replace(&mut self.clause, "table function arguments");
1664 let mut bound = Vec::new();
1665 let mut written_options = Vec::new();
1666 for argument in written {
1667 let expr = self.bind_expr(ast, argument.expr, &empty)?;
1668 if argument.alias == NONE {
1669 bound.push(expr);
1670 } else {
1671 let name = ast.string(argument.alias).to_string();
1672 let (parameter, value) = self.named_argument(called, &name, expr)?;
1673 written_options.push((parameter, value, expr));
1674 }
1675 }
1676 self.clause = previous;
1677 let options = Options::of(&written_options)?;
1678
1679 let given: Vec<LogicalType> =
1682 bound.iter().map(|&expr| self.plan.expr_type(expr).clone()).collect();
1683 let resolved = if pragma {
1684 resolve_pragma(function_name, &given)?
1685 } else {
1686 resolve_table(function_name, &given)?
1687 };
1688 let mut cast: Vec<ExprRef> = bound
1689 .iter()
1690 .zip(&resolved.arguments)
1691 .map(|(&expr, ty)| self.checked_cast_to(expr, ty, false))
1692 .collect::<Result<_>>()?;
1693
1694 if resolved.function.takes_a_name() {
1695 let Columns::Fixed(fields) = resolved.columns else {
1696 return Err(Error::internal("a pragma that resolved to a file"));
1697 };
1698 let [argument] = cast[..] else {
1699 return Err(Error::internal("a pragma that resolved to more than one name"));
1700 };
1701 return self.bind_pragma(ast, resolved.function, &fields, argument, alias, columns);
1702 }
1703 let mut measured = Stat::Unknown;
1706 let mut counted: Vec<(String, u64)> = Vec::new();
1707 let mut bounded: Option<Arc<dyn Zones>> = None;
1708 let fields = match resolved.columns {
1709 Columns::Fixed(fields) => fields,
1710 columns => {
1711 let paths = self.file_paths(cast[0], resolved.function.name())?;
1716 let mut fields = match columns {
1717 Columns::Csv => csv_fields(&paths, options.given)?,
1720 _ => {
1721 let footers = parquet_footers(&paths)?;
1722 measured = footers.rows;
1723 counted = footers.distincts;
1724 bounded = footers.zones;
1725 footers.fields
1726 }
1727 };
1728 if options.all_varchar {
1729 for field in &mut fields {
1734 field.ty = LogicalType::Varchar;
1735 }
1736 }
1737 if options.binary_as_string {
1738 for field in &mut fields {
1743 if field.ty == LogicalType::Blob {
1744 field.ty = LogicalType::Varchar;
1745 }
1746 }
1747 }
1748 if options.file_row_number {
1749 if fields.iter().any(|field| field.name == FILE_ROW_NUMBER) {
1755 return Err(Error::binder(format!(
1756 "Duplicate column name \"{FILE_ROW_NUMBER}\": the file already has a \
1757 column of that name, so file_row_number cannot add one"
1758 )));
1759 }
1760 fields.push(Field::required(FILE_ROW_NUMBER.to_string(), LogicalType::BigInt));
1761 }
1762 cast = paths.iter().map(|path| self.path_constant(path)).collect();
1763 fields
1764 }
1765 };
1766 let label = if alias == NONE {
1767 resolved.function.name().to_string()
1768 } else {
1769 ast.string(alias).to_string()
1770 };
1771 let names: Vec<&str> = ast.name(columns).collect();
1772 self.table_function_source(
1773 resolved.function,
1774 &cast,
1775 &written_options,
1776 Read { fields, rows: measured, distincts: counted, zones: bounded },
1777 &label,
1778 &names,
1779 )
1780 }
1781
1782 fn bind_pragma(
1795 &mut self,
1796 ast: &Ast,
1797 function: TableFunction,
1798 fields: &[Field],
1799 argument: ExprRef,
1800 alias: ast::StrRef,
1801 columns: ast::Slice,
1802 ) -> Result<(NodeRef, Scope)> {
1803 let written = self.pragma_name(argument, function)?;
1804 let parts = identifier_parts(&written);
1805 let spelled: Vec<&str> = parts.iter().map(String::as_str).collect();
1806 let name = self.catalog.resolve(&spelled)?;
1807 let described = self.described(ast, &name)?;
1808 let mut rows = Vec::with_capacity(described.len());
1809 for (at, field) in described.iter().enumerate() {
1810 let items = if matches!(function, TableFunction::PragmaShow) {
1811 self.describing(field)
1812 } else {
1813 self.table_info(at, field)
1814 };
1815 rows.push(self.plan.add_expr_list(&items));
1816 }
1817 let rows = self.plan.add_rows(&rows);
1818 let held = self.plan.add_fields(fields);
1819 let index = self.fresh_index();
1820 let node = self.add_node(Node::Values { index, columns: held, rows });
1821 let label =
1822 if alias == NONE { function.name().to_string() } else { ast.string(alias).to_string() };
1823 let mut scope = Scope::empty();
1824 for (at, field) in fields.iter().enumerate() {
1825 scope.push(Visible {
1826 table: label.clone(),
1827 name: field.name.clone(),
1828 binding: ColumnBinding::new(index, at as u32),
1829 ty: field.ty.clone(),
1830 not_null: false,
1831 });
1832 }
1833 if !columns.is_empty() {
1834 let names: Vec<&str> = ast.name(columns).collect();
1835 scope.rename(&names, &label)?;
1836 }
1837 Ok((node, scope))
1838 }
1839
1840 fn pragma_name(&self, argument: ExprRef, function: TableFunction) -> Result<String> {
1850 let Expr::Constant(reference) = *self.plan.expr(argument) else {
1851 return Err(Error::not_implemented(format!(
1852 "{}() given a name that is not a constant",
1853 function.name()
1854 )));
1855 };
1856 match self.plan.value(reference) {
1857 Value::Varchar(name) => Ok(name.clone()),
1858 Value::Null => Ok("NULL".to_string()),
1859 other => {
1860 Err(Error::internal(format!("a pragma name bound as VARCHAR arrived as {other}")))
1861 }
1862 }
1863 }
1864
1865 fn described(&mut self, ast: &Ast, name: &QualifiedName) -> Result<Vec<Field>> {
1876 if self.catalog.entry(name)? == Entry::Table {
1877 return Ok(self.catalog.table(name)?.columns().to_vec());
1878 }
1879 let (_, scope) = self.bind_view(ast, name, NONE, ast::Slice::default())?;
1880 Ok(scope.fields())
1881 }
1882
1883 fn describing(&mut self, field: &Field) -> Vec<ExprRef> {
1885 let written = [
1886 field.name.clone(),
1887 field.ty.to_string(),
1888 if field.not_null { "NO" } else { "YES" }.to_owned(),
1889 ];
1890 let mut items: Vec<ExprRef> =
1891 written.into_iter().map(|text| self.plan.add_constant(Value::Varchar(text))).collect();
1892 for _ in 0..3 {
1893 let empty = self.plan.add_constant(Value::Null);
1894 items.push(self.cast_to(empty, &LogicalType::Varchar));
1895 }
1896 items
1897 }
1898
1899 fn table_info(&mut self, at: usize, field: &Field) -> Vec<ExprRef> {
1905 let cid = self.plan.add_constant(Value::Integer(i32::try_from(at).unwrap_or(i32::MAX)));
1906 let name = self.plan.add_constant(Value::Varchar(field.name.clone()));
1907 let ty = self.plan.add_constant(Value::Varchar(field.ty.to_string()));
1908 let not_null = self.plan.add_constant(Value::Boolean(field.not_null));
1909 let default = self.plan.add_constant(Value::Null);
1910 let default = self.cast_to(default, &LogicalType::Varchar);
1911 let key = self.plan.add_constant(Value::Boolean(false));
1912 vec![cid, name, ty, not_null, default, key]
1913 }
1914
1915 fn named_argument(
1929 &mut self,
1930 function: TableFunction,
1931 name: &str,
1932 expr: ExprRef,
1933 ) -> Result<(&'static str, Value)> {
1934 let known = function
1935 .parameters()
1936 .iter()
1937 .find(|(parameter, _)| parameter.eq_ignore_ascii_case(name));
1938 let Some((parameter, wanted)) = known else {
1939 let candidates: Vec<String> = function
1940 .parameters()
1941 .iter()
1942 .map(|(parameter, ty)| format!(" {parameter} {ty}"))
1943 .collect();
1944 return Err(Error::binder(format!(
1945 "Invalid named parameter \"{name}\" for function {}\nCandidates:\n{}\n",
1946 function.name(),
1947 candidates.join("\n")
1948 )));
1949 };
1950 let Expr::Constant(reference) = *self.plan.expr(expr) else {
1951 return Err(Error::not_implemented(format!(
1952 "the named parameter {parameter} with a value that is not a constant"
1953 )));
1954 };
1955 let value = self.plan.value(reference).clone();
1956 if value == Value::Null {
1957 return Err(Error::binder(null_parameter(function, parameter)));
1958 }
1959 let given = self.plan.expr_type(expr).clone();
1960 if given != *wanted {
1961 return Err(Error::not_implemented(format!(
1962 "the named parameter {parameter} given a {given} where a {wanted} was wanted"
1963 )));
1964 }
1965 Ok((parameter, value))
1966 }
1967
1968 fn bind_replacement_scan(
1979 &mut self,
1980 ast: &Ast,
1981 parts: &[&str],
1982 alias: ast::StrRef,
1983 columns: ast::Slice,
1984 missing: Error,
1985 ) -> Result<(NodeRef, Scope)> {
1986 let [path] = parts else { return Err(missing) };
1987 let path = *path;
1988 let extension = path.rsplit_once('.').map(|(_, after)| after).unwrap_or_default();
1989 let Some(function) = Self::reader_for(extension) else {
1990 if is_file(path) {
1991 return Err(Error::binder(format!(
1996 "No extension found that is capable of reading the file \"{path}\"\n* If this \
1997 file is a supported file format you can explicitly use the reader functions, \
1998 such as read_csv, read_json or read_parquet"
1999 )));
2000 }
2001 return Err(missing);
2002 };
2003 let paths = files(path)?;
2008 let read = match function {
2009 TableFunction::ReadParquet => {
2010 let footers = parquet_footers(&paths)?;
2011 Read {
2012 fields: footers.fields,
2013 rows: footers.rows,
2014 distincts: footers.distincts,
2015 zones: footers.zones,
2016 }
2017 }
2018 _ => Read::uncounted(csv_fields(&paths, Given::default())?),
2019 };
2020 let label = if alias == NONE {
2026 if is_pattern(path) {
2027 path.to_string()
2028 } else {
2029 let file = path.rsplit_once('/').map_or(path, |(_, file)| file);
2030 file.rsplit_once('.').map_or(file, |(stem, _)| stem).to_string()
2031 }
2032 } else {
2033 ast.string(alias).to_string()
2034 };
2035 let arguments: Vec<ExprRef> = paths.iter().map(|path| self.path_constant(path)).collect();
2036 let names: Vec<&str> = ast.name(columns).collect();
2037 self.table_function_source(function, &arguments, &[], read, &label, &names)
2038 }
2039
2040 fn path_constant(&mut self, path: &str) -> ExprRef {
2042 let value = self.plan.add_value(Value::Varchar(path.to_string()));
2043 self.plan.add_expr(Expr::Constant(value), LogicalType::Varchar)
2044 }
2045
2046 fn reader_for(extension: &str) -> Option<TableFunction> {
2053 if extension.eq_ignore_ascii_case("parquet") {
2054 return Some(TableFunction::ReadParquet);
2055 }
2056 if extension.eq_ignore_ascii_case("csv") || extension.eq_ignore_ascii_case("tsv") {
2057 return Some(TableFunction::ReadCsv);
2058 }
2059 None
2060 }
2061
2062 fn table_function_source(
2072 &mut self,
2073 function: TableFunction,
2074 args: &[ExprRef],
2075 written: &[(&'static str, Value, ExprRef)],
2076 read: Read,
2077 label: &str,
2078 names: &[&str],
2079 ) -> Result<(NodeRef, Scope)> {
2080 let Read { fields, rows, distincts, zones } = read;
2081 let index = self.fresh_index();
2082 if rows.is_known() {
2087 self.plan.measure(index, rows);
2088 }
2089 for (column, distinct) in distincts {
2090 self.plan.measure_distinct(index, &column, distinct);
2091 }
2092 if let Some(zones) = zones {
2093 self.plan.set_zones(index, zones);
2094 }
2095 let mut scope = Scope::empty();
2096 for (at, field) in fields.iter().enumerate() {
2097 scope.push(Visible {
2098 table: label.to_string(),
2099 name: field.name.clone(),
2100 binding: ColumnBinding::new(index, at as u32),
2101 ty: field.ty.clone(),
2102 not_null: false,
2105 });
2106 }
2107 if !names.is_empty() {
2108 scope.rename(names, label)?;
2109 }
2110 let function = self.plan.intern(function.name());
2111 let args = self.plan.add_expr_list(args);
2112 let named: Vec<u32> =
2113 written.iter().map(|(parameter, _, _)| self.plan.intern(parameter)).collect();
2114 let settings: Vec<ExprRef> = written.iter().map(|(_, _, expr)| *expr).collect();
2115 let options = self.plan.add_name_list(&named);
2116 let settings = self.plan.add_expr_list(&settings);
2117 let columns = self.plan.add_fields(&fields);
2118 let node = self.add_node(Node::TableFunction {
2119 index,
2120 function,
2121 args,
2122 options,
2123 settings,
2124 columns,
2125 });
2126 Ok((node, scope))
2127 }
2128
2129 fn file_paths(&self, expr: ExprRef, name: &str) -> Result<Vec<String>> {
2136 let mut paths = Vec::new();
2137 for pattern in self.file_patterns(expr, name)? {
2138 paths.extend(files(&pattern)?);
2139 }
2140 Ok(paths)
2141 }
2142
2143 fn file_patterns(&self, expr: ExprRef, name: &str) -> Result<Vec<String>> {
2155 let Expr::Constant(reference) = *self.plan.expr(expr) else {
2156 return Err(Error::not_implemented(
2157 "a table function file name that is not a constant",
2158 ));
2159 };
2160 match self.plan.value(reference) {
2161 Value::Varchar(path) => Ok(vec![path.clone()]),
2162 Value::Null => Err(Error::parser(format!("{name} cannot take NULL list as parameter"))),
2164 Value::List { values, .. } => values
2165 .iter()
2166 .map(|value| match value {
2167 Value::Varchar(path) => Ok(path.clone()),
2168 _ => Err(Error::parser(format!(
2169 "{name} reader cannot take NULL input as parameter"
2170 ))),
2171 })
2172 .collect(),
2173 other => {
2174 Err(Error::internal(format!("a file name bound as VARCHAR arrived as {other}")))
2175 }
2176 }
2177 }
2178
2179 #[allow(clippy::too_many_arguments)]
2180 fn bind_join(
2181 &mut self,
2182 ast: &Ast,
2183 left: ast::SourceRef,
2184 right: ast::SourceRef,
2185 kind: ast::JoinKind,
2186 natural: bool,
2187 on: ast::ExprRef,
2188 using: ast::Slice,
2189 ) -> Result<(NodeRef, Scope)> {
2190 let (left_node, left_scope) = self.bind_source(ast, left)?;
2191 let (right_node, right_scope, correlated) = self.bind_lateral(ast, right, &left_scope)?;
2192 if !correlated.is_empty()
2196 && !matches!(kind, ast::JoinKind::Inner | ast::JoinKind::Cross | ast::JoinKind::Left)
2197 {
2198 return Err(Error::binder(
2199 "The combining JOIN type must be INNER or LEFT for a LATERAL reference",
2200 ));
2201 }
2202 let split = left_scope.len();
2203 let mut scope = left_scope.concat(right_scope);
2204
2205 let merged: Vec<String> = if natural {
2208 let mut names = Vec::new();
2209 for (at, column) in scope.columns.iter().enumerate().take(split) {
2210 if scope.columns[split..].iter().any(|right| same_name(&right.name, &column.name))
2211 && !names.iter().any(|held: &String| same_name(held, &column.name))
2212 {
2213 let _ = at;
2214 names.push(column.name.clone());
2215 }
2216 }
2217 names
2218 } else {
2219 let mut names: Vec<String> = Vec::new();
2225 for name in ast.name(using) {
2226 if !names.iter().any(|held| same_name(held, name)) {
2227 names.push(name.to_string());
2228 }
2229 }
2230 names
2231 };
2232
2233 let mut conditions = Vec::new();
2234 let mut dropped = Vec::new();
2235 for name in &merged {
2236 let left_at = scope.columns[..split]
2237 .iter()
2238 .position(|column| same_name(&column.name, name))
2239 .ok_or_else(|| {
2240 Error::binder(format!(
2241 "column \"{name}\" specified in USING clause does not exist in left table"
2242 ))
2243 })?;
2244 let right_at = scope.columns[split..]
2245 .iter()
2246 .position(|column| same_name(&column.name, name))
2247 .map(|at| at + split)
2248 .ok_or_else(|| {
2249 Error::binder(format!(
2250 "column \"{name}\" specified in USING clause does not exist in right table"
2251 ))
2252 })?;
2253 let left_column = &scope.columns[left_at];
2254 let (left_binding, left_type) = (left_column.binding, left_column.ty.clone());
2255 let right_column = &scope.columns[right_at];
2256 let (right_binding, right_type) = (right_column.binding, right_column.ty.clone());
2257 let left_expr = self.plan.add_expr(Expr::Column(left_binding), left_type);
2258 let right_expr = self.plan.add_expr(Expr::Column(right_binding), right_type);
2259 conditions.push(self.compare(rudb_plan::CompareOp::Equal, left_expr, right_expr)?);
2260 dropped.push(right_at);
2261 }
2262 dropped.sort_unstable();
2265 for at in dropped.into_iter().rev() {
2266 scope.remove(at);
2267 }
2268
2269 if on != NONE {
2270 if !merged.is_empty() {
2271 return Err(Error::binder("a join cannot have both ON and USING"));
2272 }
2273 self.clause = "JOIN condition";
2274 let predicate = self.bind_expr(ast, on, &scope)?;
2275 conditions.push(self.as_boolean(predicate, "JOIN")?);
2276 }
2277
2278 if kind == ast::JoinKind::Cross && !conditions.is_empty() {
2279 return Err(Error::binder("a CROSS JOIN cannot have a condition"));
2280 }
2281 if correlated.is_empty()
2285 && conditions.is_empty()
2286 && matches!(kind, ast::JoinKind::Cross | ast::JoinKind::Inner)
2287 {
2288 let node = self.add_node(Node::CrossProduct { left: left_node, right: right_node });
2289 return Ok((node, scope));
2290 }
2291 if matches!(kind, ast::JoinKind::Semi | ast::JoinKind::Anti) {
2300 scope.truncate(split);
2301 }
2302 let kind = match kind {
2303 ast::JoinKind::Inner | ast::JoinKind::Cross => JoinKind::Inner,
2304 ast::JoinKind::Left => JoinKind::Left,
2305 ast::JoinKind::Right => JoinKind::Right,
2306 ast::JoinKind::Full => JoinKind::Full,
2307 ast::JoinKind::Semi => JoinKind::Semi,
2308 ast::JoinKind::Anti => JoinKind::Anti,
2309 ast::JoinKind::Positional => JoinKind::Positional,
2310 };
2311 let conditions = self.plan.add_expr_list(&conditions);
2312 let node = if correlated.is_empty() {
2313 self.add_node(Node::Join {
2314 left: left_node,
2315 right: right_node,
2316 kind,
2317 conditions,
2318 build: BuildSide::default(),
2319 })
2320 } else {
2321 self.add_node(Node::DependentJoin {
2322 left: left_node,
2323 right: right_node,
2324 kind,
2325 conditions,
2326 })
2327 };
2328 Ok((node, scope))
2329 }
2330
2331 fn bind_filter(
2339 &mut self,
2340 ast: &Ast,
2341 filter: ast::ExprRef,
2342 scope: &Scope,
2343 ) -> Result<Option<ExprRef>> {
2344 if filter == NONE {
2345 return Ok(None);
2346 }
2347 let bound = self.bind_expr(ast, filter, scope)?;
2348 Ok(Some(self.checked_cast_to(bound, &LogicalType::Boolean, false)?))
2349 }
2350
2351 pub(crate) fn bind_aggregate(
2353 &mut self,
2354 ast: &Ast,
2355 name: &str,
2356 args: &[ast::ExprRef],
2357 distinct: bool,
2358 filter: ast::ExprRef,
2359 scope: &Scope,
2360 ) -> Result<ExprRef> {
2361 if self.in_filter {
2362 return Err(Error::binder("aggregate functions are not allowed in FILTER"));
2363 }
2364 if self.in_aggregate {
2365 return Err(Error::binder(format!(
2366 "aggregate function calls cannot be nested, and {name}() is inside one"
2367 )));
2368 }
2369 if self.aggregation.is_none() {
2370 return Err(Error::binder(format!(
2371 "aggregate function calls cannot be used in the {}",
2372 self.clause
2373 )));
2374 }
2375 self.in_aggregate = true;
2380 self.in_filter = true;
2381 let filter = self.bind_filter(ast, filter, scope);
2382 self.in_filter = false;
2383 self.in_aggregate = false;
2384 let filter = filter?;
2385
2386 self.in_aggregate = true;
2387 let mut bound = Vec::with_capacity(args.len());
2388 let mut failure = None;
2389 for &arg in args {
2390 match self.bind_expr(ast, arg, scope) {
2391 Ok(expr) => bound.push(expr),
2392 Err(error) => {
2393 failure = Some(error);
2394 break;
2395 }
2396 }
2397 }
2398 self.in_aggregate = false;
2399 if let Some(error) = failure {
2400 return Err(error);
2401 }
2402
2403 let types: Vec<LogicalType> =
2404 bound.iter().map(|&arg| self.plan.expr_type(arg).clone()).collect();
2405 let resolved = resolve(name, &types)?;
2406 let mut cast = Vec::with_capacity(bound.len());
2407 for (arg, wanted) in bound.iter().zip(&resolved.arguments) {
2408 cast.push(self.checked_cast_to(*arg, wanted, false)?);
2409 }
2410 let args = self.plan.add_expr_list(&cast);
2411 let name = self.plan.intern(resolved.name);
2412 let ty = resolved.returns;
2413 let call = self.plan.add_expr(Expr::Aggregate { name, args, distinct, filter }, ty.clone());
2414
2415 let existing = self.aggregation.as_ref().map(|held| held.aggregates.clone());
2418 let existing = existing.unwrap_or_default();
2419 let at = match existing.iter().position(|&held| self.same_expr(held, call)) {
2420 Some(at) => at,
2421 None => {
2422 let aggregation = self.aggregation.as_mut().expect("checked above");
2423 aggregation.aggregates.push(call);
2424 aggregation.aggregates.len() - 1
2425 }
2426 };
2427 let aggregation = self.aggregation.as_ref().expect("checked above");
2428 let (index, groups) = (aggregation.index, aggregation.groups.len());
2429 Ok(self.column(index, groups + at, ty))
2430 }
2431
2432 pub(crate) fn bind_window(
2440 &mut self,
2441 ast: &Ast,
2442 written: &WindowCall<'_>,
2443 scope: &Scope,
2444 ) -> Result<ExprRef> {
2445 let WindowCall { name, args, distinct, filter, ignore_nulls, spec } = *written;
2446 if self.in_aggregate {
2447 return Err(Error::binder(
2448 "aggregate function calls cannot contain window function calls",
2449 ));
2450 }
2451 if self.in_window {
2452 return Err(Error::binder("window function calls cannot be nested"));
2453 }
2454 let clause = if self.clause == "JOIN condition" { "WHERE clause" } else { self.clause };
2458 if clause != "SELECT clause" && clause != "ORDER BY clause" {
2459 return Err(Error::binder(format!("{clause} cannot contain window functions!")));
2460 }
2461
2462 let starred = args.iter().any(|&arg| {
2466 matches!(ast.expr(arg), ast::Expr::Star { qualifier, replacements }
2467 if qualifier.is_empty() && replacements.is_empty())
2468 });
2469 let (name, args): (&str, &[ast::ExprRef]) = if starred {
2470 if !same_name(name, "count") || args.len() != 1 {
2471 return Err(Error::binder(format!("* is not allowed in {name}()")));
2472 }
2473 ("count_star", &[])
2474 } else if same_name(name, "count") && args.is_empty() {
2475 ("count_star", &[])
2478 } else {
2479 (name, args)
2480 };
2481
2482 let held = ast.window(spec);
2483 self.in_window = true;
2484 let parts = self.window_parts(ast, args, held, scope);
2485 let filter = if parts.is_ok() { self.bind_filter(ast, filter, scope) } else { Ok(None) };
2490 self.in_window = false;
2491 let parts = parts?;
2492 let filter = filter?;
2493 let offsets = [parts.frame.start, parts.frame.end]
2496 .iter()
2497 .any(|end| matches!(end, WindowBound::Preceding(_) | WindowBound::Following(_)));
2498 if parts.frame.unit == WindowUnit::Range && offsets && parts.order.len() != 1 {
2499 return Err(Error::binder("RANGE frames must have only one ORDER BY expression"));
2500 }
2501
2502 let types: Vec<LogicalType> =
2503 parts.args.iter().map(|&arg| self.plan.expr_type(arg).clone()).collect();
2504 let resolved = window_signature(name, &types)?;
2505 if resolved.name == "fill" {
2508 let keys: Vec<LogicalType> =
2509 parts.order.iter().map(|key| self.plan.expr_type(key.expr).clone()).collect();
2510 refuse_fill(&types[0], &keys, distinct, ignore_nulls)?;
2511 }
2512 if distinct && kind_of(resolved.name) == Some(FunctionKind::Window) {
2516 return Err(Error::binder(format!(
2517 "DISTINCT is not implemented for the window function \"\"{name}\"\""
2518 )));
2519 }
2520 if filter.is_some() && kind_of(resolved.name) == Some(FunctionKind::Window) {
2523 return Err(Error::binder(format!(
2524 "FILTER is not implemented for the window function \"\"{name}\"\""
2525 )));
2526 }
2527 let mut cast = Vec::with_capacity(parts.args.len());
2528 for (arg, wanted) in parts.args.iter().zip(&resolved.arguments) {
2529 cast.push(self.checked_cast_to(*arg, wanted, false)?);
2530 }
2531 let args = self.plan.add_expr_list(&cast);
2532 let name = self.plan.intern(resolved.name);
2533 let ty = resolved.returns;
2534 let call = self
2535 .plan
2536 .add_expr(Expr::Window { name, args, distinct, filter, ignore_nulls }, ty.clone());
2537
2538 let at = self.window_run(parts.partition, parts.order, parts.frame, call);
2539 let index = self.windows.last().expect("the run was just filed").index;
2540 Ok(self.column(index, at, ty))
2541 }
2542
2543 fn window_run(
2550 &mut self,
2551 partition: Vec<ExprRef>,
2552 order: Vec<SortKey>,
2553 frame: WindowFrame,
2554 call: ExprRef,
2555 ) -> usize {
2556 let matches = self.windows.last().is_some_and(|run| {
2557 run.frame == frame
2558 && run.partition.len() == partition.len()
2559 && run.order.len() == order.len()
2560 && run.partition.iter().zip(&partition).all(|(&l, &r)| self.same_expr(l, r))
2561 && run.order.iter().zip(&order).all(|(l, r)| {
2562 l.descending == r.descending
2563 && l.nulls_first == r.nulls_first
2564 && self.same_expr(l.expr, r.expr)
2565 })
2566 });
2567 if !matches {
2568 let index = self.fresh_index();
2569 self.windows.push(WindowRun { index, partition, order, frame, calls: Vec::new() });
2570 }
2571 let calls = self.windows.last().expect("a run is open").calls.clone();
2574 if let Some(at) = calls.iter().position(|&held| self.same_expr(held, call)) {
2575 return at;
2576 }
2577 let run = self.windows.last_mut().expect("a run is open");
2578 run.calls.push(call);
2579 run.calls.len() - 1
2580 }
2581
2582 fn window_parts(
2588 &mut self,
2589 ast: &Ast,
2590 args: &[ast::ExprRef],
2591 held: ast::WindowSpec,
2592 scope: &Scope,
2593 ) -> Result<WindowParts> {
2594 let mut bound = Vec::with_capacity(args.len());
2595 for &arg in args {
2596 let expr = self.bind_expr(ast, arg, scope)?;
2597 bound.push(self.over_aggregate(expr, scope)?);
2598 }
2599 let mut partition = Vec::new();
2600 for &key in ast.expr_list(held.partition) {
2601 let expr = self.bind_expr(ast, key, scope)?;
2602 partition.push(self.over_aggregate(expr, scope)?);
2603 }
2604 let mut order = Vec::new();
2605 for item in ast.order_list(held.order).to_vec() {
2606 let expr = self.bind_expr(ast, item.expr, scope)?;
2607 let expr = self.over_aggregate(expr, scope)?;
2608 order.push(self.sort_key(expr, item));
2609 }
2610 let frame = WindowFrame {
2611 unit: match held.unit {
2612 ast::WindowUnit::Rows => WindowUnit::Rows,
2613 ast::WindowUnit::Range => WindowUnit::Range,
2614 ast::WindowUnit::Groups => WindowUnit::Groups,
2615 },
2616 start: self.window_bound(ast, held.start, scope)?,
2617 end: self.window_bound(ast, held.end, scope)?,
2618 exclude: match held.exclude {
2619 ast::WindowExclude::NoOthers => WindowExclude::NoOthers,
2620 ast::WindowExclude::CurrentRow => WindowExclude::CurrentRow,
2621 ast::WindowExclude::Group => WindowExclude::Group,
2622 ast::WindowExclude::Ties => WindowExclude::Ties,
2623 },
2624 };
2625 Ok(WindowParts { args: bound, partition, order, frame })
2626 }
2627
2628 fn window_bound(
2630 &mut self,
2631 ast: &Ast,
2632 bound: ast::WindowBound,
2633 scope: &Scope,
2634 ) -> Result<WindowBound> {
2635 let offset = |binder: &mut Self, written| {
2636 let expr = binder.bind_expr(ast, written, scope)?;
2637 binder.over_aggregate(expr, scope)
2638 };
2639 Ok(match bound {
2640 ast::WindowBound::UnboundedPreceding => WindowBound::UnboundedPreceding,
2641 ast::WindowBound::CurrentRow => WindowBound::CurrentRow,
2642 ast::WindowBound::UnboundedFollowing => WindowBound::UnboundedFollowing,
2643 ast::WindowBound::Preceding(written) => WindowBound::Preceding(offset(self, written)?),
2644 ast::WindowBound::Following(written) => WindowBound::Following(offset(self, written)?),
2645 })
2646 }
2647
2648 fn is_window_output(&self, binding: ColumnBinding) -> bool {
2650 self.windows.iter().any(|run| run.index == binding.table)
2651 }
2652
2653 pub(crate) fn over_aggregate(&mut self, expr: ExprRef, scope: &Scope) -> Result<ExprRef> {
2659 let Some(aggregation) = self.aggregation.as_ref() else {
2660 return Ok(expr);
2661 };
2662 let index = aggregation.index;
2663 let groups = aggregation.groups.clone();
2664 for (at, group) in groups.iter().enumerate() {
2665 if self.same_expr(expr, *group) {
2666 let ty = self.plan.expr_type(*group).clone();
2667 return Ok(self.column(index, at, ty));
2668 }
2669 }
2670 let ty = self.plan.expr_type(expr).clone();
2671 match self.plan.expr(expr).clone() {
2672 Expr::Column(binding) if binding.table == index => Ok(expr),
2673 Expr::Column(binding) if self.is_window_output(binding) => Ok(expr),
2678 Expr::Column(binding) if self.joined_above.contains(&binding.table) => Ok(expr),
2683 Expr::Column(binding) => {
2684 let name =
2685 scope.columns.iter().find(|column| column.binding == binding).map_or_else(
2686 || "a column".to_string(),
2687 |column| format!("\"{}\"", column.name),
2688 );
2689 Err(Error::binder(format!(
2690 "column {name} must appear in the GROUP BY clause or must be part of an aggregate function"
2691 )))
2692 }
2693 Expr::Constant(_) | Expr::Aggregate { .. } | Expr::Window { .. } => Ok(expr),
2694 Expr::Cast { input, try_cast } => {
2695 let input = self.over_aggregate(input, scope)?;
2696 Ok(self.plan.add_expr(Expr::Cast { input, try_cast }, ty))
2697 }
2698 Expr::Compare { op, left, right } => {
2699 let left = self.over_aggregate(left, scope)?;
2700 let right = self.over_aggregate(right, scope)?;
2701 Ok(self.plan.add_expr(Expr::Compare { op, left, right }, ty))
2702 }
2703 Expr::Conjunction { op, children } => {
2704 let written = self.plan.expr_list(children).to_vec();
2705 let mut rewritten = Vec::with_capacity(written.len());
2706 for child in written {
2707 rewritten.push(self.over_aggregate(child, scope)?);
2708 }
2709 let children = self.plan.add_expr_list(&rewritten);
2710 Ok(self.plan.add_expr(Expr::Conjunction { op, children }, ty))
2711 }
2712 Expr::Function { name, args } => {
2713 let written = self.plan.expr_list(args).to_vec();
2714 let mut rewritten = Vec::with_capacity(written.len());
2715 for arg in written {
2716 rewritten.push(self.over_aggregate(arg, scope)?);
2717 }
2718 let args = self.plan.add_expr_list(&rewritten);
2719 Ok(self.plan.add_expr(Expr::Function { name, args }, ty))
2720 }
2721 Expr::Case { arms, otherwise } => {
2722 let written = self.plan.arm_list(arms).to_vec();
2723 let mut rewritten = Vec::with_capacity(written.len());
2724 for arm in written {
2725 let when = self.over_aggregate(arm.when, scope)?;
2726 let then = self.over_aggregate(arm.then, scope)?;
2727 rewritten.push(rudb_plan::Arm { when, then });
2728 }
2729 let otherwise = match otherwise {
2730 Some(expr) => Some(self.over_aggregate(expr, scope)?),
2731 None => None,
2732 };
2733 let arms = self.plan.add_arms(&rewritten);
2734 Ok(self.plan.add_expr(Expr::Case { arms, otherwise }, ty))
2735 }
2736 }
2737 }
2738
2739 pub(crate) fn same_expr(&self, left: ExprRef, right: ExprRef) -> bool {
2741 same_expr(&self.plan, left, right)
2742 }
2743}
2744
2745#[derive(Debug, Default)]
2755struct Options {
2756 binary_as_string: bool,
2759 all_varchar: bool,
2761 file_row_number: bool,
2766 given: Given,
2768}
2769
2770impl Options {
2771 fn of(written: &[(&'static str, Value, ExprRef)]) -> Result<Self> {
2778 let mut options = Self::default();
2779 for (parameter, value, _) in written {
2780 match (*parameter, value) {
2781 ("binary_as_string", Value::Boolean(on)) => options.binary_as_string = *on,
2782 ("all_varchar", Value::Boolean(on)) => options.all_varchar = *on,
2783 ("file_row_number", Value::Boolean(on)) => options.file_row_number = *on,
2784 _ => {}
2785 }
2786 }
2787 let named: Vec<(&str, Value)> =
2788 written.iter().map(|(parameter, value, _)| (*parameter, value.clone())).collect();
2789 options.given = csv_given(&named)?;
2790 Ok(options)
2791 }
2792}
2793
2794fn null_parameter(function: TableFunction, parameter: &str) -> String {
2803 match parameter {
2804 "header" => format!("\"{parameter}\" expects a non-null boolean value (e.g. TRUE or 1)"),
2805 "all_varchar" => format!("{} \"{parameter}\" cannot be NULL", function.name()),
2806 _ => format!("Cannot use NULL as argument to \"{parameter}\""),
2807 }
2808}
2809
2810fn missing_replacement(name: &str, input: &Scope) -> Error {
2815 Error::binder(format!(
2816 "Column \"{name}\" in REPLACE list not found in FROM clause{}",
2817 input.candidates()
2818 ))
2819}
2820
2821fn subtractable(ty: &LogicalType, ordering: bool) -> bool {
2830 if ty.is_numeric() {
2831 return true;
2832 }
2833 match ty {
2834 LogicalType::Date
2835 | LogicalType::Time
2836 | LogicalType::Timestamp
2837 | LogicalType::TimestampS
2838 | LogicalType::TimestampMs
2839 | LogicalType::TimestampNs
2840 | LogicalType::TimestampTz => true,
2841 LogicalType::TimeTz => ordering,
2842 _ => false,
2843 }
2844}
2845
2846fn refuse_fill(
2855 argument: &LogicalType,
2856 order: &[LogicalType],
2857 distinct: bool,
2858 ignore_nulls: bool,
2859) -> Result<()> {
2860 if !subtractable(argument, false) {
2861 return Err(Error::binder("FILL argument must support subtraction"));
2862 }
2863 let [key] = order else {
2864 return Err(Error::binder("FILL functions must have only one ORDER BY expression"));
2865 };
2866 if !subtractable(key, true) {
2867 return Err(Error::binder("FILL ordering must support subtraction"));
2868 }
2869 if distinct {
2870 return Err(Error::binder(
2871 "DISTINCT is not implemented for the window function \"\"fill\"\"",
2872 ));
2873 }
2874 if ignore_nulls {
2875 return Err(Error::binder(
2876 "RESPECT/IGNORE NULLS is not supported for the window function \"fill\"",
2877 ));
2878 }
2879 Ok(())
2880}
2881
2882fn window_signature(name: &str, types: &[LogicalType]) -> Result<Resolved> {
2889 match kind_of(name) {
2890 Some(FunctionKind::Aggregate | FunctionKind::Window) => resolve(name, types),
2891 Some(FunctionKind::Scalar) => {
2892 Err(Error::catalog(format!("{name} is not an aggregate function")))
2893 }
2894 None => Err(Error::catalog(format!("Aggregate Function with name {name} does not exist!"))),
2895 }
2896}
2897
2898fn same_expr(plan: &Plan, left: ExprRef, right: ExprRef) -> bool {
2900 if left == right {
2901 return true;
2902 }
2903 if plan.expr_type(left) != plan.expr_type(right) {
2904 return false;
2905 }
2906 let lists = |left, right| {
2907 let left: &[ExprRef] = plan.expr_list(left);
2908 let right: &[ExprRef] = plan.expr_list(right);
2909 left.len() == right.len()
2910 && left.iter().zip(right).all(|(&left, &right)| same_expr(plan, left, right))
2911 };
2912 match (plan.expr(left), plan.expr(right)) {
2913 (Expr::Column(left), Expr::Column(right)) => left == right,
2914 (Expr::Constant(left), Expr::Constant(right)) => plan.value(*left) == plan.value(*right),
2915 (
2916 Expr::Cast { input: left, try_cast: left_try },
2917 Expr::Cast { input: right, try_cast: right_try },
2918 ) => left_try == right_try && same_expr(plan, *left, *right),
2919 (
2920 Expr::Compare { op: left_op, left: left_a, right: left_b },
2921 Expr::Compare { op: right_op, left: right_a, right: right_b },
2922 ) => {
2923 left_op == right_op
2924 && same_expr(plan, *left_a, *right_a)
2925 && same_expr(plan, *left_b, *right_b)
2926 }
2927 (
2928 Expr::Conjunction { op: left_op, children: left_children },
2929 Expr::Conjunction { op: right_op, children: right_children },
2930 ) => left_op == right_op && lists(*left_children, *right_children),
2931 (
2932 Expr::Function { name: left_name, args: left_args },
2933 Expr::Function { name: right_name, args: right_args },
2934 ) => plan.string(*left_name) == plan.string(*right_name) && lists(*left_args, *right_args),
2935 (
2936 Expr::Aggregate {
2937 name: left_name,
2938 args: left_args,
2939 distinct: left_distinct,
2940 filter: left_filter,
2941 },
2942 Expr::Aggregate {
2943 name: right_name,
2944 args: right_args,
2945 distinct: right_distinct,
2946 filter: right_filter,
2947 },
2948 ) => {
2949 plan.string(*left_name) == plan.string(*right_name)
2950 && left_distinct == right_distinct
2951 && match (left_filter, right_filter) {
2952 (None, None) => true,
2953 (Some(left), Some(right)) => same_expr(plan, *left, *right),
2954 _ => false,
2955 }
2956 && lists(*left_args, *right_args)
2957 }
2958 (
2962 Expr::Window {
2963 name: left_name,
2964 args: left_args,
2965 distinct: left_distinct,
2966 filter: left_filter,
2967 ignore_nulls: left_nulls,
2968 },
2969 Expr::Window {
2970 name: right_name,
2971 args: right_args,
2972 distinct: right_distinct,
2973 filter: right_filter,
2974 ignore_nulls: right_nulls,
2975 },
2976 ) => {
2977 plan.string(*left_name) == plan.string(*right_name)
2978 && left_distinct == right_distinct
2979 && left_nulls == right_nulls
2980 && match (left_filter, right_filter) {
2981 (None, None) => true,
2982 (Some(left), Some(right)) => same_expr(plan, *left, *right),
2983 _ => false,
2984 }
2985 && lists(*left_args, *right_args)
2986 }
2987 (
2988 Expr::Case { arms: left_arms, otherwise: left_otherwise },
2989 Expr::Case { arms: right_arms, otherwise: right_otherwise },
2990 ) => {
2991 let left_arms = plan.arm_list(*left_arms);
2992 let right_arms = plan.arm_list(*right_arms);
2993 left_arms.len() == right_arms.len()
2994 && left_arms.iter().zip(right_arms).all(|(left, right)| {
2995 same_expr(plan, left.when, right.when) && same_expr(plan, left.then, right.then)
2996 })
2997 && match (left_otherwise, right_otherwise) {
2998 (None, None) => true,
2999 (Some(left), Some(right)) => same_expr(plan, *left, *right),
3000 _ => false,
3001 }
3002 }
3003 _ => false,
3004 }
3005}