# BounceBack ♻️
[![BounceBack](https://img.shields.io/hexpm/v/bounce_back.svg)](https://hex.pm/packages/bounce_back/0.2.0)
BounceBack is an Elixir library that provides flexible retry mechanisms with customizable strategies for handling retries in the event of failures. It allows you to easily implement retry logic in your applications using a variety of strategies, such as exponential backoff and linear delay, with options for jitter to avoid congestion during retries.
## Features
- **Retry Mechanism**: Automatically retries failed operations with customizable retry policies.
- **Multiple Strategies**: Built-in strategies like exponential backoff and linear delay, with the ability to extend.
- **Customizable Options**: Control the number of retries, delay between retries, and more.
- **Telemetry Integration**: Hooks for monitoring retry attempts and failures using Elixir's `:telemetry`.
- **Error Handling**: Retry based on specific error types or conditions.
## Installation
Add `bounce_back` to your list of dependencies in `mix.exs`:
```elixir
defp deps do
[
{:bounce_back, "~> 0.2.0"}
]
end
```
Then, run the following command to install the dependency:
```bash
mix deps.get
```
## Usage
### Basic Retry Example
You can use the `BounceBack.retry/2` macro to wrap any operation you want to retry. Here's an example that retries a function that can fail, using the default options:
```elixir
defmodule MyApp.Example do
import BounceBack
def some_function do
retry do
# Your code that might fail
IO.puts("Attempting operation...")
{:error, :something_went_wrong}
end
end
end
```
In this example, the operation will be retried up to 5 times with an exponential backoff strategy if it fails.
### Customizing Retry Behavior
You can provide custom options to configure how retries are performed. The options include:
- `:max_retries`: The maximum number of retry attempts (default: `5`).
- `:strategy`: The retry strategy (`:exponential_backoff`, `:linear`), with default set to `:exponential_backoff`.
- `:retry_on`: A list of error types or a function that should trigger a retry. If empty, all errors will trigger a retry (default: `[]`).
- `:base_delay`: The base delay in milliseconds between retries (default: `100`).
- `:jitter`: A boolean to enable/disable jitter on the delay (default: `true`).
#### Example with custom options:
```elixir
defmodule MyApp.Example do
import BounceBack
def some_function do
retry(max_retries: 3, strategy: :linear, base_delay: 200, jitter: false) do
IO.puts("Attempting operation...")
{:error, :temporary_error}
end
end
end
```
### Retry Based on Error Types
You can configure `:retry_on` to specify which error types or conditions should trigger a retry:
```elixir
defmodule MyApp.Example do
import BounceBack
def some_function do
retry(retry_on: [:temporary_error]) do
IO.puts("Attempting operation...")
{:error, :temporary_error}
end
end
end
```
In this case, the operation will only retry if the error is `:temporary_error`.
### Telemetry Events
BounceBack integrates with Elixir's `:telemetry` system to emit events each time a retry is attempted. You can attach a default handler to listen for retry events:
```elixir
BounceBack.Telemetry.attach_default_handler()
```
This will log the retry attempts and errors when a retry event occurs.
#### Custom Telemetry Handler
You can also define your own handler for retry events. For example:
```elixir
:telemetry.attach(
"my-custom-handler",
[:bounce_back, :retry],
fn _event, measurements, metadata, _config ->
IO.puts("Retry attempt: #{inspect(measurements)}, Reason: #{inspect(metadata[:error])}")
end,
nil
)
```
## Retry Strategies
BounceBack comes with two built-in retry strategies:
- **Linear**: The delay between retries increases linearly with each attempt.
- **Exponential Backoff**: The delay doubles with each retry attempt, starting from the base delay.
You can define your own strategy by implementing a `wait/3` function in the `BounceBack.Strategies` module.
### Telemetry Events for Retry Attempts
Whenever a retry event occurs, BounceBack emits telemetry events with the following measurements:
- `remaining_retries`: The number of retries remaining before giving up.
- `error`: The reason for the failure that triggered the retry.
## License
BounceBack is released under the MIT License. See the [LICENSE](LICENSE) file for more details.
---
This README provides an overview of how to use the `BounceBack` library, including examples and configuration options.