You can add a cache to an OkHttpClient which will work according to the various cache-related HTTP header like cache-control:
val okHttpClient =
    OkHttpClient.Builder().apply {
        cache(Cache(File("http_cache"), 50 * 1024 * 1024))
    }.build()  
There is a resource for which the server (which is not controlled by me) specifies cache-control: no-cache in the response. But I want to cache it anyway, because I know that under certain circumstances it is safe to do so.
I thought I could intercept the response and set headers accordingly:
val okHttpClient =
    OkHttpClient.Builder().apply {
        cache(Cache(File("http_cache"), 50 * 1024 * 1024))
        addInterceptor { chain ->
            val response = chain.proceed(chain.request())
            response
                .newBuilder()
                .header("cache-control", "max-age=1000") // Enable caching
                .removeHeader("pragma")  // Remove any headers that might conflict with caching
                .removeHeader("expires") // ...
                .removeHeader("x-cache") // ...
                .build()
        }
    }.build()
Unfortunately, this does not work. Apparently, the caching decisions are made before the interceptor intercepts. Using addNetworkInterceptor() instead of addInterceptor() does not work either.
The opposite - disabling caching when the server allows it by setting cache-control: no-cache - also does not work.
Edit:
Yuri's answer is correct. addNetworkInterceptor() with .header("Cache-Control", "public, max-age=1000") works, and .header("cache-control", "max-age=1000") also works.
But when running my experiments, I had made some false assumptions. This is what I found out later:
- The OkHttp cache does not cache responses for POST requests at all. (Source)
- "Note that no-cachedoes not mean "don't cache".no-cacheallows caches to store a response, but requires them to revalidate it before reuse. If the sense of "don't cache" that you want is actually "don't store", thenno-storeis the directive to use." (Source)
 
    