我有这个代码尝试连接到xmpp服务器。一切正常,除了在最后尝试连接的尝试,onError没有在订阅者上调用,根据文档,它应该。我做错了什么?
@Override
public void connect(final AbstractXMPPConnection connection) {
Observable.<AbstractXMPPConnection>create(subscriber -> {
try {
connection.connect();
} catch (SmackException | IOException | XMPPException e) {
e.printStackTrace();
subscriber.onError(e);
}
})
.retryWhen(attempts -> attempts.zipWith(Observable.range(1, 4), (n, i) -> i).flatMap(i -> {
return Observable.timer(i, TimeUnit.SECONDS);
}))
.subscribeOn(Schedulers.newThread())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Subscriber<AbstractXMPPConnection>() {
@Override
public void onCompleted() {
}
@Override
public void onError(Throwable e) {
if (callback != null)
callback.onFailedConnecting();
}
@Override
public void onNext(AbstractXMPPConnection conn) {
if (callback != null)
callback.onConnected();
}
});
}
TLDR:在最后一次尝试时,应该调用public void onError,它不是
答案 0 :(得分:1)
你有:
.retryWhen(attempts -> attempts.zipWith(Observable.range(1, 4), (n, i) -> i).flatMap(i -> {
return Observable.timer(i, TimeUnit.SECONDS);
}))
此代码永远不会发出错误,因此它将以指数方式(Timer)重试但永远不会失败。因此永远不会调用onError()。
如果你想捕获错误,你需要通过显式的Observable.error()从retryWhen传递它,或者删除retryWhen部分。 :)
答案 1 :(得分:0)
我这样做了(Scala,RxScala):
.retryWhen(_
.zipWith(Observable.just(1, 2, 3, -1))((t, i) => (t, i))
.flatMap( tuple => tuple match {
case (t, -1) => Observable.error(t)
case (t, i) => Observable.timer(i seconds)
}))
可能存在某种zipWith
运算符,它使用第一个非对元素调用onError
。这将是很好的