android okhttp 緩存設(shè)置

緩存第一步就是要保存 response 數(shù)據(jù)到緩存文件中齿尽,oktthp 用的是 DiskLruCache 會(huì)緩存到文件中鬼吵。


cache.png
// 緩存路徑- app 緩存目錄
File file = new File(getCacheDir(), "bbb");
Cache cache = new Cache(file,
        10 * 1024 * 1024); // 10 MB

OkHttpClient.Builder builder = new OkHttpClient.Builder()
        .addNetworkInterceptor(new Interceptor() {
            @Override
            public Response intercept(Chain chain) throws IOException {
                Response response = chain.proceed(chain.request());

                // 緩存 10 秒
                CacheControl cacheControl = new CacheControl.Builder()
                        .maxAge(10, TimeUnit.SECONDS)
                        .build();

                return response.newBuilder()
                        .removeHeader("Pragma")
                        .header("Cache-Control", cacheControl.toString())
                        .build();
            }
        })
        .cache(cache);

通過(guò) addNetworkInterceptor 添加網(wǎng)絡(luò)攔截器修改 response 設(shè)置 cacheControl项炼,cacheControl 頭部就是服務(wù)器告訴瀏覽器緩存的規(guī)則揭厚。這里通過(guò) maxAge 參數(shù)設(shè)置緩存最大 10 秒內(nèi)有效但绕。

如果要實(shí)現(xiàn)無(wú)網(wǎng)絡(luò)時(shí)從緩存讀染却蕖(如果有的話)惶看,有網(wǎng)絡(luò)時(shí)緩存 10 秒怎么做?六孵?纬黎?

OkHttpClient.Builder builder = new OkHttpClient.Builder()
        .addInterceptor(new Interceptor() {
            @Override
            public Response intercept(Chain chain) throws IOException {
                Request request = chain.request();
                if (!isNetworkConnected()) {
                    // 無(wú)網(wǎng)絡(luò)時(shí)強(qiáng)制從緩存讀取,如果緩存中沒有數(shù)據(jù)會(huì)返回 504
                    // FORCE_CACHE 里設(shè)置了 only-if-cached=true 和 maxStale
                    // only-if-cached 顧名思義就是只有緩存中有數(shù)據(jù)才返回劫窒,沒有時(shí)返回 504
                    // maxStale 指可以取過(guò)期多久的數(shù)據(jù)本今,F(xiàn)ORCE_CACHE 中設(shè)置為了Int最大值
                    request = request.newBuilder()
                            .cacheControl(CacheControl.FORCE_CACHE)
                            .build();
                }
                return chain.proceed(request);
            }
        })
        .addNetworkInterceptor(new Interceptor() {
            @Override
            public Response intercept(Chain chain) throws IOException {
                Response response = chain.proceed(chain.request());

                // 緩存 10 秒
                CacheControl cacheControl = new CacheControl.Builder()
                        .maxAge(10, TimeUnit.SECONDS)
                        .build();

                return response.newBuilder()
                        .removeHeader("Pragma")
                        .header("Cache-Control", cacheControl.toString())
                        .build();
            }
        })
        .cache(cache);

網(wǎng)絡(luò)緩存那不用動(dòng),通過(guò) addInterceptor 添加攔截器判斷是否有網(wǎng)絡(luò)主巍,沒有網(wǎng)絡(luò)時(shí)修改 request 添加 CacheControl.FORCE_CACHE 強(qiáng)制客戶端從緩存中讀取

如果要求無(wú)網(wǎng)絡(luò)時(shí)從緩存讀裙谙ⅰ(如果有的話),有網(wǎng)絡(luò)時(shí)從網(wǎng)絡(luò)獲取怎么做孕索?铐达?只需要在網(wǎng)絡(luò)判斷那簡(jiǎn)單修改就可以

OkHttpClient.Builder builder = new OkHttpClient.Builder()
        .addInterceptor(new Interceptor() {
            @Override
            public Response intercept(Chain chain) throws IOException {
                Request request = chain.request();
                if (!isNetworkConnected()) {
                    // 無(wú)網(wǎng)絡(luò)時(shí)強(qiáng)制從緩存讀取,如果緩存中沒有數(shù)據(jù)會(huì)返回 504
                    // FORCE_CACHE 里設(shè)置了 only-if-cached==true 和 maxStale
                    // only-if-cached 顧名思義就是只有緩存中有數(shù)據(jù)才返回檬果,沒有時(shí)返回 504
                    // maxStale 指可以取過(guò)期多久的數(shù)據(jù),F(xiàn)ORCE_CACHE 中設(shè)置為了Int最大值
                    request = request.newBuilder()
                            .cacheControl(CacheControl.FORCE_CACHE)
                            .build();
                } else {
                    // 有網(wǎng)絡(luò)時(shí)從網(wǎng)絡(luò)獲取
                    // FORCE_NETWORK 里設(shè)置了 no-cache
                    // no-cache 顧名思義唐断,強(qiáng)制客戶端直接向服務(wù)器發(fā)送請(qǐng)求,也就是說(shuō)每次請(qǐng)求都必須向服務(wù)器發(fā)送选脊。服務(wù)器接收到請(qǐng)求,然后判斷資源是否變更脸甘,是則返回新內(nèi)容恳啥,否則返回304(Not Modified)。
                    // 注意服務(wù)器根據(jù) Etag 判斷資源未變更時(shí)返回的是 304丹诀,這時(shí)還是從緩存中拿钝的,這里有點(diǎn)違背 no-cache 的含義,要注意理解铆遭。
                    request = request.newBuilder()
                            .cacheControl(CacheControl.FORCE_NETWORK)
                            .build();
                }
                return chain.proceed(request);
            }
        })
        .addNetworkInterceptor(new Interceptor() {
            @Override
            public Response intercept(Chain chain) throws IOException {
                Response response = chain.proceed(chain.request());

                // 緩存 10 秒
                CacheControl cacheControl = new CacheControl.Builder()
                        .maxAge(10, TimeUnit.SECONDS)
                        .build();

                return response.newBuilder()
                        .removeHeader("Pragma")
                        .header("Cache-Control", cacheControl.toString())
                        .build();
            }
        })
        .cache(cache);

boolean isNetworkConnected() {
    ConnectivityManager connectivityManager = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
    NetworkInfo networkInfo = connectivityManager.getActiveNetworkInfo();
    return networkInfo != null && networkInfo.isConnected();
}
保存緩存是在客戶端瀏覽器中保存硝桩,所以修改的是 Response 通過(guò)添加 Cache-control 告訴瀏覽器數(shù)據(jù)緩存的規(guī)則。 讀取緩存修改的肯定是 Request 了枚荣,也是通過(guò)添加 Cache-control 告訴服務(wù)端你是要取緩存還是不要緩存及緩存數(shù)據(jù)的規(guī)則碗脊。
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市橄妆,隨后出現(xiàn)的幾起案子衙伶,更是在濱河造成了極大的恐慌,老刑警劉巖害碾,帶你破解...
    沈念sama閱讀 217,657評(píng)論 6 505
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件矢劲,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡慌随,警方通過(guò)查閱死者的電腦和手機(jī)芬沉,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,889評(píng)論 3 394
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人花嘶,你說(shuō)我怎么就攤上這事笋籽。” “怎么了椭员?”我有些...
    開封第一講書人閱讀 164,057評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵车海,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我隘击,道長(zhǎng)侍芝,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,509評(píng)論 1 293
  • 正文 為了忘掉前任埋同,我火速辦了婚禮州叠,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘凶赁。我一直安慰自己咧栗,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,562評(píng)論 6 392
  • 文/花漫 我一把揭開白布虱肄。 她就那樣靜靜地躺著致板,像睡著了一般。 火紅的嫁衣襯著肌膚如雪咏窿。 梳的紋絲不亂的頭發(fā)上斟或,一...
    開封第一講書人閱讀 51,443評(píng)論 1 302
  • 那天,我揣著相機(jī)與錄音集嵌,去河邊找鬼萝挤。 笑死,一個(gè)胖子當(dāng)著我的面吹牛根欧,可吹牛的內(nèi)容都是我干的怜珍。 我是一名探鬼主播,決...
    沈念sama閱讀 40,251評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼凤粗,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼绘面!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起侈沪,我...
    開封第一講書人閱讀 39,129評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤揭璃,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后亭罪,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體瘦馍,經(jīng)...
    沈念sama閱讀 45,561評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,779評(píng)論 3 335
  • 正文 我和宋清朗相戀三年应役,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了情组。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片燥筷。...
    茶點(diǎn)故事閱讀 39,902評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖院崇,靈堂內(nèi)的尸體忽然破棺而出肆氓,到底是詐尸還是另有隱情,我是刑警寧澤底瓣,帶...
    沈念sama閱讀 35,621評(píng)論 5 345
  • 正文 年R本政府宣布谢揪,位于F島的核電站,受9級(jí)特大地震影響捐凭,放射性物質(zhì)發(fā)生泄漏拨扶。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,220評(píng)論 3 328
  • 文/蒙蒙 一茁肠、第九天 我趴在偏房一處隱蔽的房頂上張望患民。 院中可真熱鬧,春花似錦垦梆、人聲如沸匹颤。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,838評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)惋嚎。三九已至,卻和暖如春站刑,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背鼻百。 一陣腳步聲響...
    開封第一講書人閱讀 32,971評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工绞旅, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人温艇。 一個(gè)月前我還...
    沈念sama閱讀 48,025評(píng)論 2 370
  • 正文 我出身青樓因悲,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親勺爱。 傳聞我的和親對(duì)象是個(gè)殘疾皇子晃琳,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,843評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容