One thing I would like to add. Most of the exceptions (99.999%) mean that something is very wrong with your code or environment that requires the attention of admins. If your code cannot connect to the database, this is probably a misconfigured environment, it makes little sense to repeat it to find out that it does not work the 3rd, 4th or 5th time. If you throw an exception because the person did not give a valid credit card number, retrying will not magically populate the credit card number.
The only situations that require a repeated attempt to remotely work are when the system is very stressed and ends from time to time, but in this situation, the repetition logic will probably cause more stress than less (3 times for 3 attempts in each transaction). But this is what systems do to reduce demand (see apollo landing module mission story). When the system is asked to do more than it can, it starts to drop tasks, and timeouts are a signal that the system is stressed (or poorly written). You would be in a much better situation if you simply increased the capacity of your system (add more bars, larger servers, more servers, improve algorithms, scale it!).
Another situation would be if you used optimistic locking, and you can somehow restore and automatically combine the two versions of the object. Although I saw this before I cautioned this approach, it can be done for simple objects that can be combined without conflict in 100% of cases.
The logic of most exceptions should be captured at the appropriate level (very important), make sure your system is in a good coordinated state (for example, rollback transactions, closed files, etc.), write it down, tell the user that it does not work.
But I will laugh at this idea and try to give a good framework (well, because it's fun, like the pleasure of a crossword puzzle).
// client code - what you write a lot public class SomeDao { public SomeReturn saveObject( final SomeObject obj ) throws RetryException { Retry<SomeReturn> retry = new Retry<SomeReturn>() { public SomeReturn execute() throws Exception { try { // doSomething return someReturn; } catch( SomeExpectedBadExceptionNotWorthRetrying ex ) { throw new NoRetryException( ex ); // optional exception block } } } return retry.run(); } } // framework - what you write once public abstract class Retry<T> { public static final int MAX_RETRIES = 3; private int tries = 0; public T execute() throws Exception; public T run() throws RetryException { try { return execute(); } catch( NoRetryException ex ) { throw ex; } catch( Exception ex ) { tries++; if( MAX_RETRIES == tries ) { throw new RetryException("Maximum retries exceeded", ex ); } else { return run(); } } } }
chubbsondubs
source share