• Stars
    star
    237
  • Rank 169,885 (Top 4 %)
  • Language
    Ruby
  • License
    MIT License
  • Created about 12 years ago
  • Updated over 4 years ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

A tiny Rubygem for retrying code with randomized, exponential backoff.

Retries

Retries is a gem that provides a single function, with_retries, to evaluate a block with randomized, truncated, exponential backoff.

There are similar projects out there (see retry_block and retry_this, for example) but these will require you to implement the backoff scheme yourself. If you don't need randomized exponential backoff, you should check out those gems.

Installation

You can get the gem with gem install retries or simply add gem "retries" to your Gemfile if you're using bundler.

Usage

Suppose we have some task we are trying to perform: do_the_thing. This might be a call to a third-party API or a flaky service. Here's how you can try it three times before failing:

require "retries"
with_retries(:max_tries => 3) { do_the_thing }

The block is passed a single parameter, attempt_number, which is the number of attempts that have been made (starting at 1):

with_retries(:max_tries => 3) do |attempt_number|
  puts "Trying to do the thing: attempt #{attempt_number}"
  do_the_thing
end

Custom exceptions

By default with_retries rescues instances of StandardError. You'll likely want to make this more specific to your use case. You may provide an exception class or an array of classes:

with_retries(:max_tries => 3, :rescue => RestClient::Exception) { do_the_thing }
with_retries(:max_tries => 3, :rescue => [RestClient::Unauthorized, RestClient::RequestFailed]) do
  do_the_thing
end

Handlers

with_retries allows you to pass a custom handler that will be called each time before the block is retried. The handler will be called with three arguments: exception (the rescued exception), attempt_number (the number of attempts that have been made thus far), and total_delay (the number of seconds since the start of the time the block was first attempted, including all retries).

handler = Proc.new do |exception, attempt_number, total_delay|
  puts "Handler saw a #{exception.class}; retry attempt #{attempt_number}; #{total_delay} seconds have passed."
end
with_retries(:max_tries => 5, :handler => handler, :rescue => [RuntimeError, ZeroDivisionError]) do |attempt|
  (1 / 0) if attempt == 3
  raise "hey!" if attempt < 5
end

This will print something like:

Handler saw a RuntimeError; retry attempt 1; 2.9e-05 seconds have passed.
Handler saw a RuntimeError; retry attempt 2; 0.501176 seconds have passed.
Handler saw a ZeroDivisionError; retry attempt 3; 1.129921 seconds have passed.
Handler saw a RuntimeError; retry attempt 4; 1.886828 seconds have passed.

Delay parameters

By default, with_retries will wait about a half second between the first and second attempts, and then the delay time will increase exponentially between attempts (but stay at no more than 1 second). The delays are perturbed randomly. You can control the parameters via the two options :base_sleep_seconds and :max_sleep_seconds. For instance, you can start the delay at 100ms and go up to a maximum of about 2 seconds:

with_retries(:max_tries => 10, :base_sleep_seconds => 0.1, :max_sleep_seconds => 2.0) { do_the_thing }

Testing

In tests, you may wish to test that retries are being performed without any delay for sleeping:

Retries.sleep_enabled = false
with_retries(:max_tries => 100) { raise "Boo!" } # Now this fails fast

Of course, this will mask any errors to the :base_sleep_seconds and :max_sleep_seconds parameters, so use with caution.

Issues

File tickets here on Github.

Development

To run the tests: first clone the repo, then

$ bundle install
$ bundle exec rake test

Authors

Retries was created by Harry Robertson and Caleb Spare.

Other contributions from:

License

Retries is released under the MIT License.

More Repositories

1

barkeep

The friendly code review system.
Ruby
1,424
star
2

atlantis

Open Source PaaS Built on Docker
Go
391
star
3

spark-jobserver

REST job server for Spark. Note that this is *not* the mainline open source version. For that, go to https://github.com/spark-jobserver/spark-jobserver. This fork now serves as a semi-private repo for Ooyala.
Scala
344
star
4

livecss

Making the browser dance to your CSS
JavaScript
128
star
5

metrics_storm

Easy metrics collection for Storm topologies using Coda Hale Metrics
Scala
100
star
6

hastur-server

Hastur's server
Ruby
42
star
7

android-sample-apps

Java
35
star
8

ios-sample-apps

Ooyala SDK for iOS Sample Apps
Objective-C
33
star
9

go-dogstatsd

Go
30
star
10

go-docker-registry

Docker Registry Written in Go
Go
30
star
11

chromecast-sample-receiver

Chromecast Sample Receiver
JavaScript
24
star
12

html5-skin

JavaScript
22
star
13

hastur

Hastur's Ruby client
Ruby
20
star
14

tarball-chef-cookbook

Ruby based resource provider to manage tarballs in chef.
Ruby
20
star
15

cumulus-linux-cookbook

Cookbook for managing cummulus switches
Ruby
18
star
16

scamr

A Hadoop map reduce framework for Scala.
Scala
15
star
17

native-skin

The source of the new Skin UI SDKs for both Android and IOS
JavaScript
13
star
18

pathological

Manage your Ruby project's load path
Ruby
10
star
19

api-sdks

Ooyala V2 API SDKs written in several languages.
Ruby
10
star
20

scope

Concise Ruby unit testing, in the spirit of Shoulda
Ruby
9
star
21

miyamoto

Masterless puppet with S3
Perl
9
star
22

quagga-cookbook

Ruby
8
star
23

html5-ad-plugins

JavaScript
7
star
24

remote_http_testing

A small library for making remote HTTP requests and response assertions in tests.
Ruby
7
star
25

immunity

Continuous integration and staged deployment.
Ruby
7
star
26

hadoopmon

High Availability Hadoop (hadoop 2.x.0) watcher
Go
6
star
27

skin-config

The shared JSON for styling Alice
JavaScript
5
star
28

html5-analytics-plugins

JavaScript
5
star
29

statusz

Write out deploy-time git metadata for your server.
Ruby
5
star
30

flags

Ruby
5
star
31

ruby-v2-sdk

Ruby
5
star
32

php-v2-sdk

PHP
5
star
33

Ooyala-AdobeCQ

Java
5
star
34

backlot-ingestion-library

Create and upload movies to Backlot through JavaScript
JavaScript
4
star
35

html5-video-plugins

HTML5 Video Plugins
JavaScript
4
star
36

atlantis-router

Router for Atlantis
Go
4
star
37

node-ooyala-api-client

Ooyala API wrapper for Node.js
JavaScript
4
star
38

html5-common

JavaScript
3
star
39

m3u8

Go
3
star
40

csharp-v2-sdk

C#
3
star
41

my-sequel-synchrony

A fiber-aware MySQL adapter for Sequel that works with em-synchrony
Ruby
3
star
42

quilt

Javascript stitcher for node.js
JavaScript
3
star
43

java-v2-sdk

Java
3
star
44

oppm

JavaScript
3
star
45

Ooyala-Sharepoint

C#
2
star
46

playback-lab-samples

Sample projects from the playback team.
JavaScript
2
star
47

atlantis-dashboard

Dashboard for Atlantis
JavaScript
2
star
48

ruby-quilt

Ruby
2
star
49

atlantis-aquarium

Ruby
2
star
50

atlantis-manager

Manager for Atlantis
Go
2
star
51

go-jenkins-cli

Jenkins Client in Go
Go
2
star
52

osmf-html5-emulator

2
star
53

node-asset-builder

Image/css bundler for node.js
JavaScript
2
star
54

kitchen-vagrant-disks

Example code for adding extra disks to test-kitchen
Ruby
1
star
55

_legacy_code-samples

List of code samples of various uses of Ooyala technology. From simple pages embedding a player to pages assembled with dynamic content coming from our APIs
PHP
1
star
56

hastur-c

Hastur's C client
C
1
star
57

nodejs-ooyala-v2-sdk

JavaScript
1
star
58

sequel_rails_migrations

Ruby
1
star
59

beIN_playlist-plugin

Custom Ooyala player v4 playlist plugin for beIN.
JavaScript
1
star
60

iq-sdk-roku-sample

Brightscript
1
star
61

nodule

Ruby
1
star
62

atlantis-builder

Builder for Atlantis
Go
1
star
63

mediaaccessinsights

Media Streaming Access insights
Ruby
1
star
64

barkeep_integration_tests

A repo full of test data used for running barkeep's integration tests.
1
star
65

immunity_integration_test_app

A sample app used by the Immunity System's integration tests.
Ruby
1
star
66

getbarkeep.org

The Barkeep Project Website
Ruby
1
star
67

guzzle-rotten-tomatoes

Access the Rotten Tomatoes API in PHP using Guzzle. This client serves as a simple example of how to build web service clients using Guzzle.
PHP
1
star
68

termite

Ruby
1
star
69

ecology

Ruby
1
star
70

atlantis-supervisor

Supervisor for Atlantis
Go
1
star
71

panache

Templated code style checking
Ruby
1
star
72

iq-sdk-roku

Brightscript
1
star
73

hello-atlantis

Sample and test apps to be run on Atlantis
Go
1
star
74

route53

Go
1
star
75

java-cli-uploader-sampleapp

A sample app that demonstrates how to use the Backlot API for uploading assets from the Command Line (CLI).
Java
1
star