内置条件
概述
Chance
支持大量内置条件,见Chance.Builder
的成员方法。
条件表格
内置条件整理成表格如下:
条件方法 | 功能描述 |
---|---|
withListener | 添加监听器实例,参考高级特性 - 监听器 |
withTimeLimiter | 配置TimeLimiter 组件, 参考TimeLimiter 组件 |
withBlocker | 配置Blocker 组件,参考Blocker 组件 |
withChoice | 添加Choice 组件,参考Choice 组件 |
withWait | 添加Wait 组件,参考Wait 组件 |
withFixedWaitTime | 定义每一轮重试的等待时间为固定时间间隔 |
withRandomWaitTime | 定义每一轮重试的等待时间为随机时间间隔,需要设定随机范围的最小和最大值 |
withIncrementingWaitTime | 定义每一轮重试的等待时间为增长时间间隔,需要设定初始和增长值 |
withExponentialWaitTime | 通过指数退避算法定义每一轮重试的等待的时间间隔,需要设定算法参数 |
withFibonacciWaitTime | 通过斐波那契算法定义每一轮重试的等待的时间间隔,需要设定算法参数 |
withMaxRetryTimes | 定义最大重试次数 |
withRetryForever | 启用永久重试 |
withNeverRetry | 禁止重试 |
withMaxCallingDuration | 限制整个调用重试过程的最大时间间隔 |
withRetryableExceptions | 添加需要重试的异常类型映射 |
withRetryableResult(s) | 添加需要重试的结果集合 |
withRecoverPredicate | 添加恢复条件 |
withRecoverIfHasException | 启用出现异常结果进行恢复条件 |
withAttemptPredicate | 添加重试成功判断条件 |
withRecovery | 添加恢复组件,参考异常恢复 |
用法详解
所有内置条件方法都是通过Chance.Builder
的链式调用进行。例如想要创建一个有下列特性的Chance
:
- 最大重试次数为
3
- 调用目标方法出现
RuntimeException
的时候进行重试 - 调用目标方法返回值为
ERROR
字符串的时候进行重试 - 超过最大重试次数后返回
FALLBACK
字符串作为最终结果
代码如下:
java
public static void main(String[] args) {
Chance<String> chance = Chance.<String, Throwable>newBuilder()
.withMaxRetryTimes(3)
.withRetryableExceptions(Collections.singletonMap(RuntimeException.class, Boolean.TRUE))
.withRetryableResult(r -> Objects.equals("ERROR", r))
.withRecovery(attempt -> "FALLBACK")
.build();
// do something with chance instance
}
@ChanceFor 属性
由于注解的局限性,@ChanceFor
只支持部分内置条件。timeout()
(单位为毫秒)和timeLimiter()
用于定义TimeLimiter
组件,例如:
java
@ChanceFor(timeout = 10, timeLimiter = TimeLimiter.CompletableFutureTimeLimiter.class)
String invokeTimeLimiter();
// 相当于
Chance<String> c = Chance.<String, Throwable>newBuilder()
.withTimeLimiter(TimeLimiter.newCompletableFutureTimeLimiter(), 10, TimeUnit.MILLISECONDS)
.build();
String r = c.call(() -> invokeTimeLimiter());
maxRetryTimes()
用于定义最大重试次数N
,默认值为3
,它的取值有三种情况:
- 取值大于
0
:相当于withMaxRetryTimes(N)
,也就是定义最大重试次数为N
- 取值等于
0
:相当于withNeverRetry()
,也就是禁止重试 - 取值小于
0
:相当于withRetryForever()
,也就是启用永久重试
include()
和exclude()
用于定义需要重试的异常类型映射和禁止重试的异常类型映射,例如:
java
@ChanceFor(
include = {RuntimeException.class},
exclude = {IllegalArgumentException.class}
)
String invokeIncludeAndExclude();
// 相当于
Map<Class<? extends Throwable>, Boolean> map = new HashMap<>();
map.put(RuntimeException.class, Boolean.TRUE);
map.put(IllegalArgumentException.class, Boolean.FALSE);
Chance<String> c = Chance.<String, Throwable>newBuilder()
.withRetryableExceptions(map)
.build();
String r = c.call(() -> invokeIncludeAndExclude());
waits()
方法用于定义@WaitFor
数组,每个@WaitFor
元素对应于一个Wait
组件实现。@WaitFor
注解中定义了WaitType
枚举用于标识Wait
组件类型:
NO
:相当于NoWait
,固定返回0
,也就是不进行等待FIXED
:等效于内置条件中的withFixedWaitTime()
RANDOM
:等效于内置条件中的withRandomWaitTime()
INCREMENTING
:等效于内置条件中的withIncrementingWaitTime()
EXPONENTIAL
:等效于内置条件中的withExponentialWaitTime()
FIBONACCI
:等效于内置条件中的withFibonacciWaitTime()
@WaitFor
注解中的成员变量对应各个Wait
组件的参数映射关系如下:
WaitType | 参数映射 |
---|---|
NO | - |
FIXED | multiplier() -> duration |
RANDOM | multiplier() -> minDuration , maxDuration() -> maxDuration |
INCREMENTING | multiplier() -> initialDuration , maxDuration() -> increasedDuration |
EXPONENTIAL | multiplier() -> multiplier , maxDuration() -> maxDuration |
FIBONACCI | base() -> base , multiplier() -> multiplier , maxDuration() -> maxDuration |
@WaitFor
注解中的custom()
属性用于指定自定义的Wait
组件实现,更多细节参考Wait 组件。listeners()
用于指定监听器类型数组,更多细节参考高级特性 - 监听器。recovery()
用于指定恢复接口Recovery
的实现类,更多细节参考高级特性 - 异常恢复。这里基于@ChanceFor
的使用展示一个相对复杂的例子:
java
@ChanceFor(maxRetryTimes = 0, waits = {
@ChanceFor.WaitFor(type = ChanceFor.WaitType.NO)
})
public interface ChanceApi {
// 继承接口类型的@ChanceFor,关闭重试,并且不进行等待
String type();
// 方法注解,最大重试次数为5,每次重试之间等待random[1000,3000)毫秒
// 方法执行抛出RuntimeException才进行重试
// 方法执行抛出IllegalArgumentException会中断重试马上返回
@ChanceFor(maxRetryTimes = 5, waits = {
@ChanceFor.WaitFor(type = ChanceFor.WaitType.RANDOM, multiplier = 1000, maxDuration = 3000)
}, include = RuntimeException.class, exclude = IllegalArgumentException.class)
String method();
}