这一切都足够合理.我的新应用程序项目只针对iOS 5及更高版本,所以我认为我可以利用新的NSURLCache实现我所有的Web缓存需求.我需要一个NSURLCache的自定义子类来处理一些特殊的任务,但是这似乎都被API的有力支持.快速阅读文档,我会参加比赛:
[NSURLCache setSharedURLCache:[[MyCustomCache alloc] initWithMemoryCapacity:8 * 1024 * 1024 //8mb diskCapacity:32 * 1024 * 1024 // 32mb diskPath:@"webcache.db"]];
我认为一个8MB缓存启动是很好的,我会用更大的磁盘缓存来备份它,所以我们可以在本地服务更多的我们更大的图像.我连接我的网络代码的其余部分使用NSURLConnection(实际上,我使用了MKNetworkKit,但结果是无关紧要),并期望从我的缓存伟大的事情.果然,应该缓存的所有请求都被尽可能地保存到缓存中,并且响应在从缓存提供时迅速飞回.这是Penzance海盗的常规生产,在我的网络堆栈中有如此多的责任.
除了没有加起来的东西.可以从缓存提供的请求仍然通过网络进行.除非他们不是.它是完全随机的和间歇性的,无论缓存是否实际用于提供请求.我沮丧地撕开了我的头发,并从字面上挖掘出所有想弄清楚发生了什么的一切.我构建测试应用程序,设置断点,撕裂数据包跟踪,阅读互联网上的每个单词,提到NSURLCache,实验缓存控制头,注释掉代码,绕过我的子类,甚至采取艰苦的追踪,通过组装NSURLCache及其CFNetworking的朋友试图了解什么神秘的逻辑在下面.我大力提高了我对ARM和Objective-C调用约定的了解,并学习了一些关于低级调试的公正内容,但实际上并没有弄清楚发生了什么.整个事情的感觉比Iolanthe的Nightmare Song更像是海盗王的良性专政,而且我几乎完全把它抛在脑后.
TL / DR版本:NSURLCache似乎正在工作,但即使有可用的缓存结果也随机返回.
解决方法
瞧,所有的奇怪都消失了!应该缓存的一切都会得到保存.应该来自缓存的所有内容在没有网络请求的情况下得到满足.
看来,iOS5中的NSURLCache实现仍然不完整.它使用磁盘和内存缓存(不像iOS4和更早版本,它只实现了内存中的缓存),但是当请求未命中时,它实际上并没有通过内存缓存到磁盘缓存.因此,基本上是盲目的运气(好的,盲目的运气受所有其他网络和缓存使用情况的影响)是否在给定的响应恰好在内存中或不在正确的时刻.这可能有助于减少设备上的闪存文件IO,但如果您期望类的理性行为,则会非常讨厌.
所以笑歌和快乐的舞蹈,我检查我的双线修复,急于为酒吧,最终分享这个知识与SO(和一个苹果bug报告),希望没有人必须经过这个再次疼痛
这个悲剧故事的道德:如果您尝试在具有大于内存容量的磁盘容量的iOS5上使用NSURLCache,将会发生奇怪的事情.不要这样做并避免制造魔法仙女的敌人.