RxJava2 - 如何每次重试,除非它是 TimeoutException?
RxJava2 - How to retry everytime except if it's TimeoutException?
我有一个 Observables
链,在链的最后,我正在通过蓝牙向设备写入命令,我正在等待通知。有一种情况,它可以永远在这里等待,所以我想使用 timeout
- 简单。
但问题是,每次出现任何其他问题时我都想 retry
,只有当 timeout
发生时才应该终止它 - 否则它应该 retry
。此外,如果我们沿着链向下,我们将遇到也应该具有相同行为的其他重试。超时异常应该被推回到更高层(在我的例子中是交互器)。
我考虑过 retryWhen
但我不确定在那种情况下如何正确使用它。
.retryWhen { it.filter { throwable -> throwable !is TimeoutException } }
此外,很难为此编写测试,因此我更难找到正确的解决方案。
请尝试以下我在我的项目中使用的方法。
创建一个class(这是一个java class如果需要你可以把它改成kotlin)
public class RetryWithDelay implements Function<Observable<? extends Throwable>, Observable<?>> {
private static final String TAG = "RetryWithDelay";
private final int maxRetries;
private final int retryDelayInMinutes;
private int retryCount;
public RetryWithDelay(final int maxRetries, final int retryDelayInMinutes) {
this.maxRetries = maxRetries;
this.retryDelayInMinutes = retryDelayInMinutes;
this.retryCount = 0;
}
@Override
public Observable<?> apply(Observable<? extends Throwable> attempts) {
return attempts.flatMap(new Function<Throwable, Observable<?>>() {
@Override
public Observable<?> apply(Throwable throwable) {
if (throwable instanceof TimeoutException) {
return Observable.error(throwable);
}
if (++retryCount < maxRetries) {
// When this Observable calls onNext, the original
// Observable will be retried (i.e. re-subscribed).
return Observable.timer(retryDelayInMinutes, TimeUnit.MINUTES);
}
// Max retries hit. Just pass the error along.
return Observable.error(throwable);
}
});
}}
在 apply 方法中,它会检查异常是否是 TimeOut 的实例,它会抛出错误,否则它会不断重试您想要的 maxRetries。
并按如下方式传递 class
.retryWhen (new RetyWithDelay(3,5))
每 5 分钟重试 3 次。
我有一个 Observables
链,在链的最后,我正在通过蓝牙向设备写入命令,我正在等待通知。有一种情况,它可以永远在这里等待,所以我想使用 timeout
- 简单。
但问题是,每次出现任何其他问题时我都想 retry
,只有当 timeout
发生时才应该终止它 - 否则它应该 retry
。此外,如果我们沿着链向下,我们将遇到也应该具有相同行为的其他重试。超时异常应该被推回到更高层(在我的例子中是交互器)。
我考虑过 retryWhen
但我不确定在那种情况下如何正确使用它。
.retryWhen { it.filter { throwable -> throwable !is TimeoutException } }
此外,很难为此编写测试,因此我更难找到正确的解决方案。
请尝试以下我在我的项目中使用的方法。
创建一个class(这是一个java class如果需要你可以把它改成kotlin)
public class RetryWithDelay implements Function<Observable<? extends Throwable>, Observable<?>> {
private static final String TAG = "RetryWithDelay";
private final int maxRetries;
private final int retryDelayInMinutes;
private int retryCount;
public RetryWithDelay(final int maxRetries, final int retryDelayInMinutes) {
this.maxRetries = maxRetries;
this.retryDelayInMinutes = retryDelayInMinutes;
this.retryCount = 0;
}
@Override
public Observable<?> apply(Observable<? extends Throwable> attempts) {
return attempts.flatMap(new Function<Throwable, Observable<?>>() {
@Override
public Observable<?> apply(Throwable throwable) {
if (throwable instanceof TimeoutException) {
return Observable.error(throwable);
}
if (++retryCount < maxRetries) {
// When this Observable calls onNext, the original
// Observable will be retried (i.e. re-subscribed).
return Observable.timer(retryDelayInMinutes, TimeUnit.MINUTES);
}
// Max retries hit. Just pass the error along.
return Observable.error(throwable);
}
});
}}
在 apply 方法中,它会检查异常是否是 TimeOut 的实例,它会抛出错误,否则它会不断重试您想要的 maxRetries。
并按如下方式传递 class
.retryWhen (new RetyWithDelay(3,5))
每 5 分钟重试 3 次。