Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add join type for logical plan display #1674

Merged
merged 1 commit into from
Jan 27, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion datafusion/src/logical_plan/builder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1150,7 +1150,7 @@ mod tests {

// id column should only show up once in projection
let expected = "Projection: #t1.id, #t1.first_name, #t1.last_name, #t1.state, #t1.salary, #t2.first_name, #t2.last_name, #t2.state, #t2.salary\
\n Join: Using #t1.id = #t2.id\
\n Inner Join: Using #t1.id = #t2.id\
\n TableScan: t1 projection=None\
\n TableScan: t2 projection=None";

Expand Down
25 changes: 23 additions & 2 deletions datafusion/src/logical_plan/plan.rs
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ use crate::error::DataFusionError;
use crate::logical_plan::dfschema::DFSchemaRef;
use crate::sql::parser::FileType;
use arrow::datatypes::{DataType, Field, Schema, SchemaRef};
use std::fmt::Formatter;
use std::{
collections::HashSet,
fmt::{self, Display},
Expand All @@ -48,6 +49,20 @@ pub enum JoinType {
Anti,
}

impl Display for JoinType {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

fn fmt(&self, f: &mut Formatter) -> fmt::Result {
let join_type = match self {
JoinType::Inner => "Inner",
JoinType::Left => "Left",
JoinType::Right => "Right",
JoinType::Full => "Full",
JoinType::Semi => "Semi",
JoinType::Anti => "Anti",
};
write!(f, "{}", join_type)
}
}

/// Join constraint
#[derive(Debug, Clone, Copy)]
pub enum JoinConstraint {
Expand Down Expand Up @@ -934,16 +949,22 @@ impl LogicalPlan {
LogicalPlan::Join(Join {
on: ref keys,
join_constraint,
join_type,
..
}) => {
let join_expr: Vec<String> =
keys.iter().map(|(l, r)| format!("{} = {}", l, r)).collect();
match join_constraint {
JoinConstraint::On => {
write!(f, "Join: {}", join_expr.join(", "))
write!(f, "{} Join: {}", join_type, join_expr.join(", "))
}
JoinConstraint::Using => {
write!(f, "Join: Using {}", join_expr.join(", "))
write!(
f,
"{} Join: Using {}",
join_type,
join_expr.join(", ")
)
}
}
}
Expand Down
30 changes: 15 additions & 15 deletions datafusion/src/optimizer/filter_push_down.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1014,15 +1014,15 @@ mod tests {
format!("{:?}", plan),
"\
Filter: #test.a <= Int64(1)\
\n Join: #test.a = #test2.a\
\n Inner Join: #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n TableScan: test2 projection=None"
);

// filter sent to side before the join
let expected = "\
Join: #test.a = #test2.a\
Inner Join: #test.a = #test2.a\
\n Filter: #test.a <= Int64(1)\
\n TableScan: test projection=None\
\n Projection: #test2.a\
Expand Down Expand Up @@ -1055,15 +1055,15 @@ mod tests {
format!("{:?}", plan),
"\
Filter: #test.a <= Int64(1)\
\n Join: Using #test.a = #test2.a\
\n Inner Join: Using #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n TableScan: test2 projection=None"
);

// filter sent to side before the join
let expected = "\
Join: Using #test.a = #test2.a\
Inner Join: Using #test.a = #test2.a\
\n Filter: #test.a <= Int64(1)\
\n TableScan: test projection=None\
\n Projection: #test2.a\
Expand Down Expand Up @@ -1099,7 +1099,7 @@ mod tests {
format!("{:?}", plan),
"\
Filter: #test.c <= #test2.b\
\n Join: #test.a = #test2.a\
\n Inner Join: #test.a = #test2.a\
\n Projection: #test.a, #test.c\
\n TableScan: test projection=None\
\n Projection: #test2.a, #test2.b\
Expand Down Expand Up @@ -1138,15 +1138,15 @@ mod tests {
format!("{:?}", plan),
"\
Filter: #test.b <= Int64(1)\
\n Join: #test.a = #test2.a\
\n Inner Join: #test.a = #test2.a\
\n Projection: #test.a, #test.b\
\n TableScan: test projection=None\
\n Projection: #test2.a, #test2.c\
\n TableScan: test2 projection=None"
);

let expected = "\
Join: #test.a = #test2.a\
Inner Join: #test.a = #test2.a\
\n Projection: #test.a, #test.b\
\n Filter: #test.b <= Int64(1)\
\n TableScan: test projection=None\
Expand Down Expand Up @@ -1180,7 +1180,7 @@ mod tests {
format!("{:?}", plan),
"\
Filter: #test2.a <= Int64(1)\
\n Join: Using #test.a = #test2.a\
\n Left Join: Using #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n TableScan: test2 projection=None"
Expand All @@ -1189,7 +1189,7 @@ mod tests {
// filter not duplicated nor pushed down - i.e. noop
let expected = "\
Filter: #test2.a <= Int64(1)\
\n Join: Using #test.a = #test2.a\
\n Left Join: Using #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n TableScan: test2 projection=None";
Expand Down Expand Up @@ -1221,7 +1221,7 @@ mod tests {
format!("{:?}", plan),
"\
Filter: #test.a <= Int64(1)\
\n Join: Using #test.a = #test2.a\
\n Right Join: Using #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n TableScan: test2 projection=None"
Expand All @@ -1230,7 +1230,7 @@ mod tests {
// filter not duplicated nor pushed down - i.e. noop
let expected = "\
Filter: #test.a <= Int64(1)\
\n Join: Using #test.a = #test2.a\
\n Right Join: Using #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n TableScan: test2 projection=None";
Expand Down Expand Up @@ -1262,15 +1262,15 @@ mod tests {
format!("{:?}", plan),
"\
Filter: #test.a <= Int64(1)\
\n Join: Using #test.a = #test2.a\
\n Left Join: Using #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n TableScan: test2 projection=None"
);

// filter sent to left side of the join, not the right
let expected = "\
Join: Using #test.a = #test2.a\
Left Join: Using #test.a = #test2.a\
\n Filter: #test.a <= Int64(1)\
\n TableScan: test projection=None\
\n Projection: #test2.a\
Expand Down Expand Up @@ -1303,15 +1303,15 @@ mod tests {
format!("{:?}", plan),
"\
Filter: #test2.a <= Int64(1)\
\n Join: Using #test.a = #test2.a\
\n Right Join: Using #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n TableScan: test2 projection=None"
);

// filter sent to right side of join, not duplicated to the left
let expected = "\
Join: Using #test.a = #test2.a\
Right Join: Using #test.a = #test2.a\
\n TableScan: test projection=None\
\n Projection: #test2.a\
\n Filter: #test2.a <= Int64(1)\
Expand Down
6 changes: 3 additions & 3 deletions datafusion/src/optimizer/projection_push_down.rs
Original file line number Diff line number Diff line change
Expand Up @@ -593,7 +593,7 @@ mod tests {

// make sure projections are pushed down to both table scans
let expected = "Projection: #test.a, #test.b, #test2.c1\
\n Join: #test.a = #test2.c1\
\n Left Join: #test.a = #test2.c1\
\n TableScan: test projection=Some([0, 1])\
\n TableScan: test2 projection=Some([0])";

Expand Down Expand Up @@ -634,7 +634,7 @@ mod tests {

// make sure projections are pushed down to both table scans
let expected = "Projection: #test.a, #test.b\
\n Join: #test.a = #test2.c1\
\n Left Join: #test.a = #test2.c1\
\n TableScan: test projection=Some([0, 1])\
\n TableScan: test2 projection=Some([0])";

Expand Down Expand Up @@ -673,7 +673,7 @@ mod tests {

// make sure projections are pushed down to table scan
let expected = "Projection: #test.a, #test.b\
\n Join: Using #test.a = #test2.a\
\n Left Join: Using #test.a = #test2.a\
\n TableScan: test projection=Some([0, 1])\
\n TableScan: test2 projection=Some([0])";

Expand Down
22 changes: 11 additions & 11 deletions datafusion/src/sql/planner.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3289,7 +3289,7 @@ mod tests {
JOIN orders \
ON id = customer_id";
let expected = "Projection: #person.id, #orders.order_id\
\n Join: #person.id = #orders.customer_id\
\n Inner Join: #person.id = #orders.customer_id\
\n TableScan: person projection=None\
\n TableScan: orders projection=None";
quick_test(sql, expected);
Expand All @@ -3303,7 +3303,7 @@ mod tests {
ON id = customer_id AND order_id > 1 ";
let expected = "Projection: #person.id, #orders.order_id\
\n Filter: #orders.order_id > Int64(1)\
\n Join: #person.id = #orders.customer_id\
\n Inner Join: #person.id = #orders.customer_id\
\n TableScan: person projection=None\
\n TableScan: orders projection=None";
quick_test(sql, expected);
Expand All @@ -3316,7 +3316,7 @@ mod tests {
LEFT JOIN orders \
ON id = customer_id AND order_id > 1";
let expected = "Projection: #person.id, #orders.order_id\
\n Join: #person.id = #orders.customer_id\
\n Left Join: #person.id = #orders.customer_id\
\n TableScan: person projection=None\
\n Filter: #orders.order_id > Int64(1)\
\n TableScan: orders projection=None";
Expand All @@ -3330,7 +3330,7 @@ mod tests {
RIGHT JOIN orders \
ON id = customer_id AND id > 1";
let expected = "Projection: #person.id, #orders.order_id\
\n Join: #person.id = #orders.customer_id\
\n Right Join: #person.id = #orders.customer_id\
\n Filter: #person.id > Int64(1)\
\n TableScan: person projection=None\
\n TableScan: orders projection=None";
Expand All @@ -3344,7 +3344,7 @@ mod tests {
JOIN orders \
ON person.id = orders.customer_id";
let expected = "Projection: #person.id, #orders.order_id\
\n Join: #person.id = #orders.customer_id\
\n Inner Join: #person.id = #orders.customer_id\
\n TableScan: person projection=None\
\n TableScan: orders projection=None";
quick_test(sql, expected);
Expand All @@ -3357,7 +3357,7 @@ mod tests {
JOIN person as person2 \
USING (id)";
let expected = "Projection: #person.first_name, #person.id\
\n Join: Using #person.id = #person2.id\
\n Inner Join: Using #person.id = #person2.id\
\n TableScan: person projection=None\
\n TableScan: person2 projection=None";
quick_test(sql, expected);
Expand All @@ -3370,7 +3370,7 @@ mod tests {
JOIN lineitem as lineitem2 \
USING (l_item_id)";
let expected = "Projection: #lineitem.l_item_id, #lineitem.l_description, #lineitem.price, #lineitem2.l_description, #lineitem2.price\
\n Join: Using #lineitem.l_item_id = #lineitem2.l_item_id\
\n Inner Join: Using #lineitem.l_item_id = #lineitem2.l_item_id\
\n TableScan: lineitem projection=None\
\n TableScan: lineitem2 projection=None";
quick_test(sql, expected);
Expand All @@ -3384,8 +3384,8 @@ mod tests {
JOIN lineitem ON o_item_id = l_item_id";
let expected =
"Projection: #person.id, #orders.order_id, #lineitem.l_description\
\n Join: #orders.o_item_id = #lineitem.l_item_id\
\n Join: #person.id = #orders.customer_id\
\n Inner Join: #orders.o_item_id = #lineitem.l_item_id\
\n Inner Join: #person.id = #orders.customer_id\
\n TableScan: person projection=None\
\n TableScan: orders projection=None\
\n TableScan: lineitem projection=None";
Expand Down Expand Up @@ -3918,8 +3918,8 @@ mod tests {
fn cross_join_to_inner_join() {
let sql = "select person.id from person, orders, lineitem where person.id = lineitem.l_item_id and orders.o_item_id = lineitem.l_description;";
let expected = "Projection: #person.id\
\n Join: #lineitem.l_description = #orders.o_item_id\
\n Join: #person.id = #lineitem.l_item_id\
\n Inner Join: #lineitem.l_description = #orders.o_item_id\
\n Inner Join: #person.id = #lineitem.l_item_id\
\n TableScan: person projection=None\
\n TableScan: lineitem projection=None\
\n TableScan: orders projection=None";
Expand Down
6 changes: 3 additions & 3 deletions datafusion/tests/sql/explain_analyze.rs
Original file line number Diff line number Diff line change
Expand Up @@ -616,9 +616,9 @@ order by
Sort: #revenue DESC NULLS FIRST\
\n Projection: #customer.c_custkey, #customer.c_name, #SUM(lineitem.l_extendedprice * Int64(1) - lineitem.l_discount) AS revenue, #customer.c_acctbal, #nation.n_name, #customer.c_address, #customer.c_phone, #customer.c_comment\
\n Aggregate: groupBy=[[#customer.c_custkey, #customer.c_name, #customer.c_acctbal, #customer.c_phone, #nation.n_name, #customer.c_address, #customer.c_comment]], aggr=[[SUM(#lineitem.l_extendedprice * Int64(1) - #lineitem.l_discount)]]\
\n Join: #customer.c_nationkey = #nation.n_nationkey\
\n Join: #orders.o_orderkey = #lineitem.l_orderkey\
\n Join: #customer.c_custkey = #orders.o_custkey\
\n Inner Join: #customer.c_nationkey = #nation.n_nationkey\
\n Inner Join: #orders.o_orderkey = #lineitem.l_orderkey\
\n Inner Join: #customer.c_custkey = #orders.o_custkey\
\n TableScan: customer projection=Some([0, 1, 2, 3, 4, 5, 7])\
\n Filter: #orders.o_orderdate >= Date32(\"8674\") AND #orders.o_orderdate < Date32(\"8766\")\
\n TableScan: orders projection=Some([0, 1, 4]), filters=[#orders.o_orderdate >= Date32(\"8674\"), #orders.o_orderdate < Date32(\"8766\")]\
Expand Down