1use jrsonnet_evaluator::{2 Error, Result, Thunk, Val,3 function::{FuncVal, NativeFn},4 typed::{ComplexValType, FromUntyped, Typed, ValType},5};67type PreparedKeyF = NativeFn!((Thunk<Val>) -> Val);89#[derive(Default, Clone)]10pub enum KeyF {11 #[default]12 Identity,13 Prepared(PreparedKeyF),14 PrepareFailure(Error),15}16impl KeyF {17 pub fn is_identity(&self) -> bool {18 matches!(self, Self::Identity)19 }20 fn new(val: FuncVal) -> Self {21 if val.is_identity() {22 Self::Identity23 } else {24 PreparedKeyF::try_from(val).map_or_else(Self::PrepareFailure, Self::Prepared)25 }26 }27 pub fn eval(&self, val: impl Into<Thunk<Val>>) -> Result<Val> {28 match self {29 KeyF::Identity => val.into().evaluate(),30 KeyF::Prepared(p) => p.call(val.into()),31 KeyF::PrepareFailure(e) => Err(e.clone()),32 }33 }34}3536impl Typed for KeyF {37 const TYPE: &'static ComplexValType = &ComplexValType::Simple(ValType::Func);38}39impl FromUntyped for KeyF {40 fn from_untyped(untyped: Val) -> Result<Self> {41 FuncVal::from_untyped(untyped).map(Self::new)42 }43}