Skip to content

Commit 66805b1

Browse files
author
Shiv Bhatia
committed
Same for TableScan
1 parent c07eb8a commit 66805b1

File tree

1 file changed

+33
-0
lines changed

1 file changed

+33
-0
lines changed

datafusion/optimizer/src/push_down_filter.rs

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1140,6 +1140,16 @@ impl OptimizerRule for PushDownFilter {
11401140
}
11411141
LogicalPlan::Join(join) => push_down_join(join, Some(&filter.predicate)),
11421142
LogicalPlan::TableScan(scan) => {
1143+
// If the scan has a fetch (limit), pushing filters into it
1144+
// would change semantics: the limit should apply before the
1145+
// filter, not after.
1146+
if scan.fetch.is_some() {
1147+
let plan = LogicalPlan::Filter(Filter::try_new(
1148+
filter.predicate,
1149+
Arc::new(LogicalPlan::TableScan(scan)),
1150+
)?);
1151+
return Ok(Transformed::no(plan));
1152+
}
11431153
let filter_predicates = split_conjunction(&filter.predicate);
11441154

11451155
let (volatile_filters, non_volatile_filters): (Vec<&Expr>, Vec<&Expr>) =
@@ -4326,6 +4336,29 @@ mod tests {
43264336
)
43274337
}
43284338

4339+
#[test]
4340+
fn filter_not_pushed_down_through_table_scan_with_fetch() -> Result<()> {
4341+
let scan = test_table_scan()?;
4342+
let scan_with_fetch = match scan {
4343+
LogicalPlan::TableScan(scan) => LogicalPlan::TableScan(TableScan {
4344+
fetch: Some(10),
4345+
..scan
4346+
}),
4347+
_ => unreachable!(),
4348+
};
4349+
let plan = LogicalPlanBuilder::from(scan_with_fetch)
4350+
.filter(col("a").gt(lit(10i64)))?
4351+
.build()?;
4352+
// Filter must NOT be pushed into the table scan when it has a fetch (limit)
4353+
assert_optimized_plan_equal!(
4354+
plan,
4355+
@r"
4356+
Filter: test.a > Int64(10)
4357+
TableScan: test, fetch=10
4358+
"
4359+
)
4360+
}
4361+
43294362
#[test]
43304363
fn filter_push_down_through_sort_without_fetch() -> Result<()> {
43314364
let table_scan = test_table_scan()?;

0 commit comments

Comments
 (0)