19 releases (6 stable)

1.3.0 Nov 22, 2024
1.1.0 Aug 29, 2024
0.5.0 Aug 22, 2024
0.4.4 Apr 8, 2024
0.0.2 Apr 14, 2022

#69 in Rust patterns

Download history 54043/week @ 2024-08-22 49836/week @ 2024-08-29 60004/week @ 2024-09-05 92514/week @ 2024-09-12 91325/week @ 2024-09-19 98155/week @ 2024-09-26 98473/week @ 2024-10-03 95667/week @ 2024-10-10 83413/week @ 2024-10-17 72086/week @ 2024-10-24 65788/week @ 2024-10-31 63275/week @ 2024-11-07 66983/week @ 2024-11-14 72323/week @ 2024-11-21 66506/week @ 2024-11-28 69625/week @ 2024-12-05

287,749 downloads per month
Used in 243 crates (33 directly)

Apache-2.0

91KB
1.5K SLoC

BackON   Build Status Latest Version

BackON

Make retry like a built-in feature provided by Rust.

  • Simple: Just like a built-in feature: your_fn.retry(ExponentialBuilder::default()).await.
  • Flexible: Supports both blocking and async functions.
  • Powerful: Allows control over retry behavior such as when and notify.
  • Customizable: Supports custom retry strategies like exponential, constant, etc.
  • Adaptable: Works on all platforms supported by Rust, including both wasm and no-std.

Quick Start

Retry an async function.

use anyhow::Result;
use backon::ExponentialBuilder;
use backon::Retryable;

async fn fetch() -> Result<String> {
    Ok("hello, world!".to_string())
}

#[tokio::main]
async fn main() -> Result<()> {
    let content = fetch
        // Retry with exponential backoff
        .retry(ExponentialBuilder::default())
        // Sleep implementation, required if no feature has been enabled
        .sleep(tokio::time::sleep)
        // When to retry
        .when(|e| e.to_string() == "EOF")
        // Notify when retrying
        .notify(|err: &anyhow::Error, dur: Duration| {
            println!("retrying {:?} after {:?}", err, dur);
        })
        .await?;
    println!("fetch succeeded: {}", content);

    Ok(())
}

Retry a blocking function.

use anyhow::Result;
use backon::BlockingRetryable;
use backon::ExponentialBuilder;

fn fetch() -> Result<String> {
    Ok("hello, world!".to_string())
}

fn main() -> Result<()> {
    let content = fetch
        // Retry with exponential backoff
        .retry(ExponentialBuilder::default())
        // Sleep implementation, required if no feature has been enabled
        .sleep(std::thread::sleep)
        // When to retry
        .when(|e| e.to_string() == "EOF")
        // Notify when retrying
        .notify(|err: &anyhow::Error, dur: Duration| {
            println!("retrying {:?} after {:?}", err, dur);
        })
        .call()?;
    println!("fetch succeeded: {}", content);

    Ok(())
}

Contributing

Check out the CONTRIBUTING.md guide for more details on getting started with contributing to this project.

Getting help

Submit issues for bug report or asking questions in discussion.

License

Licensed under Apache License, Version 2.0.

Dependencies

~0–5.5MB
~24K SLoC