use std::fmt::{Debug, Display};
use vantage_expressions::{Expression, Expressive, ExpressiveEnum};
#[derive(Debug, Clone)]
pub struct Case<T: Debug + Display + Clone> {
branches: Vec<(Expression<T>, Expression<T>)>,
else_branch: Option<Expression<T>>,
}
impl<T: Debug + Display + Clone> Default for Case<T> {
fn default() -> Self {
Self::new()
}
}
impl<T: Debug + Display + Clone> Case<T> {
pub fn new() -> Self {
Self {
branches: Vec::new(),
else_branch: None,
}
}
pub fn when(mut self, condition: impl Expressive<T>, then: impl Expressive<T>) -> Self {
self.branches.push((condition.expr(), then.expr()));
self
}
pub fn else_(mut self, value: impl Expressive<T>) -> Self {
self.else_branch = Some(value.expr());
self
}
}
impl<T: Debug + Display + Clone> Expressive<T> for Case<T> {
fn expr(&self) -> Expression<T> {
let mut parts: Vec<Expression<T>> = Vec::new();
for (cond, then) in &self.branches {
parts.push(Expression::new(
" WHEN {} THEN {}",
vec![
ExpressiveEnum::Nested(cond.clone()),
ExpressiveEnum::Nested(then.clone()),
],
));
}
let branches_expr = Expression::from_vec(parts, "");
match &self.else_branch {
Some(else_val) => Expression::new(
"CASE{} ELSE {} END",
vec![
ExpressiveEnum::Nested(branches_expr),
ExpressiveEnum::Nested(else_val.clone()),
],
),
None => Expression::new("CASE{} END", vec![ExpressiveEnum::Nested(branches_expr)]),
}
}
}