Guava-Retrying實現重試機制

在接口調用中由於各種原因,可能會重置失敗的任務,使用Guava-Retrying可以方便的實現重試功能。

首先,需要引用Guava-Retrying的包

		<dependency>
			<groupId>com.github.rholder</groupId>
			<artifactId>guava-retrying</artifactId>
			<version>2.0.0</version>
		</dependency>

代碼示例:

public class RetryDemo {
	
	public static void main(String[] args) {
		Retryer<Boolean> retryer = RetryerBuilder.<Boolean>newBuilder().
				//如果異常會重試
				retryIfException().
				//如果結果爲false會重試
				retryIfResult(Predicates.equalTo(false)).
				//重調策略
				withWaitStrategy(WaitStrategies.fixedWait(10, TimeUnit.SECONDS)).
				//嘗試次數
				withStopStrategy(StopStrategies.stopAfterAttempt(3)).
				//註冊監聽
				withRetryListener(new MyRetryListener()).build();
		try {
			retryer.call(new TaskCallable());
		} catch (Exception e) {
			e.printStackTrace();
		}	
	}

}

其中TaskCallable是任務的具體實現類,它實現了Callable接口

public class TaskCallable implements Callable<Boolean>{

	public Boolean call() throws Exception {
		return false;
	}
}

另外,MyRetryListener監聽實現了RetryListener接口,每次重試都會回調註冊的監聽

public class MyRetryListener implements RetryListener {

	public <V> void onRetry(Attempt<V> attempt) {
		System.out.print("[retry]time=" + attempt.getAttemptNumber());
		// 距離第一次重試的延遲
		System.out.print(",delay=" + attempt.getDelaySinceFirstAttempt());

		// 重試結果: 是異常終止, 還是正常返回
		System.out.print(",hasException=" + attempt.hasException());
		System.out.print(",hasResult=" + attempt.hasResult());

		// 是什麼原因導致異常
		if (attempt.hasException()) {
			System.out.print(",causeBy=" + attempt.getExceptionCause().toString());
		} else {
			// 正常返回時的結果
			System.out.print(",result=" + attempt.getResult());
		}
		System.out.println();
	}

}

執行一下main方法,可以看到執行的結果:

[retry]time=1,delay=0,hasException=false,hasResult=true,result=false
[retry]time=2,delay=10001,hasException=false,hasResult=true,result=false
[retry]time=3,delay=20002,hasException=false,hasResult=true,result=false
com.github.rholder.retry.RetryException: Retrying failed to complete successfully after 3 attempts.
	at com.github.rholder.retry.Retryer.call(Retryer.java:174)
	at org.thinking.java.base.guava.retrying.RetryDemo.main(RetryDemo.java:26)

下面詳細分析一下:

RetryerBuilder是一個factory創建者,可以定製設置重試源且可以支持多個重試源,可以配置重試次數或重試超時時間,以及可以配置等待時間間隔,創建重試者Retryer實例。

RetryerBuilder的重試源支持Exception異常對象 和自定義斷言對象,通過retryIfException 和retryIfResult設置,同時支持多個且能兼容。
retryIfException,拋出runtime異常、checked異常時都會重試,但是拋出error不會重試。
retryIfRuntimeException只會在拋runtime異常的時候才重試,checked異常和error都不重試。
retryIfExceptionOfType允許我們只在發生特定異常的時候才重試,比如NullPointerException和IllegalStateException都屬於runtime異常,也包括自定義的error

retryIfResult可以指定你的Callable方法在返回值的時候進行重試

StopStrategy:停止重試策略,提供三種:
StopAfterDelayStrategy 設定一個最長允許的執行時間;比如設定最長執行10s,無論任務執行次數,只要重試的時候超出了最長時間,則任務終止,並返回重試異常RetryException。
NeverStopStrategy 不停止,用於需要一直輪訓知道返回期望結果的情況。

StopAfterAttemptStrategy 設定最大重試次數,如果超出最大重試次數則停止重試,並返回重試異常。

WaitStrategy:等待時長策略(控制時間間隔),返回結果爲下次執行時長:
FixedWaitStrategy 固定等待時長策略。
RandomWaitStrategy 隨機等待時長策略(可以提供一個最小和最大時長,等待時長爲其區間隨機值)。
IncrementingWaitStrategy 遞增等待時長策略(提供一個初始值和步長,等待時間隨重試次數增加而增加)。
ExponentialWaitStrategy 指數等待時長策略。
FibonacciWaitStrategy Fibonacci 等待時長策略。
ExceptionWaitStrategy 異常時長等待策略。
CompositeWaitStrategy 複合時長等待策略。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章