Skip to content

Commit

Permalink
cleaning
Browse files Browse the repository at this point in the history
  • Loading branch information
andicuko committed Mar 18, 2024
1 parent 1fd4dae commit c31086a
Show file tree
Hide file tree
Showing 4 changed files with 50 additions and 28 deletions.
14 changes: 11 additions & 3 deletions src/hierarchy.rs
Original file line number Diff line number Diff line change
Expand Up @@ -494,16 +494,24 @@ mod tests {
(vec!["a", "e", "f"], 5),
(vec!["b", "c"], 6),
]);

let expected = Hierarchy::from([
(vec!["d"], 2),
(vec!["e"], 4),
(vec!["f"], 5),
]);
let non_ambiguous = values.non_ambiguous_tails();
assert_eq!(non_ambiguous, expected);
println!("{}", non_ambiguous);

let values = Hierarchy::from([
(vec!["t1", "x"], 1),
(vec!["x"], 1),
(vec!["x"], 2),
]);
let expected = Hierarchy::from([
(vec!["x"], 2),
]);

let non_ambiguous = values.non_ambiguous_tails();
assert_eq!(non_ambiguous, expected);
println!("{}", non_ambiguous);
}
}
29 changes: 18 additions & 11 deletions src/relation/rewriting.rs
Original file line number Diff line number Diff line change
Expand Up @@ -202,44 +202,51 @@ impl Join {
self
}

/// Replace the duplicates fields specified in `columns` by their coalesce expression
/// Its mimics teh behavior of USING in SQL
/// To mimic the behavior of USING(col) and NATURAL JOIN in SQL we create
/// a map where join columns identified by `vec` are coalesced.
/// vec: vector of string identifying input columns present in both _LEFT_
/// and _RIGHT_ relation of the join.
/// columns: is the Hierarchy mapping input names in the JOIN to name field
///
/// The coalesced fields names and the corresponding alias is also returned in Hierarchy<Identifier>
/// It returns a:
/// - Map build on top the Join with coalesced column along with
/// the other fields of the join and
/// - coalesced columns mapping (name in join -> name in map)
pub fn remove_duplicates_and_coalesce(
self,
vec: Vec<String>,
columns: &Hierarchy<Identifier>,
) -> (Relation, Hierarchy<Identifier>) {
let mut coalesced_cols: Vec<(Identifier, Identifier)> = vec![];
let fields = self
let coalesced = self
.field_inputs()
.filter_map(|(_, id)| {
let col = id.as_ref().last().unwrap();
if id.as_ref().first().unwrap().as_str() == LEFT_INPUT_NAME && vec.contains(col) {
.filter_map(|(_, input_id)| {
let col = input_id.as_ref().last().unwrap();
if input_id.as_ref().first().unwrap().as_str() == LEFT_INPUT_NAME && vec.contains(col) {
let left_col = columns[[LEFT_INPUT_NAME, col]].as_ref().last().unwrap();
let right_col = columns[[RIGHT_INPUT_NAME, col]].as_ref().last().unwrap();
coalesced_cols.push((left_col.as_str().into(), col[..].into()));
coalesced_cols.push((right_col.as_str().into(), col[..].into()));
Some((
col.clone(),
Expr::coalesce(
Expr::col(columns[[LEFT_INPUT_NAME, col]].as_ref().last().unwrap()),
Expr::col(columns[[RIGHT_INPUT_NAME, col]].as_ref().last().unwrap()),
Expr::col(left_col),
Expr::col(right_col),
),
))
} else {
None
}
})
});
let coalesced_with_others = coalesced
.chain(self.field_inputs().filter_map(|(name, id)| {
let col = id.as_ref().last().unwrap();
(!vec.contains(col)).then_some((name.clone(), Expr::col(name)))
}))
.collect::<Vec<_>>();
(Relation::map()
.input(Relation::from(self))
.with_iter(fields)
.with_iter(coalesced_with_others)
.build(), coalesced_cols.into_iter().collect())
}
}
Expand Down
14 changes: 0 additions & 14 deletions src/sql/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -118,20 +118,6 @@ mod tests {
use itertools::Itertools;
use sqlparser::dialect::BigQueryDialect;

#[test]
fn test_display_test() {
let database = postgresql::test_database();
let relations = database.relations();
let query = r#"
WITH t1 AS (SELECT a,d FROM table_1),
t2 AS (SELECT * FROM table_2)
SELECT * FROM t1 INNER JOIN t2 ON t1.d = t2.x INNER JOIN table_2 ON t1.d=table_2.x ORDER BY t1.a, t2.x, t2.y, t2.z
"#;
let relation = Relation::try_from(parse(query).unwrap().with(&relations)).unwrap();
relation.display_dot().unwrap();
let relation_query: &str = &ast::Query::from(&relation).to_string();
println!("{}",relation_query);
}

#[test]
fn test_display() {
Expand Down
21 changes: 21 additions & 0 deletions src/sql/relation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1456,6 +1456,27 @@ mod tests {
let mut database = postgresql::test_database();
let relations = database.relations();

let query_str = r#"
SELECT *
FROM table_2 AS t1 INNER JOIN table_2 AS t2 USING(x) INNER JOIN table_2 AS t3 USING(x)
WHERE x > 50
ORDER BY x, t2.y, t2.z
"#;
let query = parse(query_str).unwrap();
let relation = Relation::try_from(QueryWithRelations::new(
&query,
&relations
))
.unwrap();
relation.display_dot().unwrap();
let query: &str = &ast::Query::from(&relation).to_string();
println!("{query}");
_ = database
.query(query)
.unwrap()
.iter()
.map(ToString::to_string);

let query_str = r#"
WITH my_tab AS (SELECT * FROM user_table u JOIN order_table o USING (id))
SELECT * FROM my_tab WHERE id > 50;
Expand Down

0 comments on commit c31086a

Please sign in to comment.