仅当本地缓存的数据早于5分钟时,才进行翻新以从服务器获取新数据 [英] Make retrofit fetch new data from server only if localy cached data is older than 5 minutes
问题描述
仅当本地缓存的数据早于5分钟或不存在时,我才必须让改装客户端从服务器中获取新数据
I have to make my retrofit client fetch new data from the server only if the locally cached data is older than 5 minutes or if it doesn't exist
private fun initRetrofit(){
val retrofit = Retrofit.Builder()
.baseUrl("https://newsapi.org/")
.addConverterFactory(GsonConverterFactory.create())
.build()
val service = retrofit.create(NewsService::class.java)
val call = service.getCurrentNews(
"bbc-news",
"top",
"75702474c08c4c0c96c4081147233679"
)
call.enqueue(object : Callback<NewsResponse> {
override fun onResponse(call: Call<NewsResponse>, response: Response<NewsResponse>) {
if (response.isSuccessful){
val body = response.body()
addDataSet(body!!.articles)
}
}
override fun onFailure(call: Call<NewsResponse>, t: Throwable) {
val alertDialogBuilder = AlertDialog.Builder(this@MainActivity)
alertDialogBuilder.setTitle("Greška")
alertDialogBuilder.setMessage("Ups, došlo je do pogreške.")
alertDialogBuilder.setPositiveButton("U REDU"){ _, _ -> }
alertDialogBuilder.setCancelable(false)
alertDialogBuilder.show()
}
} )
}
上面显示了我当前如何使用改造.我以前使用过okhttpclient和拦截器,但是我不确定应该怎么做.
It is shown above how I am currently using a retrofit. I've used okhttpclient and interceptors before, but I'm not sure how exactly I should do it.
我现在已经弥补了这一点,但是它不能正常工作.
I made up with this now, but it's not working as it shoud.
private fun retrofit(okHttpClient: OkHttpClient) = Retrofit.Builder()
.baseUrl("https://newsapi.org/")
.addConverterFactory(GsonConverterFactory.create())
.client(okHttpClient)
.build()
private fun okHttp(cache: Cache): OkHttpClient {
return OkHttpClient.Builder()
.cache(cache)
.addNetworkInterceptor(CacheInterceptor())
.build()
}
private fun httpCache(application: Application): Cache {
return Cache(application.applicationContext.cacheDir, CACHE_SIZE)
}
class CacheInterceptor : Interceptor {
override fun intercept(chain: Interceptor.Chain): okhttp3.Response {
val request = chain.request()
val originalResponse = chain.proceed(request)
val shouldUseCache = request.header(CACHE_CONTROL_HEADER) != CACHE_CONTROL_NO_CACHE
if(!shouldUseCache) return originalResponse
val cacheControl = CacheControl.Builder()
.maxAge(5, TimeUnit.MINUTES)
.build()
return originalResponse.newBuilder()
.header(CACHE_CONTROL_HEADER, cacheControl.toString())
.build()
}
}
有了所有这些,我只需进行以下改造: val retrofit = retrofit(okHttp(httpCache(application)))
有时工作正常,有时获取数据,但仍然调用 onFailure()
,似乎调用已排队两次,有时只是抛出了 onFailure()
.我不确定他是使用本地缓存还是每次发送请求.
A with all this, I just build retrofit with:
val retrofit = retrofit(okHttp(httpCache(application )))
Sometimes it works fine, sometimes gets data but still call onFailure()
, it seems that call was enqueued twice, and sometimes just throw onFailure()
. I'm am not sure if he is using local cache or is he sending requests every time.
推荐答案
您需要这样的缓存拦截器:
You need cache interceptor like this:
public class CacheInterceptor implements Interceptor {
@Override
public Response intercept(Chain chain) throws IOException {
Response response = chain.proceed(chain.request());
CacheControl cacheControl = new CacheControl.Builder()
.maxAge(5, TimeUnit.MINUTES) // 5 minutes cache
.build();
return response.newBuilder()
.removeHeader("Pragma")
.removeHeader("Cache-Control")
.header("Cache-Control", cacheControl.toString())
.build();
}
}
将此拦截器和 Cache
添加到您的 OkHttpClient
中,如下所示:
Add this interceptor with Cache
to your OkHttpClient
like this:
File httpCacheDirectory = new File(applicationContext.getCacheDir(), "http-cache");
int cacheSize = 10 * 1024 * 1024; // 10 MiB
Cache cache = new Cache(httpCacheDirectory, cacheSize);
OkHttpClient okHttpClient = new OkHttpClient.Builder()
.addNetworkInterceptor(new CacheInterceptor())
.cache(cache)
.build();
这篇关于仅当本地缓存的数据早于5分钟时,才进行翻新以从服务器获取新数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!