2017-07-31 50 views
0

我是新来的android编程和改造,我做了一个示例应用程序,我必须使用访问令牌进行两个并行网络调用。 当访问令牌过期并返回401状态码时,如果我看到401 HTTP状态码,我必须使用此访问令牌进行刷新刷新调用,但是并行调用的问题是它导致刷新竞争条件刷新令牌是否有避免这种情况的最佳方法,以及如何智能地刷新令牌而没有任何冲突。当响应未授权重试最后一次失败的请求与他们处理背景刷新令牌调用改进并行网络调用

回答

2

OkHttp会自动询问凭据身份验证

public class TokenAuthenticator implements Authenticator { 
    @Override 
    public Request authenticate(Proxy proxy, Response response) throws IOException { 
     // Refresh your access_token using a synchronous api request 
     newAccessToken = service.refreshToken(); 

     // Add new header to rejected request and retry it 
     return response.request().newBuilder() 
      .header(AUTHORIZATION, newAccessToken) 
      .build(); 
    } 

    @Override 
    public Request authenticateProxy(Proxy proxy, Response response) throws IOException { 
     // Null indicates no attempt to authenticate. 
     return null; 
    } 

连接的验证器OkHttpClient你做拦截

OkHttpClient okHttpClient = new OkHttpClient(); 
okHttpClient.setAuthenticator(authAuthenticator); 

使用此客户端创建改造RestAdapter时

RestAdapter restAdapter = new RestAdapter.Builder() 
      .setEndpoint(ENDPOINT) 
      .setClient(new OkClient(okHttpClient)) 
      .build(); 
return restAdapter.create(API.class); 

选中此相同的方式:Fore more details visit this link

0

尝试拨打队列,如刷新令牌操作:

class TokenProcessor { 
    private List<Listener> queue = new List<Listener>(); 
    private final Object synch = new Object(); 
    private State state = State.None; 
    private String token; 
    private long tokenExpirationDate; 

    public void getNewToken(Listener listener){ 
     synchronized(synch) { 

      // check token expiration date 
      if (isTokenValid()){ 
       listener.onSuccess(token); 
       return; 
      } 
      queue.add(listener); 

      if (state != State.Working) { 
       sendRefreshTokenRequest(); 
      } 
     } 
    } 
    private void sendRefreshTokenRequest(){ 
     // get token from your API using Retrofit 
     // on the response call onRefreshTokenLoaded() method with the token and expiration date 
    } 
    private void onRefreshTokenLoaded(String token, long expirationDate){ 
     synchronized(synch){ 
      this.token = token; 
      this.tokenExpirationDate = expirationDate; 

      for(Listener listener : queue){ 
       try { 
        listener.onTokenRefreshed(token); 
       } catch (Throwable){} 
      } 
      queue.clear();     
     } 
    } 
} 

这是一个示例代码,它是如何实现的。