Skip to main content

vrl/stdlib/
boolean.rs

1use crate::compiler::prelude::*;
2
3fn boolean(value: Value) -> Resolved {
4    match value {
5        v @ Value::Boolean(_) => Ok(v),
6        v => Err(format!("expected boolean, got {}", v.kind()).into()),
7    }
8}
9
10#[derive(Clone, Copy, Debug)]
11pub struct Boolean;
12
13impl Function for Boolean {
14    fn identifier(&self) -> &'static str {
15        "bool"
16    }
17
18    fn usage(&self) -> &'static str {
19        indoc! {"
20            Returns `value` if it is a Boolean, otherwise returns an error. This enables the type
21            checker to guarantee that the returned value is a Boolean and can be used in any
22            function that expects a Boolean.
23        "}
24    }
25
26    fn category(&self) -> &'static str {
27        Category::Type.as_ref()
28    }
29
30    fn internal_failure_reasons(&self) -> &'static [&'static str] {
31        &["`value` is not a Boolean."]
32    }
33
34    fn return_kind(&self) -> u16 {
35        kind::BOOLEAN
36    }
37
38    fn return_rules(&self) -> &'static [&'static str] {
39        &[
40            "Returns `value` if it's a Boolean.",
41            "Raises an error if not a Boolean.",
42        ]
43    }
44
45    fn parameters(&self) -> &'static [Parameter] {
46        const PARAMETERS: &[Parameter] = &[Parameter::required(
47            "value",
48            kind::ANY,
49            "The value to check if it is a Boolean.",
50        )];
51        PARAMETERS
52    }
53
54    fn examples(&self) -> &'static [Example] {
55        &[
56            example! {
57                title: "Valid Boolean",
58                source: "bool(false)",
59                result: Ok("false"),
60            },
61            example! {
62                title: "Invalid Boolean",
63                source: "bool!(42)",
64                result: Err(
65                    r#"function call error for "bool" at (0:9): expected boolean, got integer"#,
66                ),
67            },
68            example! {
69                title: "Valid Boolean from path",
70                source: "bool!(.value)",
71                input: r#"{ "value": true }"#,
72                result: Ok("true"),
73            },
74        ]
75    }
76
77    fn compile(
78        &self,
79        _state: &state::TypeState,
80        _ctx: &mut FunctionCompileContext,
81        arguments: ArgumentList,
82    ) -> Compiled {
83        let value = arguments.required("value");
84
85        Ok(BooleanFn { value }.as_expr())
86    }
87}
88
89#[derive(Debug, Clone)]
90struct BooleanFn {
91    value: Box<dyn Expression>,
92}
93
94impl FunctionExpression for BooleanFn {
95    fn resolve(&self, ctx: &mut Context) -> Resolved {
96        boolean(self.value.resolve(ctx)?)
97    }
98
99    fn type_def(&self, state: &state::TypeState) -> TypeDef {
100        let non_boolean = !self.value.type_def(state).is_boolean();
101
102        TypeDef::boolean().maybe_fallible(non_boolean)
103    }
104}