ETag 和 If-None-Match HTTP 标头不起作用

Posted

技术标签:

【中文标题】ETag 和 If-None-Match HTTP 标头不起作用【英文标题】:ETag and If-None-Match HTTP Headers are not working 【发布时间】:2016-06-07 02:11:08 【问题描述】:

我的 webserver 中有一个文件,每次访问它时我都会将其下载到我的应用程序中,因为文件内容可能会更改但如果更改了,我想在那个时候下载只有这样才能节省带宽,幸运的是,这就是 ETagIf-None-Match 标头字段 的用途。

当我第一次发出请求时,我从 HTTP 响应标头中检索 ETag

在随后的下载该文件的请求中,我会为 If-None-Match 标头字段附加 Etag 值,这样如果没有更改,那么我会获取 HTTP 响应状态码 304,否则如果文件发生更改,我将得到 200。

注意:

当我在 Chrome 中的 Advanced REST Client Application 中尝试上述步骤时,它可以正常工作,但是当我在 ios 中尝试时,我总是得到响应代码 200,但它应该有给我 304 用于后续请求。

这是我使用的示例代码

var request1 =  NSMutableURLRequest(URL:NSURL(string: "http://10.12.1.101/Etag/ringtone1.mp3")!)
let Etagvalue="\"36170-52c1cc36d9b40\""
var session1 = NSURLSession.sharedSession()
request1.HTTPMethod = "GET"
var err: NSError?
request1.addValue(Etagvalue, forHTTPHeaderField: "If-None-Match")

var task = session1.dataTaskWithRequest(request1, completionHandler: data, response, error -> Void in
       print("response: \(response)")

)

这是回复

响应:可选( URL: http://10.12.1.101/Etag/ringtone1.mp3 状态码:200,标题 “接受范围” = 字节; 连接=“保持活动”; “内容长度”= 221552; “内容类型”=“音频/mpeg”; 日期 =“格林威治标准时间 2016 年 2 月 24 日星期三 14:57:53”; Etag = "\"36170-52c1cc36d9b40\""; “保活”=“超时=5,最大值=100”; “上次修改时间”=“格林威治标准时间 2016 年 2 月 19 日星期五 10:15:33”; 服务器 = "Apache/2.4.16 (Unix) php/5.5.29"; )

我在这里做错了什么?

【问题讨论】:

向我们展示生成的请求。例如使用代理服务器(例如 charles) @Daij-Djan - 突然间它开始工作了!我猜不出为什么会出现这种不一致! @Daij-Djan - 除了 ..server 端配置之外,E-tag 是否存在任何依赖项?我的手指仍然交叉它是如何开始工作的? 不这么认为......好吧,你不能在当地兑现,但我认为你不会;)——所以不:/ @Daij-Djan - 因为我没有在我的请求中指定任何关于缓存策略的内容,所以默认的 NSURLRequestCachePolicy.UseProtocolCachePolicy 将是行为......所以缓存会发生。 【参考方案1】:

我也遇到了同样的问题。我发现这是因为cachePolicy。您需要按如下方式设置:

request.cachePolicy = .ReloadIgnoringLocalAndRemoteCacheData

你会没事的

【讨论】:

这应该被标记为答案。精彩绝伦! 这对我有用。您能将此标记为解决方案吗? 这节省了我数小时的时间来追踪为什么 S3 忽略了我的 If-None-Match 标头,谢谢!!! 字面上花了 2 周时间寻找这个。谢谢!!【参考方案2】:

CachePolicy 命名约定令人困惑,但它实际上并没有实现其中的一些......

这篇文章很好地解释了它们。 http://nshipster.com/nsurlcache/

另外,如果您让缓存策略使用UseProtocolCachePolicy,那么您的 NSURLSession 将收到状态代码 200 并从缓存生成响应。

【讨论】:

【参考方案3】:

此问题是由于缓存策略“useProtocolCachePolicy”、“returnCacheDataElseLoad”或“returnCacheDataDontLoad”造成的。

您可以使用上述任何其他策略。最好是'reloadIgnoringLocalAndRemoteCacheData'。

【讨论】:

以上是关于ETag 和 If-None-Match HTTP 标头不起作用的主要内容,如果未能解决你的问题,请参考以下文章

If-None-Match标头未接受请求标头

Last-Modified If-Modified-Since ETag If-None-Match

Web缓存杂谈--Etag & If-None-Match

爱创课堂每日一题第二十四天-ETag应用?

If-Modified-Since 覆盖浏览器中的 If-None-Match

If-None-Match 有效时 304 Not Modified