wp-lang 0.3.0

WPL language crate with AST, parser, evaluator, builtins, and generators.
Documentation
use crate::{WplRule, WplStatementType, ast::AnnFun};
use derive_getters::Getters;
use serde::{Deserialize, Deserializer, Serialize, Serializer};
use smol_str::SmolStr;

#[derive(Serialize, Deserialize)]
pub struct WplRuleMeta {
    pub name: SmolStr,
    pub tags: Vec<WplTag>,
}

impl From<&WplRule> for WplRuleMeta {
    fn from(value: &WplRule) -> Self {
        let mut tags = Vec::new();
        match &value.statement {
            WplStatementType::Express(x) => {
                Self::export_tags(&mut tags, &x.tags);
            }
        }
        Self {
            name: value.name.clone(),
            tags,
        }
    }
}

impl WplRuleMeta {
    fn export_tags(tags: &mut Vec<WplTag>, x: &Option<AnnFun>) {
        if let Some(tag_obj) = x {
            for (k, v) in &tag_obj.tags {
                tags.push(WplTag::new(
                    SmolStr::from(k.as_str()),
                    SmolStr::from(v.as_str()),
                ))
            }
        }
    }
}

#[derive(Default, Getters, Debug, Clone)]
pub struct WplTag {
    pub key: SmolStr,
    pub val: SmolStr,
}
impl WplTag {
    pub fn new(key: SmolStr, val: SmolStr) -> Self {
        Self { key, val }
    }
}

impl Serialize for WplTag {
    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
    where
        S: Serializer,
    {
        serializer.serialize_str(format!("{}:{}", self.key.as_str(), self.val.as_str()).as_str())
    }
}

impl<'de> Deserialize<'de> for WplTag {
    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
    where
        D: Deserializer<'de>,
    {
        let s = String::deserialize(deserializer)?;
        let parts: Vec<&str> = s.split(':').collect();
        if parts.len() == 2 {
            Ok(WplTag {
                key: SmolStr::from(parts[0]),
                val: SmolStr::from(parts[1]),
            })
        } else {
            Err(serde::de::Error::custom("Invalid format"))
        }
    }
}