Skip to content

Commit

Permalink
Support Expr::Case in aggregate module (#945)
Browse files Browse the repository at this point in the history
  • Loading branch information
ever0de authored Oct 15, 2022
1 parent 2d18de8 commit 24c30da
Show file tree
Hide file tree
Showing 6 changed files with 62 additions and 3 deletions.
36 changes: 36 additions & 0 deletions core/src/executor/aggregate/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -179,6 +179,7 @@ async fn aggregate<'a>(
expr: &'a Expr,
) -> Result<State<'a>> {
let aggr = |state, expr| aggregate(state, filter_context.as_ref().map(Rc::clone), expr);

match expr {
Expr::Between {
expr, low, high, ..
Expand All @@ -200,6 +201,26 @@ async fn aggregate<'a>(
}
Expr::UnaryOp { expr, .. } => aggr(state, expr).await,
Expr::Nested(expr) => aggr(state, expr).await,
Expr::Case {
operand,
when_then,
else_result,
} => {
let operand = std::iter::once(operand.as_ref())
.filter_map(|operand| operand.map(|operand| &**operand));
let when_then = when_then
.iter()
.flat_map(|(when, then)| std::iter::once(when).chain(std::iter::once(then)));
let else_result = std::iter::once(else_result.as_ref())
.filter_map(|else_result| else_result.map(|else_result| &**else_result));

stream::iter(operand.chain(when_then).chain(else_result))
.fold(
Ok(state),
|state, expr| async move { aggr(state?, expr).await },
)
.await
}
Expr::Aggregate(aggr) => state.accumulate(filter_context, aggr.as_ref()).await,
_ => Ok(state),
}
Expand All @@ -213,6 +234,21 @@ fn check(expr: &Expr) -> bool {
Expr::BinaryOp { left, right, .. } => check(left) || check(right),
Expr::UnaryOp { expr, .. } => check(expr),
Expr::Nested(expr) => check(expr),
Expr::Case {
operand,
when_then,
else_result,
} => {
operand.as_ref().map(|expr| check(&*expr)).unwrap_or(false)
|| when_then
.iter()
.map(|(when, then)| check(when) || check(then))
.any(identity)
|| else_result
.as_ref()
.map(|expr| check(&*expr))
.unwrap_or(false)
}
Expr::Aggregate(_) => true,
_ => false,
}
Expand Down
2 changes: 2 additions & 0 deletions core/src/executor/aggregate/state.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,11 @@ use {
std::{cmp::Ordering, rc::Rc},
utils::{IndexMap, Vector},
};

type Group = Rc<Vec<Key>>;
type ValuesMap<'a> = HashMap<&'a Aggregate, Value>;
type Context<'a> = Rc<BlendContext<'a>>;

enum AggrValue {
Count {
wildcard: bool,
Expand Down
16 changes: 14 additions & 2 deletions test-suite/src/aggregate/min.rs
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,20 @@ test_case!(min, async move {
),
),
(
"SELECT SUM(quantity) * 2 + MIN(quantity) - 3 / 1 FROM Item",
select!("SUM(quantity) * 2 + MIN(quantity) - 3 / 1"; I64; 91),
"SELECT SUM(quantity) * 2 + MIN(quantity) - 3 / 1 FROM Item;",
select!(
"SUM(quantity) * 2 + MIN(quantity) - 3 / 1"
I64;
91
),
),
(
"SELECT MIN(CASE WHEN quantity > 5 THEN id END) FROM Item;",
select!(
"MIN(CASE WHEN quantity > 5 THEN id END)"
I64;
1
),
),
];

Expand Down
8 changes: 8 additions & 0 deletions test-suite/src/aggregate/sum.rs
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,14 @@ test_case!(sum, async move {
174
),
),
(
"SELECT SUM(CASE WHEN id > 3 THEN quantity ELSE 0 END) FROM Item;",
select!(
"SUM(CASE WHEN id > 3 THEN quantity ELSE 0 END)"
I64;
28
),
),
];

for (sql, expected) in test_cases {
Expand Down
2 changes: 1 addition & 1 deletion test-suite/src/arithmetic/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ use {
gluesql_core::{
data::{Literal, LiteralError, NumericBinaryOperator, ValueError},
executor::{EvaluateError, UpdateError},
prelude::Value::{self},
prelude::Value,
},
std::borrow::Cow,
};
Expand Down
1 change: 1 addition & 0 deletions test-suite/src/inline_view.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ use {
translate::TranslateError,
},
};

test_case!(inline_view, async move {
let test_cases = [
(
Expand Down

0 comments on commit 24c30da

Please sign in to comment.