Android 将所有正在进行的请求放入队列改造和okhttp
我正在使用Android 将所有正在进行的请求放入队列改造和okhttp,android,retrofit,retrofit2,okhttp,Android,Retrofit,Retrofit2,Okhttp,我正在使用OKHttp的身份验证程序,如果出现401状态错误,它将重试获取新的访问令牌,但我的应用程序必须同时调用多个API,导致数据损坏,因为现有的刷新令牌将在请求时被删除,但另一个API调用方仍然依赖于此令牌来使用。所以我的问题是:当我们得到401错误状态代码时,是否有必要将请求放入队列(或者至少取消)所有其他api请求 这是我的验证器: public Request authenticate(Route route, Response response) throws IOExcepti
OKHttp
的身份验证程序
,如果出现401
状态错误,它将重试获取新的访问令牌,但我的应用程序必须同时调用多个API,导致数据损坏,因为现有的刷新令牌将在请求时被删除,但另一个API调用方仍然依赖于此令牌来使用。所以我的问题是:当我们得到401错误状态代码时,是否有必要将请求放入队列(或者至少取消)所有其他api请求
这是我的验证器:
public Request authenticate(Route route, Response response) throws IOException {
// Refresh your access_token using a synchronous api request
access_token = getNewAccessTokenHere();
// Add new header to rejected request and retry it
return response.request().newBuilder()
.header("Authorization", "Bearer " + access_token)
.build();
} else {
ToastUtil.toast("login again");
return null;
}
}
我的目标是让其他api等待第一个请求的响应,并使用新的访问令牌。您可以使用
调度程序来访问所有飞行中的呼叫并取消它们
我知道这个问题已经很老了,但最近我发现自己也遇到了同样的问题,我找到了一个对我有效的解决方案,我相信它可以在同样的情况下帮助其他人
如所述,将a连接到OkHttp客户端并限制max请求量的解决方案似乎不适用于开箱即用的改造
因此,我的解决方案是同步我自定义的authenticate方法,对我的singleton翻新实例进行并发调用,直到每个线程的authenticate例程完成。这样,具有未经授权响应的第一个调用可以刷新令牌,并通知下一个调用(也得到未经授权的响应),新的访问令牌已经可用
public class MyAuthenticator implements Authenticator {
private boolean isRefreshed = false;
// Call when a new request is being made. Concurrent request should call this method to enable the refresh routine
public void newRequest(){
isRefreshed = false;
}
@Nullable
@Override
public synchronized Request authenticate(@NonNull Route route, @NonNull Response response) throws IOException { // Synchronize the method to avoid refreshing thread overlapping
if (responseCount(response) > 3) {
return null;
}
if (!isRefreshed){
// Refresh your access_token using a synchronous api request
String accessToken = getNewAccessTokenHere();
// Saves the new access token
saveNewAccessToken(accessToken);
isRefreshed = true;
// Add new header to rejected request and retry it
return response.request().newBuilder()
.removeHeader("Authorization") // removes the old header, avoiding duplications
.addHeader("Authorization", "Bearer " + accessToken)
.build();
}
else{ // Access token already refreshed so retry with the new one
// Get the saved access token
String accessToken = getAccessToken();
return response.request()
.newBuilder()
.removeHeader("Authorization")
.addHeader("Authorization", accessToken)
.build();
}
}
private int responseCount(Response response) {
int result = 1;
while ((response = response.priorResponse()) != null) {
result++;
}
return result;
}
}我们是否必须将所有其他请求放入队列中,以便稍后重试?另外,我是否可以在authenticator中创建新的调度器,如下所示:dispatcher dp=new dispatcher()代码>?从何处调用newRequest()?