openpql_pql_parser/ast/
selector.rs

1use super::{Error, Expr, Ident, ResultE, SelectorKind, String};
2
3#[derive(Clone, PartialEq, derive_more::Debug)]
4#[debug("{:?}({:?}){}", self.kind, self.expr, _alias_to_str(self.alias.as_ref()))]
5pub struct Selector<'i> {
6    pub kind: SelectorKind,
7    pub expr: Expr<'i>,
8    pub alias: Option<Ident<'i>>,
9}
10
11fn _alias_to_str(alias: Option<&Ident>) -> String {
12    alias.map_or_else(String::default, |id| format!(" as {id:?}"))
13}
14
15impl<'i> Selector<'i> {
16    pub fn new(
17        kind: &Ident<'i>,
18        expr: Expr<'i>,
19        alias: Option<Ident<'i>>,
20    ) -> ResultE<'i, Self> {
21        let kind = match kind.inner.to_ascii_lowercase().as_str() {
22            "avg" => SelectorKind::Avg,
23            "count" => SelectorKind::Count,
24            "max" => SelectorKind::Max,
25            "min" => SelectorKind::Min,
26            _ => return Err(Error::UnrecognizedSelector(kind.loc).into()),
27        };
28
29        Ok(Self { kind, expr, alias })
30    }
31}
32
33#[cfg(test)]
34#[cfg_attr(coverage_nightly, coverage(off))]
35mod tests {
36    use crate::*;
37
38    fn assert_selector(src: &str, expected: &str) {
39        assert_eq!(format!("{:?}", parse_selector(src).unwrap()), expected);
40    }
41
42    #[test]
43    fn test_selector() {
44        assert_selector("avg(equity(hero, river))", "avg(equity(hero,river))");
45        assert_selector(
46            "avg(equity(hero, river)) as s1",
47            "avg(equity(hero,river)) as s1",
48        );
49
50        assert_selector("count(_)", "count(_)");
51        assert_selector("max(_)", "max(_)");
52        assert_selector("min(_)", "min(_)");
53    }
54
55    fn assert_err(src: &str, expected: Error) {
56        assert_eq!(parse_selector(src).unwrap_err(), expected);
57    }
58
59    #[test]
60    fn test_selector_err() {
61        let src = "invalid(_)";
62        assert_err(src, Error::UnrecognizedSelector(loc(src, "invalid")));
63    }
64}