RX Java-重试引发异常的代码

RX Java-重试引发异常的代码,java,error-handling,rx-java,observable,exponential-backoff,Java,Error Handling,Rx Java,Observable,Exponential Backoff,我正在尝试使用RXJava来使用来自不断发送对象的源的一些数据 我想知道如何为我自己的代码引发异常的情况实现重试策略。例如,网络异常应使用指数退避策略触发重试 一些代码: message.map(this::processMessage) .subscribe((message)->{ //do something after mapping }); processMessag

我正在尝试使用RXJava来使用来自不断发送对象的源的一些数据

我想知道如何为我自己的代码引发异常的情况实现重试策略。例如,网络异常应使用指数退避策略触发重试

一些代码:

 message.map(this::processMessage)
                 .subscribe((message)->{
                     //do something after mapping
                 });
processMessagemessage是一种包含可能失败的风险代码的方法,它是我想重试的代码部分,但我不想阻止可观察对象使用源数据


对此有何想法?

以以下文章为例:


有一天他们帮助了我。

以文章为例:

message
    .map(this::processMessage)
    .retryWhen(errors -> errors.flatMap(error -> {  
        if (error instanceof IOException) {
          return Observable.just(null);
        }
        // For anything else, don't retry
        return Observable.error(error);
     })
     .subscribe(
         System.out::println,
         error -> System.out.println("Error!")
     );
有一天他们帮助了我

message
    .map(this::processMessage)
    .retryWhen(errors -> errors.flatMap(error -> {  
        if (error instanceof IOException) {
          return Observable.just(null);
        }
        // For anything else, don't retry
        return Observable.error(error);
     })
     .subscribe(
         System.out::println,
         error -> System.out.println("Error!")
     );
或者抓住错误

message.map(this::processMessage)
           .onErrorReturn(error -> "Empty result")
           .subscribe((message)->{})
或处理错误

message
    .map(this::processMessage)
    .doOnError(throwable -> Log.e(TAG, "Throwable " + throwable.getMessage()))
    .subscribe(
         System.out::println,
         error -> System.out.println("Error!")
     );
未测试,但retryWhen与repeatWhen不同,这不仅在onComplete中调用

->每个错误都是平面映射的,因此我们可以返回onNextnull来触发重新订阅,也可以返回onErrorerror来避免重新订阅

退避政策:

source.retryWhen(errors ->  
  errors
    .zipWith(Observable.range(1, 3), (n, i) -> i)
    .flatMap(retryCount -> Observable.timer((long) Math.pow(5, retryCount), TimeUnit.SECONDS))
);
在这种情况下,flatMap+定时器优于延迟,因为它允许我们通过重试次数修改延迟。上述重试三次,每次重试延迟5^retryCount,只需少量操作员即可实现指数级退避

或者抓住错误

message.map(this::processMessage)
           .onErrorReturn(error -> "Empty result")
           .subscribe((message)->{})
或处理错误

message
    .map(this::processMessage)
    .doOnError(throwable -> Log.e(TAG, "Throwable " + throwable.getMessage()))
    .subscribe(
         System.out::println,
         error -> System.out.println("Error!")
     );
未测试,但retryWhen与repeatWhen不同,这不仅在onComplete中调用

->每个错误都是平面映射的,因此我们可以返回onNextnull来触发重新订阅,也可以返回onErrorerror来避免重新订阅

退避政策:

source.retryWhen(errors ->  
  errors
    .zipWith(Observable.range(1, 3), (n, i) -> i)
    .flatMap(retryCount -> Observable.timer((long) Math.pow(5, retryCount), TimeUnit.SECONDS))
);

在这种情况下,flatMap+定时器优于延迟,因为它允许我们通过重试次数修改延迟。上述重试三次,每次重试延迟5^retryCount,只需少量操作员即可实现指数级退避

最近,我开发了完全适合您需要的库


如果您将指数策略与backupObservable相结合,您将获得预期的结果。

最近,我开发了完全适合您需要的库


如果您将指数策略与backupObservable相结合,您将获得预期的结果。

您的建议不包括任何重复失败代码的逻辑。此外,如果使用OneRorReturn,可观察对象将停止使用新值。关于指数退避策略的内容?已修改。应该能解决你的问题。如果不只是注释,那么我将提供一个工作代码。您的建议不包括任何重复失败代码的逻辑。此外,如果使用OneRorReturn,可观察对象将停止使用新值。关于指数退避策略的内容?已修改。应该能解决你的问题。如果不只是评论,那么我将提供一个工作代码。酷项目,但我不使用改装或http。我有一个来自RabbitMQ的恒定提要,可观察的响应就是这个。因此,代码可能是您试图实现的目标的基础。很酷的项目,但我没有使用改型或http。我有一个来自RabbitMQ的恒定提要,可观察的响应就是这个提要。因此,代码可能是您试图实现的目标的基础。