Search code examples
javaandroidretrofit

How to setup timeout dynamically with retrofit2?


public class Router {

    ...

    private static Retrofit retrofit = null;

    ...

    public Retrofit getRetrofit() {
        if (retrofit == null) {

            ...

            OkHttpClient client = new OkHttpClient.Builder()
                    .connectTimeout(30, TimeUnit.SECONDS)
                    .writeTimeout(60, TimeUnit.SECONDS)
                    .readTimeout(60, TimeUnit.SECONDS)
                    .build();

            retrofit = new Retrofit.Builder()
                    .baseUrl("***")
                    .addConverterFactory(GsonConverterFactory.create())
                    .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
                    .client(client)
                    .build();
        }
        return retrofit;
    }

    ...

}

I setup timeout in OkHttpClient. Now there is a API needs different timeout.

How can i do?

Is there something like this?

@Timeout
Observable<ResponseBody> exapmle(@Timeout("connect") int connect
 , @Timeout("read") int read
 , @Timeout("write") int write);

Solution

  • enter image description here

    Thanks a lot.

    here is my code:

    public static final String CONNECT_TIMEOUT = "CONNECT_TIMEOUT";
    public static final String READ_TIMEOUT = "READ_TIMEOUT";
    public static final String WRITE_TIMEOUT = "WRITE_TIMEOUT";
    
    ...
    
    Interceptor timeoutInterceptor = new Interceptor() {
        @Override
        public Response intercept(Chain chain) throws IOException {
            Request request = chain.request();
    
            int connectTimeout = chain.connectTimeoutMillis();
            int readTimeout = chain.readTimeoutMillis();
            int writeTimeout = chain.writeTimeoutMillis();
    
            String connectNew = request.header(CONNECT_TIMEOUT);
            String readNew = request.header(READ_TIMEOUT);
            String writeNew = request.header(WRITE_TIMEOUT);
    
            if (!TextUtils.isEmpty(connectNew)) {
                connectTimeout = Integer.valueOf(connectNew);
            }
            if (!TextUtils.isEmpty(readNew)) {
                readTimeout = Integer.valueOf(readNew);
            }
            if (!TextUtils.isEmpty(writeNew)) {
                writeTimeout = Integer.valueOf(writeNew);
            }
    
            return chain
                    .withConnectTimeout(connectTimeout, TimeUnit.MILLISECONDS)
                    .withReadTimeout(readTimeout, TimeUnit.MILLISECONDS)
                    .withWriteTimeout(writeTimeout, TimeUnit.MILLISECONDS)
                    .proceed(request);
        }
    };
    
    OkHttpClient httpClient = new OkHttpClient.Builder()
            .connectTimeout(DEFAULT_CONNECT_TIMEOUT, TimeUnit.MILLISECONDS)
            .writeTimeout(DEFAULT_WRITE_TIMEOUT, TimeUnit.MILLISECONDS)
            .readTimeout(DEFAULT_READ_TIMEOUT, TimeUnit.MILLISECONDS)
            .addInterceptor(timeoutInterceptor)
            .build();
    
    retrofit = new Retrofit.Builder()
            .baseUrl(Host.Develop.ACCOUNT_HOST)
            .addConverterFactory(GsonConverterFactory.create())
            .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
            .client(httpClient)
            .build();
    
    ...
    

    example usage:

    /**
     * check account status
     *
     * @param account
     * @return
     */
    @Headers({"CONNECT_TIMEOUT:10000", "READ_TIMEOUT:10000", "WRITE_TIMEOUT:10000"})
    @GET("login/prelogin")
    Observable<ResponseBody> preLogin(@Query("account") String account);
    

    or

    /**
     * check account status
     * 
     * @param connectTimeout
     * @param readTimeout
     * @param writeTimeout
     * @param account
     * @return
     */
    @GET("login/prelogin")
    Observable<ResponseBody> preLogin(
            @Header("CONNECT_TIMEOUT") String connectTimeout,
            @Header("READ_TIMEOUT") String readTimeout,
            @Header("WRITE_TIMEOUT") String writeTimeout,
            @Query("account") String account);