pub trait Backoff: Send + Sync + 'static {
fn next_backoff(&self) -> impl Future<Output = bool> + Send + '_;
fn reset(&self) -> impl Future<Output = ()> + Send + '_;
}
impl Backoff for () {
async fn next_backoff(&self) -> bool {
false
}
async fn reset(&self) {}
}
impl<T: Backoff> Backoff for Option<T> {
async fn next_backoff(&self) -> bool {
match self {
Some(backoff) => backoff.next_backoff().await,
None => false,
}
}
async fn reset(&self) {
if let Some(backoff) = self {
backoff.reset().await;
}
}
}
impl<T: Backoff> Backoff for crate::std::Arc<T> {
#[inline]
fn next_backoff(&self) -> impl Future<Output = bool> + Send + '_ {
(**self).next_backoff()
}
fn reset(&self) -> impl Future<Output = ()> + Send + '_ {
(**self).reset()
}
}
mod exponential;
#[doc(inline)]
pub use exponential::ExponentialBackoff;
#[cfg(test)]
mod tests {
use super::*;
#[tokio::test(start_paused = true)]
async fn option_backoff_delegates_to_some() {
let backoff = Some(ExponentialBackoff::default());
assert!(backoff.next_backoff().await);
backoff.reset().await;
assert!(backoff.next_backoff().await);
}
#[tokio::test]
async fn option_backoff_none_gives_up() {
let backoff: Option<ExponentialBackoff<()>> = None;
assert!(!backoff.next_backoff().await);
}
}