retry-policy 0.2.1

Retry Policy
Documentation
use alloc::boxed::Box;

use retry_backoff::RetryBackoff;
use retry_predicate::RetryPredicate;

use crate::retry_policy::RetryPolicy;

//
#[derive(Debug)]
pub struct Policy<PParams> {
    pub predicate: Box<dyn RetryPredicate<PParams> + Send + Sync>,
    pub max_retries: usize,
    pub backoff: Box<dyn RetryBackoff + Send + Sync>,
}

impl<PParams> Policy<PParams> {
    pub fn new<P, BO>(predicate: P, max_retries: usize, backoff: BO) -> Self
    where
        P: RetryPredicate<PParams> + Send + Sync + 'static,
        BO: RetryBackoff + Send + Sync + 'static,
    {
        Self {
            predicate: Box::new(predicate),
            max_retries,
            backoff: Box::new(backoff),
        }
    }
}

impl<PParams> RetryPolicy<PParams> for Policy<PParams> {
    fn predicate(&self) -> &dyn RetryPredicate<PParams> {
        self.predicate.as_ref()
    }
    fn max_retries(&self) -> usize {
        self.max_retries
    }
    fn backoff(&self) -> &dyn RetryBackoff {
        self.backoff.as_ref()
    }

    fn name(&self) -> &str {
        "Simple"
    }
}

#[cfg(test)]
mod tests {
    use super::*;

    use core::{ops::ControlFlow, time::Duration};

    use retry_backoff::backoffs::FnBackoff;
    use retry_predicate::predicates::AlwaysPredicate;

    #[test]
    fn test_impl_retry_policy() {
        let policy = Policy::new(
            AlwaysPredicate,
            1,
            FnBackoff::from(|_attempts: usize| Duration::from_secs(1)),
        );

        assert_eq!(
            RetryPolicy::next_step(&policy, &(), 1),
            ControlFlow::Continue(Duration::from_secs(1))
        );
        assert_eq!(RetryPolicy::name(&policy), "Simple");
    }
}