From 2a1aa9e8199b5236b0c0a244922d845d2bf8024b Mon Sep 17 00:00:00 2001 From: Mikey Date: Thu, 10 Aug 2023 00:32:52 +1200 Subject: [PATCH] add If operation (#8) also - add `value.is_truthy()` - add `#[serde(deny_unknown_fields)]` to Operation's --- rimu-value/src/lib.rs | 17 ++++ rimu/src/operations/eval.rs | 1 + rimu/src/operations/if_.rs | 80 ++++++++++++++++++ rimu/src/operations/let_.rs | 3 +- rimu/src/operations/mod.rs | 5 ++ rimu/tests/spec.rs | 5 ++ rimu/tests/spec/if.yml | 156 ++++++++++++++++++++++++++++++++++++ rimu/tests/spec/let.yml | 19 ++--- 8 files changed, 276 insertions(+), 10 deletions(-) create mode 100644 rimu/src/operations/if_.rs create mode 100644 rimu/tests/spec/if.yml diff --git a/rimu-value/src/lib.rs b/rimu-value/src/lib.rs index dfb4899..bbe3e04 100644 --- a/rimu-value/src/lib.rs +++ b/rimu-value/src/lib.rs @@ -112,6 +112,23 @@ pub fn value_get_in<'a>(value: &'a Value, keys: &[&str]) -> Option<&'a Value> { } } +impl Value { + pub fn is_truthy(&self) -> bool { + match self { + Value::Null => false, + Value::Boolean(boolean) => *boolean, + Value::String(string) => string.len() > 0, + Value::Number(number) => match number { + Number::Unsigned(u) => u != &0_u64, + Number::Signed(s) => s != &0_i64, + Number::Float(f) => f != &0_f64, + }, + Value::List(list) => list.len() > 0, + Value::Object(object) => object.len() > 0, + } + } +} + #[cfg(test)] mod test { use std::{borrow::Cow, ffi::OsString, path::PathBuf}; diff --git a/rimu/src/operations/eval.rs b/rimu/src/operations/eval.rs index 0cf8535..ff86c95 100644 --- a/rimu/src/operations/eval.rs +++ b/rimu/src/operations/eval.rs @@ -4,6 +4,7 @@ use super::Operation; use crate::{Context, Engine, RenderError, Value}; #[derive(Clone, Debug, PartialEq, Deserialize)] +#[serde(deny_unknown_fields)] pub struct EvalOperation { #[serde(alias = "$eval")] pub expr: String, diff --git a/rimu/src/operations/if_.rs b/rimu/src/operations/if_.rs new file mode 100644 index 0000000..18e5b82 --- /dev/null +++ b/rimu/src/operations/if_.rs @@ -0,0 +1,80 @@ +use serde::Deserialize; + +use super::Operation; +use crate::{Context, Engine, RenderError, Template, Value}; + +#[derive(Clone, Debug, PartialEq, Deserialize)] +#[serde(deny_unknown_fields)] +pub struct IfOperation { + #[serde(rename = "$if")] + pub condition: Box