use std::fmt::Display;
use zrx_scheduler::step::Result;
use zrx_scheduler::Scope;
use crate::stream::function::arguments::{ForId, ForScope, ForValue};
use crate::stream::function::catch;
pub trait DefaultFn<A, I, T>: Send + 'static {
fn execute(&self, scope: &Scope<I>) -> Result<Option<T>>;
}
impl<F, I, T> DefaultFn<ForScope, I, T> for F
where
F: Fn(&Scope<I>) -> Result<Option<T>> + Send + 'static,
I: Display,
{
#[cfg_attr(
feature = "tracing",
tracing::instrument(level = "debug", skip_all, fields(scope = %scope))
)]
#[inline]
fn execute(&self, scope: &Scope<I>) -> Result<Option<T>> {
catch(|| self(scope))
}
}
impl<F, I, T> DefaultFn<ForId, I, T> for F
where
F: Fn(&I) -> Result<Option<T>> + Send + 'static,
I: Display,
{
#[cfg_attr(
feature = "tracing",
tracing::instrument(level = "debug", skip_all, fields(scope = %scope))
)]
#[inline]
fn execute(&self, scope: &Scope<I>) -> Result<Option<T>> {
catch(|| self(scope.try_as_id()?))
}
}
impl<F, I, T> DefaultFn<ForValue, I, T> for F
where
F: Fn() -> Result<Option<T>> + Send + 'static,
I: Display,
{
#[cfg_attr(
feature = "tracing",
tracing::instrument(level = "debug", skip_all, fields(scope = %scope))
)]
#[inline]
fn execute(&self, scope: &Scope<I>) -> Result<Option<T>> {
catch(self)
}
}