NSURLCache 實現離線加載網頁數據,離線緩存,節約流量,增加體驗

最近做優化網頁請求 研究了下NSURLCache ?實現離線加載網頁數據


? ? 代碼:?KLURLCache

? ? 博客:@火柴大男人

網上找了很多資料,寫的好的是一個外國人寫的但也是2012年寫的..很多東西已經過時 代碼風格也是MRC.

國內有些人翻譯過來,自己寫成中文版,看了一下也沒有DEMO代碼. 查了其它的一些文章試了下,大多只是在講理論.都 沒有代

碼DMEO.感覺研究起來費時間. ?后來找一份實現代碼.也有相關 博客說明.代碼是MRC 有些方法也過期了..本人就是參考那份

代碼實現,并做了一些改進.


寫文章前一直找當時下載代碼的地方 和博客地址 ?希望 注明一下引用一下.以示對原作者的尊重..但由于當時沒有標記位置.現在也無法找到當時出處.所以在此謝過原作者的開源精神!!


第一步:

創建一個類繼承 NSURLCache?

@interface KLURLCache : NSURLCache

重寫這個方法,,該方法是設置 內存 與 磁盤緩存 空間大小的

- (instancetype)initWithMemoryCapacity:(NSUInteger)memoryCapacity diskCapacity:(NSUInteger)diskCapacity diskPath:(NSString *)path{

if (self = [super initWithMemoryCapacity:memoryCapacity diskCapacity:diskCapacity diskPath:path]) {

if (!path) {

_diskPath = [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES)lastObject];

_responseInfoDict = [NSMutableDictionary? dictionaryWithCapacity:0];

}else{

_diskPath = path;

}

}

return self;

}


第二步:

關鍵的一步

重寫 這個方法 ?每個請求都 會經過這個方法.做緩存就是攔截這個方法 只要是GET請求才能緩存的

- (NSCachedURLResponse *)cachedResponseForRequest:(NSURLRequest *)request{

NSLog(@"%@",request.HTTPMethod);

if ([request.HTTPMethod compare:@"GET"] != NSOrderedSame) {

return [super cachedResponseForRequest:request];

}else{

return [self KL_CacheResponseDataFromRequest:request];

}

第三步:


緩存是如果做的 之前 請求都是通過[NSURLConnection sendAsynchronousRequest:request queue:[[NSOperationQueue alloc] init] completionHandler:^(NSURLResponse *response, NSData *data,NSError *error)進行的

IOS 9.0 后網絡請求改為NSURLSession 進行管理.而不是之前的 NSURLConnection 原代碼是NSURLConnection 代碼也是MRC 這個地方自己修改了;


我們拿到 全局 NSURLSession *session = [NSURLSession sharedSession];

session 請求來的數據我們寫入磁盤.

關于那個字典是什么,我們是緩存請求數據類型時間 鍵值對的.. 到時取緩存的時侯時需要用到的

NSURLSession *session = [NSURLSession sharedSession];

NSURLSessionTask *dataTask = [session dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {

if (response && data) {

[self.responseInfoDict removeObjectForKey:fileName];

}

if (error) {

cachedResponse = nil;

}

NSDictionary *dict = [NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"%f", [date timeIntervalSince1970]], @"time",response.MIMEType,@"MIMEType",response.textEncodingName,@"textEncodingName" ,nil];

[dict writeToFile:otherInfoPath atomically:YES];

[data writeToFile:filePath atomically:YES];

cachedResponse = [[NSCachedURLResponse alloc]initWithResponse:response data:data];

}];


一個GET請求 類似于 鍵值對一樣..因為一個網頁不是簡單的請求一個? www.baidu.com 這么簡單..請求這個后里面還會產生很多小請求加載數據的..每次請求都 會有一個request? 我們所做的就是 根據當前request里面的URL 做一對一的緩存.

比如打開百度時? www.baidu.com 這個URL地址已經緩存了,那么當request的URL地址是這個的時侯我們就不會向風絡再發請求.而是從本地沙盒中拿相應的數據返回給到它..但百度www.baidu.com后里面可能還www.baidu.com/1323.jpg 等等.而且每次刷新在www.baidu.com里面會有新的數據.URL請求,這個時侯可能就會出現第二次打開www.baidu.com時 些是從網絡請求的.有些是從本地加載的.如下:


2016-10-21 16:57:09.928 DEMO[1924:698294] 請求的數據是---http://www.baidu.com/

2016-10-21 16:57:09.928 DEMO[1924:698294] data from Cache

......地址是----http://m.baidu.com/static/ecom/js/wise/home/ecomAds_5f3f8bc.js

2016-10-21 16:57:09.935 DEMO[1924:698304] GET

2016-10-21 16:57:09.935 DEMO[1924:698304] 請求的數據是---http://www.baidu.com/

2016-10-21 16:57:09.936 DEMO[1924:698304] data from Cache

......地址是----http://m.baidu.com/static/search/baiduapp_icon.png

2016-10-21 16:57:09.937 DEMO[1924:698351] GET

2016-10-21 16:57:09.937 DEMO[1924:698351] 請求的數據是---http://www.baidu.com/

2016-10-21 16:57:09.938 DEMO[1924:698351] data from request

地址是------http://m.baidu.com/tc?tcreq4log=1&ssid=0&from=844b&pu=sz%401320_2001%2Cta%40iphone_1_9.3_3_601&qid=15764434222633284224-2&ct=21&cst=1&ref=index_iphone&lid=15764434222633284224-2&w=0_0_&sid=110316_104496_100186_102628_104381_100100_108470_110005_107800_110394_109974_110420_110498_110011_110298_110251_109588_108013_107320_110357_110031_110270_110400&sOS=1&banner=wiseindex&r=1477040229894

2016-10-21 16:57:09.939 DEMO[1924:698351] GET

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容

  • Android 自定義View的各種姿勢1 Activity的顯示之ViewRootImpl詳解 Activity...
    passiontim閱讀 173,333評論 25 708
  • Spring Cloud為開發人員提供了快速構建分布式系統中一些常見模式的工具(例如配置管理,服務發現,斷路器,智...
    卡卡羅2017閱讀 134,937評論 18 139
  • 概覽 緩存組件應該說是每個客戶端程序必備的核心組件,試想對于每個界面的訪問都必須重新請求勢必降低用戶體驗。但是如何...
    默默_David閱讀 1,966評論 1 9
  • 記得央視的那個調查“你幸福嘛?”讓人調侃了個遍,仔細看,那個調查也并非那么不堪,還是有人滿滿的幸福在臉上蕩漾。當時...
    吃貨不孤獨閱讀 199評論 0 0
  • 今天繼續分享【得到】App付費專欄李笑來的《通往財富自由之路》,第十六周內容——《看得見別人的好才能獲得新生》。 ...
    注冊營養師阿娟閱讀 1,035評論 4 7