使用重试2改造的要求 [英] Retrying the request using Retrofit 2
问题描述
我如何添加重试功能,通过改造2 库的要求。是这样的:
service.listItems()排队(新回拨<名单,LT;项目>>(){
@覆盖
公共无效onResponse(响应<名单,LT;项目>>响应){
...
} @覆盖
公共无效onFailure处(的Throwable t)的{
...
}
})retryOnFailure(5 / *倍* /);
我终于做了这样的事情,有兴趣的人士:
1
首先我做了一个抽象类 CallbackWithRetry
公共抽象类CallbackWithRetry< T>实现回调< T> { 私有静态最终诠释TOTAL_RETRIES = 3;
私有静态最后弦乐TAG = CallbackWithRetry.class.getSimpleName();
私人最终呼叫< T>呼叫;
私人INT RetryCount重= 0; 公共CallbackWithRetry(呼叫< T>调用){
this.call =调用;
} @覆盖
公共无效onFailure处(的Throwable t)的{
Log.e(TAG,t.getLocalizedMessage());
如果(RetryCount重++< TOTAL_RETRIES){
Log.v(TAG,重试...(+ RetryCount重+出的+ TOTAL_RETRIES +));
重试();
}
} 私人无效重试(){
。call.clone()排队(本);
}
}
使用这个类,我可以做这样的事情:
serviceCall.enqueue(新CallbackWithRetry<名单,LT;相册和GT;>(serviceCall){
@覆盖
公共无效onResponse(响应<名单,LT;相册和GT;>响应){
...
}
});
2
这是不完全令人满意,因为我必须通过同样的 serviceCall
的两倍。这可以混淆为一个能想到的第二个 serviceCall
(即进入的构造 CallbackWithRetry
)应该或可以是不同的东西从第一个(我们调用它排队
法)
所以,我实现了一个辅助类 CallUtils
:
公共类CallUtils { 公共静态< T>无效enqueueWithRetry(呼叫< T>打电话,最后回调< T>回调){
call.enqueue(新CallbackWithRetry< T>(通话){
@覆盖
公共无效onResponse(响应< T>响应){
callback.onResponse(响应);
} @覆盖
公共无效onFailure处(的Throwable t)的{
super.onFailure(T);
callback.onFailure(T);
}
});
}}
我可以这样使用它:
CallUtils.enqueueWithRetry(serviceCall,新的回调<名单,LT;相册和GT;>(){
@覆盖
公共无效onResponse(响应<名单,LT;相册和GT;>响应){
...
} @覆盖
公共无效onFailure处(的Throwable t)的{
//让下面的方法做重试的工作。
}
});
有了这个,我必须要通过一个标准的回调
到 enqueueWithRetry
方法,它让我实现 onFailure处
(尽管在previous方法我可以实现它太)
这就是我如何已经解决了这个问题。为更好的设计的任何建议将是AP preciated。
How can I add retry functionality to the requests sent by Retrofit 2 library. Something like:
service.listItems().enqueue(new Callback<List<Item>>() {
@Override
public void onResponse(Response<List<Item>> response) {
...
}
@Override
public void onFailure(Throwable t) {
...
}
}).retryOnFailure(5 /* times */);
I finally did something like this, for anyone interested:
1
First I made an abstract class CallbackWithRetry
public abstract class CallbackWithRetry<T> implements Callback<T> {
private static final int TOTAL_RETRIES = 3;
private static final String TAG = CallbackWithRetry.class.getSimpleName();
private final Call<T> call;
private int retryCount = 0;
public CallbackWithRetry(Call<T> call) {
this.call = call;
}
@Override
public void onFailure(Throwable t) {
Log.e(TAG, t.getLocalizedMessage());
if (retryCount++ < TOTAL_RETRIES) {
Log.v(TAG, "Retrying... (" + retryCount + " out of " + TOTAL_RETRIES + ")");
retry();
}
}
private void retry() {
call.clone().enqueue(this);
}
}
Using this class I can do something like this:
serviceCall.enqueue(new CallbackWithRetry<List<Album>>(serviceCall) {
@Override
public void onResponse(Response<List<Album>> response) {
...
}
});
2
This is not completely satisfactory because I have to pass same serviceCall
twice. This can confusing as one can think the second serviceCall
(that goes into constructor of CallbackWithRetry
) should or could be something different from first one (which we invoke enqueue
method on it)
So I implemented a helper class CallUtils
:
public class CallUtils {
public static <T> void enqueueWithRetry(Call<T> call, final Callback<T> callback) {
call.enqueue(new CallbackWithRetry<T>(call) {
@Override
public void onResponse(Response<T> response) {
callback.onResponse(response);
}
@Override
public void onFailure(Throwable t) {
super.onFailure(t);
callback.onFailure(t);
}
});
}
}
And I can use it like this:
CallUtils.enqueueWithRetry(serviceCall, new Callback<List<Album>>() {
@Override
public void onResponse(Response<List<Album>> response) {
...
}
@Override
public void onFailure(Throwable t) {
// Let the underlying method do the job of retrying.
}
});
With this I have to pass a standard Callback
to enqueueWithRetry
method and it makes me implement onFailure
(Though in the previous method I can implement it too)
So this is how I've solved the issue. Any suggestion for a better design would be appreciated.
这篇关于使用重试2改造的要求的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!