use hamelin_lib::func::defs::Filter;
use crate::eval::error::EvalError;
use crate::eval::evaluator::invoke_closure;
use crate::registry::EvalRegistry;
use crate::value::Value;
pub fn register(registry: &mut EvalRegistry) {
registry.register_eval::<Filter>(|mut bindings| {
let array_value = bindings.take_by_name("array")?;
let closure_value = bindings.take_by_name("lambda")?;
if array_value.is_null() {
return Ok(Value::Null);
}
let elements = array_value.require_array()?;
let closure = closure_value.require_closure()?;
let mut results = Vec::new();
for elem in elements {
let predicate_result = invoke_closure(&closure, vec![elem.clone()])?;
match &predicate_result {
Value::Null => {}
Value::Boolean(true) => results.push(elem),
Value::Boolean(false) => {}
other => {
return Err(EvalError::execution(format!(
"filter predicate must return boolean, got {}",
other.type_name()
))
.into());
}
}
}
Ok(Value::Array(results))
});
}