use altair_retry::prelude::*;
use std::sync::Arc;
use std::sync::atomic::{AtomicU32, Ordering};
use std::time::Duration;
#[tokio::main]
async fn main() -> anyhow::Result<()> {
let cancel = CancellationToken::new();
let cfg = Config::builder()
.name("checkout.charge")
.max_retries(5)
.initial_interval(Duration::from_millis(50))
.max_interval(Duration::from_secs(5))
.multiplier(2.0)
.jitter(true)
.cancellation_token(cancel)
.build();
let attempts = Arc::new(AtomicU32::new(0));
let counter = attempts.clone();
let result = retry(cfg, move || {
let counter = counter.clone();
async move {
let n = counter.fetch_add(1, Ordering::SeqCst) + 1;
println!("attempt {n}");
if n < 3 {
Err::<&'static str, _>(std::io::Error::other("not yet ready"))
} else {
Ok("charged")
}
}
})
.await?;
println!("result: {result}");
println!("total attempts: {}", attempts.load(Ordering::SeqCst));
Ok(())
}