Add token to request

After a successful login, subsequent requests generally require the token to be added to the request header to get the correct callback result. Using the Okhttp Interceptor makes this easy

public class TokenInterceptor implements Interceptor {

    private String token;

    public TokenInterceptor(String token) {
        this.token = token;
    }

    public void setToken(String token) {
        this.token = token;
    }

    @Override
    public @NotNull Response intercept(@NotNull Chain chain) throws IOException {
        Request original = chain.request();
        Request.Builder builder = original.newBuilder()
                .header("token", token);
        Request request = builder.build();
        returnchain.proceed(request); }}Copy the code

After successful login:

 TokenInterceptor tokenInterceptor = new TokenInterceptor(token);
        HttpManager.getInstance().addInterper(tokenInterceptor);
Copy the code

Handling after the token becomes invalid

After the token becomes invalid, you can request the current data with a new token. Maybe jump straight to the login page. Both methods need to be able to intercept the token when it expires.

Method 1: Implement the Authenticator interface

public class TokenAuthenticator implements Authenticator {
 
    @Override
    public Request authenticate(Proxy proxy, Response response) throws IOException {
 
        // Fetch the local refreshToken
        String refreshToken = "sssgr122222222";
 
        // Get the new token through a specific interface, where a synchronous Retrofit request is used
        ApiService service = ServiceManager.getService(ApiService.class);
        Call<String> call = service.refreshToken(refreshToken);
 
        // Use retrofit synchronization
        String newToken = call.execute().body();
 
        return response.request().newBuilder()
                .header("token", newToken)
                .build();
    }
 
    @Override
    public Request authenticateProxy(Proxy proxy, Response response) throws IOException {
        return null; }}Copy the code

Since the business has never encountered such a situation of HTTP response 401, it is just reproduced for record. Most of the cases are encountered in mode 2. In the case of HTTP response 200, the custom status code is judged and the token is invalid:

{"data":null."message":"Please log in again."."status":401}
Copy the code
public class TokenInterceptor implements Interceptor { private static final Charset UTF8 = Charset.forName("UTF-8"); @Override public Response intercept(Chain chain) throws IOException { Request request = chain.request(); // try the request Response originalResponse = chain.proceed(request); Originalresponse.body ().string() * {originalResponse.body().string()}} ResponseBody = originalResponse.body(); ResponseBody = originalResponse.body(); BufferedSource source = responseBody.source(); source.request(Long.MAX_VALUE); // Buffer the entire body. Buffer buffer = source.buffer(); Charset charset = UTF8; MediaType contentType = responseBody.contentType(); if (contentType ! = null) { charset = contentType.charset(UTF8); } String bodyString = buffer.clone().readString(charset); LogUtil.debug("body---------->" + bodyString); / * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * / if (the response shows expired token) {/ / judgment according to stipulations and server-side token / / remove the local refreshToken date String refreshToken = "sssgr122222222"; / / through a special interface to get new token, here will use synchronous retrofit request ApiService service = ServiceManager. GetService (ApiService. Class); Call<String> call = service.refreshToken(refreshToken); String newToken = call.execute().body(); // create a new request and modify it accordingly using the new token Request newRequest = request.newBuilder().header("token", newToken) .build(); // retry the request originalResponse.body().close(); return chain.proceed(newRequest); } // otherwise just pass the original response on return originalResponse; }}Copy the code
OkHttpClient client = new OkHttpClient();
client.interceptors().add(new TokenInterceptor());
Retrofit retrofit = new Retrofit.Builder()
        .baseUrl(BASEURL)
        .addConverterFactory(GsonConverterFactory.create(gson))
        .addCallAdapterFactory(RxJavaCallAdapterFactory.create())
        .client(getOkHttpClient())
        .build();
Copy the code

reference

This section describes how to handle token invalidation on Android

Retrofit Refreshes tokens concurrently

Android Network Combat chapter — Token addition, Expiration judgment and Processing (global automatic refresh)