Cleanest way to write retry logic?

前端 未结 29 2590
旧巷少年郎
旧巷少年郎 2020-11-22 03:01

Occasionally I have a need to retry an operation several times before giving up. My code is like:

int retries = 3;
while(true) {
  try {
    DoSomething();
         


        
29条回答
  •  太阳男子
    2020-11-22 03:27

    Retry helper: a generic java implementation that contains both returnable and void type retries.

    import java.util.function.Supplier;
    import org.slf4j.Logger;
    import org.slf4j.LoggerFactory;
    
    public class RetryHelper {
      private static final Logger log = LoggerFactory.getLogger(RetryHelper.class);
      private int retryWaitInMS;
      private int maxRetries;
    
      public RetryHelper() {
        this.retryWaitInMS = 300;
        this.maxRetries = 3;
      }
    
      public RetryHelper(int maxRetry) {
        this.maxRetries = maxRetry;
        this.retryWaitInMS = 300;
      }
    
      public RetryHelper(int retryWaitInSeconds, int maxRetry) {
        this.retryWaitInMS = retryWaitInSeconds;
        this.maxRetries = maxRetry;
      }
    
      public  T retryAndReturn(Supplier supplier) {
        try {
          return supplier.get();
        } catch (Exception var3) {
          return this.retrySupplier(supplier);
        }
      }
    
      public void retry(Runnable runnable) {
        try {
          runnable.run();
        } catch (Exception var3) {
          this.retrySupplier(() -> {
            runnable.run();
            return null;
          });
        }
    
      }
    
      private  T retrySupplier(Supplier supplier) {
        log.error("Failed , will be retried " + this.maxRetries + " times.");
        int retryCounter = 0;
    
        while(retryCounter < this.maxRetries) {
          try {
            return supplier.get();
          } catch (Exception var6) {
            ++retryCounter;
            log.error(" failed on retry: " + retryCounter + " of " + this.maxRetries + " with error: " + var6.getMessage());
            if (retryCounter >= this.maxRetries) {
              log.error("Max retries exceeded.");
              throw var6;
            }
    
            try {
              Thread.sleep((long)this.retryWaitInMS);
            } catch (InterruptedException var5) {
              var5.printStackTrace();
            }
          }
        }
    
        return supplier.get();
      }
    
      public int getRetryWaitInMS() {
        return this.retryWaitInMS;
      }
    
      public int getMaxRetries() {
        return this.maxRetries;
      }
    }
    
    

    Usage:

        try {
          returnValue = new RetryHelper().retryAndReturn(() -> performSomeTask(args));
          //or no return type:
          new RetryHelper().retry(() -> mytask(args));
        } catch(Exception ex){
          log.error(e.getMessage());
          throw new CustomException();
        }
    

提交回复
热议问题