Skip to content

Commit d1308f0

Browse files
authored
fix: order by expr rewrite fix (#14486)
* fix: rewrite order by on compound expr * fmt * revert transform * test fix
1 parent 5e1e693 commit d1308f0

File tree

3 files changed

+43
-3
lines changed

3 files changed

+43
-3
lines changed

datafusion/expr/src/expr_rewriter/order_by.rs

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,9 @@ use crate::expr::Alias;
2121
use crate::expr_rewriter::normalize_col;
2222
use crate::{expr::Sort, Cast, Expr, LogicalPlan, TryCast};
2323

24-
use datafusion_common::tree_node::{Transformed, TransformedResult, TreeNode};
24+
use datafusion_common::tree_node::{
25+
Transformed, TransformedResult, TreeNode, TreeNodeRecursion,
26+
};
2527
use datafusion_common::{Column, Result};
2628

2729
/// Rewrite sort on aggregate expressions to sort on the column of aggregate output
@@ -101,8 +103,18 @@ fn rewrite_in_terms_of_projection(
101103
let search_col = Expr::Column(Column::new_unqualified(name));
102104

103105
// look for the column named the same as this expr
104-
if let Some(found) = proj_exprs.iter().find(|a| expr_match(&search_col, a)) {
105-
let found = found.clone();
106+
let mut found = None;
107+
for proj_expr in &proj_exprs {
108+
proj_expr.apply(|e| {
109+
if expr_match(&search_col, e) {
110+
found = Some(e.clone());
111+
return Ok(TreeNodeRecursion::Stop);
112+
}
113+
Ok(TreeNodeRecursion::Continue)
114+
})?;
115+
}
116+
117+
if let Some(found) = found {
106118
return Ok(Transformed::yes(match normalized_expr {
107119
Expr::Cast(Cast { expr: _, data_type }) => Expr::Cast(Cast {
108120
expr: Box::new(found),

datafusion/sql/tests/sql_integration.rs

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2511,6 +2511,21 @@ fn select_groupby_orderby() {
25112511
FROM person GROUP BY person.birth_date ORDER BY birth_date;
25122512
"#;
25132513
quick_test(sql, expected);
2514+
2515+
// Use columnized `avg(age)` in the order by
2516+
let sql = r#"SELECT
2517+
avg(age) + avg(age),
2518+
date_trunc('month', person.birth_date) AS "birth_date"
2519+
FROM person GROUP BY person.birth_date ORDER BY avg(age) + avg(age);
2520+
"#;
2521+
2522+
let expected =
2523+
"Sort: avg(person.age) + avg(person.age) ASC NULLS LAST\
2524+
\n Projection: avg(person.age) + avg(person.age), date_trunc(Utf8(\"month\"), person.birth_date) AS birth_date\
2525+
\n Aggregate: groupBy=[[person.birth_date]], aggr=[[avg(person.age)]]\
2526+
\n TableScan: person";
2527+
2528+
quick_test(sql, expected);
25142529
}
25152530

25162531
fn logical_plan(sql: &str) -> Result<LogicalPlan> {

datafusion/sqllogictest/test_files/order.slt

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -384,6 +384,19 @@ ORDER BY time;
384384
2 2022-01-01T01:00:00
385385
3 2022-01-02T00:00:00
386386

387+
# Tests for https://github.com/apache/datafusion/issues/14459
388+
query PI
389+
select
390+
date_trunc('minute',time) AS "time",
391+
sum(value) + sum(value)
392+
FROM t
393+
GROUP BY time
394+
ORDER BY sum(value) + sum(value);
395+
----
396+
2022-01-01T00:00:00 2
397+
2022-01-01T01:00:00 4
398+
2022-01-02T00:00:00 6
399+
387400
## SORT BY is not supported
388401
statement error DataFusion error: This feature is not implemented: SORT BY
389402
select * from t SORT BY time;

0 commit comments

Comments
 (0)