Android Retrofit OkHttp Offline Caching With Examples

In this tutorial, we’ll be discussing and implementing Offline caching in our android application.

We’ll be using Retrofit and Okhttp libraries.

Offline Caching

Opening your application with no internet and seeing no previous data is a very common occurrence.
Two ways to deal with loading network requests that come first to our minds are:

Using either of them comes with its fair share of cons (and more code to write).

While Adding Data in SharedPreferences is easy. It’s time-consuming to retrieve the required data. Plus scalability is an issue.

SQLite with tables makes it hard to do many changes in the future. Plus SQLite operations are heavy.

Why use both when OkHtttp caches the HTTP responses built-in?

Caching Requests

We know that OkHttp is the default HttpClient for Retrofit.
OkHttp comes with a powerful component Interceptors.

Interceptors are generally of two types:

  • Application Interceptors – Gets you the final response.
  • Network Interceptors – To intercept intermediate requests.

Using Interceptors you can read and modify the requests. And obviously, we’ll add Cache control on the responses.

Cache-control is an header used to specify caching policies in client requests and server responses.

You cannot cache POST requests. Only GET requests can be cached.

Inside the interceptors, you need to get chain.request() to get the current request and add Cache options to it.

For example, we can add a header “Cache-Control” to the request as: "public, only-if-cached, max-stale=60"

Then do a chain.proceed(request) to proceed with the modified request to return the response.

max-age vs max-stale

max-age is the oldest limit ( lower limit) till which the response can be returned from the cache.
max-stale is the highest limit beyond which cache cannot be returned.

In the following section, we’ll do a Retrofit Request with OkHttp as the Client and using RxJava.
We’ll cache the requests such that they can be displayed the next time if there is no internet/problem in getting the latest request.

Project Structure

android-retrofit-offline-caching-project

The app‘s build.gradle is given below:

Code

The code for the activity_main.xml layout is given below:

The code for the APIService.java is given below:

The code for the Jokes.java model class is given below:

The code for the MainActivity.java is given below:

The order of the interceptors in the OkHttpClient Builder is important.
The addNetworkInterceptor adds the cache control to the request.

In the addInterceptor, provideOfflineCacheInterceptor is called. If there is an exception which would typically be a ConnectException or a NoRouteFoundException, the request is retried again, this time with a header to get the response from the Cache.

Alternatively, you can set the cache in the header as:

It’s a good practice to add removeHeader("Pragma").

The output of the above application in action is given below:

android retrofit offline caching output

So we’ve disabled the wifi on our device after the first Retrofit Request.
And we are still able to load the response from the Http Cache.

This brings an end to this tutorial. You can download the project from the link below:

By admin

Leave a Reply