Skip to main content

pdk_script/
expression.rs

1// Copyright 2023 Salesforce, Inc. All rights reserved.
2use std::fmt::{Display, Formatter};
3
4use serde::de::Visitor;
5use serde::{Deserialize, Deserializer};
6
7use pel::expression::Expression as PelExpression;
8use pel::parser::{Parser, ParsingUnitError};
9
10/// An evaluable expression.
11#[derive(PartialEq, Clone, Debug)]
12pub struct Expression {
13    pub(crate) source: Option<String>,
14    pub(crate) expression: PelExpression,
15}
16
17impl Expression {
18    fn new(expression: PelExpression) -> Self {
19        Self {
20            source: None,
21            expression,
22        }
23    }
24
25    pub(crate) fn with_source(mut self, source: Option<String>) -> Self {
26        self.source = source;
27        self
28    }
29}
30
31impl Display for Expression {
32    fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
33        let source = self.source.as_deref().unwrap_or_default();
34        f.write_fmt(format_args!("#[{}]", source))
35    }
36}
37
38impl<'de> Deserialize<'de> for Expression {
39    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
40    where
41        D: Deserializer<'de>,
42    {
43        struct ResolverVisitor;
44
45        impl Visitor<'_> for ResolverVisitor {
46            type Value = Expression;
47
48            fn expecting(&self, formatter: &mut Formatter) -> std::fmt::Result {
49                formatter.write_str("PEL Expression")
50            }
51
52            fn visit_str<E>(self, value: &str) -> Result<Self::Value, E>
53            where
54                E: serde::de::Error,
55            {
56                let effective_value = if value.is_empty() {
57                    r##"P[[":null", "0-4"], "#[null]"]"##
58                } else {
59                    value
60                };
61
62                let (expression, source) =
63                    Parser::new()
64                        .parse_unit(effective_value)
65                        .map_err(|error| match error {
66                            ParsingUnitError::InvalidContainer => serde::de::Error::invalid_type(
67                                serde::de::Unexpected::Str(value),
68                                &self,
69                            ),
70                            _ => serde::de::Error::custom(format_args!(
71                                "Unexpected error when parsing expression '{value}': {error}"
72                            )),
73                        })?;
74
75                Ok(Expression::new(expression).with_source(source))
76            }
77        }
78
79        deserializer.deserialize_str(ResolverVisitor)
80    }
81}