拦截器分为:
应用拦截器(addInterceptor)
主要用于查看请求信息及返回信息,如链接地址、头信息、参数信息等
网络拦截器(addNetworkInterceptor)
可以添加、删除或替换请求头信息,还可以改变的请求携带的实体
缓存如字面意思,就是缓存… 有了缓存,你的APP在没有网络的情况下也能正常展示以前缓存过的数据,如果这些数据不需要长期更变,使用缓存可以提高效率,减少与服务器交互产生的流量。
问答小剧场:
问:我添加了缓存,为什么没有网的时候不能读取缓存呢,还是提示网络问题
答:缓存需要某些字段(Cache-Control),如果你正常添加了缓存,并且本地已经有了缓存文件,那就说明缺少这些字段
解决:
1.让服务端添加该字段
2.自己写一个拦截器添加该字段
实际操作:
添加缓存和拦截器都是在OkHttpClient.Builder()的时候,如下:
OkHttpClient client = new OkHttpClient.Builder()
.connectTimeout(10, TimeUnit.SECONDS) //连接超时阈值
.writeTimeout(10, TimeUnit.SECONDS) //写超时阈值
.readTimeout(10, TimeUnit.SECONDS) //读超时阈值
.retryOnConnectionFailure(true) //当失败后重试
.addNetworkInterceptor(new CacheInterceptor())//添加网络拦截器-设置缓存
.addInterceptor(new LoggingInterceptor())//添加应用拦截器-日志拦截器
.cache(new Cache(new File(this.getExternalCacheDir(), "okhttpcache"), 10 * 1024 * 1024))//添加缓存
.build();
Request request = new Request.Builder().url("https://www.wanandroid.com//hotkey/json").build();
这里用的.玩Android.的开放API测试,请求方法就不写了,请求一次,此时添加缓存在手机内存中,打开手机空间
Android - data - 你的APP包名 - cache - okhttpcache
你会发现里面有三个文件,此时说明已经缓存成功了,其中有个 0和1为后缀名的文件,正常打不开,你改成 .txt 后发现里面就是本应当返回的数据内容
CacheInterceptor
class CacheInterceptor implements Interceptor {
@Override
public Response intercept(Chain chain) throws IOException {
Response originResponse = chain.proceed(chain.request());
//设置缓存时间为60秒,并移除了pragma消息头,移除它的原因是因为pragma也是控制缓存的一个消息头属性
return originResponse.newBuilder().removeHeader("pragma")
.header("Cache-Control","max-age=600").build();
}
}
LoggingInterceptor
public class LoggingInterceptor implements Interceptor {
@Override
public Response intercept(Interceptor.Chain chain) throws IOException {
//这个chain里面包含了request和response,所以你要什么都可以从这里拿
Request request = chain.request();
long t1 = System.nanoTime();//请求发起的时间
Log.i("dt",String.format("发送请求 %s on %s%n%s",
request.url(), chain.connection(), request.headers()));
Response response = chain.proceed(request);
long t2 = System.nanoTime();//收到响应的时间
//这里不能直接使用response.body().string()的方式输出日志
//因为response.body().string()之后,response中的流会被关闭,程序会报错,我们需要创建出一
//个新的response给应用层处理
ResponseBody responseBody = response.peekBody(1024 * 1024);
Log.i("dt",String.format("接收响应: [%s] %n返回json:【%s】 %.1fms%n%s",
response.request().url(),
responseBody.string(),
(t2 - t1) / 1e6d,
response.headers()));
return response;
}
}
拦截器写法基本一致,就看你通过哪种方式添加到OKHTTP中了。
以上就是通过网络拦截器添加缓存以及应用拦截器添加请求日志。
感谢这两篇文章让我认识了 拦截器以及缓存
android OkHttp拦截器(Interceptor)的使用
一网打尽OkHttp中的缓存问题