Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Design pattern for "retrying" logic that failed?

I'm writing some reconnect logic to periodically attempt to establish a connection to a remote endpoint which went down. Essentially, the code looks like this:

public void establishConnection() {     try {         this.connection = newConnection();     } catch (IOException e) {         // connection failed, try again.         try { Thread.sleep(1000); } catch (InterruptedException e) {};          establishConnection();     } } 

I've solved this general problem with code similar to the above on many occasions, but I feel largely unsatisfied with the result. Is there a design pattern designed for dealing with this issue?

like image 987
Naftuli Kay Avatar asked Jul 27 '12 17:07

Naftuli Kay


People also ask

How do you write a retry mechanism in Java?

1. Simple for-loop with try-catch. A simple solution to implement retry logic in Java is to write your code inside a for loop that executes the specified number of times (the maximum retry value).

What is a retry logic?

Retry logic is implemented whenever there is a failing operation. Implement retry logic only where the full context of a failing operation. It's important to log all connectivity failures that cause a retry so that underlying problems with the application, services, or resources can be identified.

What is a retry mechanism?

This retry mechanism should control the number of retries attempted before giving up and any thread sleep time between attempts. The following is a simplified example of a retry mechanism written in Java to serve as a guide. It employs a helper class, RetryOnException .


2 Answers

Shameless plug: I have implemented some classes to allow retrying operations. The library is not made available yet, but you may fork it on github. And a fork exists.

It allows building a Retryer with various flexible strategies. For example:

Retryer retryer =      RetryerBuilder.newBuilder()                   .withWaitStrategy(WaitStrategies.fixedWait(1, TimeUnit.SECOND))                   .withStopStrategy(StopStrategies.stopAfterAttempt(3))                   .retryIfExceptionOfType(IOException.class)                   .build(); 

And you can then execute a callable (or several ones) with the Retryer:

retryer.call(new Callable<Void>() {     public Void call() throws IOException {         connection = newConnection();         return null;     } } 
like image 64
JB Nizet Avatar answered Oct 02 '22 12:10

JB Nizet


You could try the Idempotent Retry Pattern.

enter image description here

like image 30
GalacticJello Avatar answered Oct 02 '22 13:10

GalacticJello