我正在尝试使用Java的HttpURLConnection来执行“条件获取”,但我从未获得304状态代码 [英] I'm trying to use Java's HttpURLConnection to do a "conditional get", but I never get a 304 status code

查看:167
本文介绍了我正在尝试使用Java的HttpURLConnection来执行“条件获取”,但我从未获得304状态代码的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是我的代码:

    final HttpURLConnection conn = (HttpURLConnection) sourceURL.openConnection();
    if (cachedPage != null) {
        if (cachedPage.eTag != null) {
            conn.setRequestProperty("If-None-Match", cachedPage.eTag);
        }
        conn.setIfModifiedSince(cachedPage.pageLastModified);
    }

    conn.connect();

    if (conn.getResponseCode() == HttpURLConnection.HTTP_OK) {

        newCachedPage.eTag = conn.getHeaderField("ETag");
        newCachedPage.pageLastModified = conn.getHeaderFieldDate("Last-Modified", 0);

    } else if (conn.getResponseCode() == HttpURLConnection.HTTP_NOT_MODIFIED) {
        // Never reaches here
    }

我似乎永远不会得到HTTP_NOT_MODIFIED响应代码,即使连续多次点击同一台服务器 - 页面肯定没有变化。此外,conn.getHeaderField(ETag)似乎总是响应null,有时conn.getHeaderFieldDate(Last-Modified,0)返回0.我已经尝试过针对各种Web服务器。

I never seem to get the HTTP_NOT_MODIFIED response code, even hitting the same server several times in quick succession - where there is definitely no change to the page. Also, conn.getHeaderField("ETag") always seems to respond null, and sometimes conn.getHeaderFieldDate("Last-Modified", 0) returns 0. I've tried this against a variety of web servers.

谁能告诉我我做错了什么?

Can anyone tell me what I'm doing wrong?

推荐答案

你们都是取决于服务器配置。

You're all dependent on the server config.

如果你得到一个 Expires 响应标题,那么它只是意味着你不要我需要请求任何东西,直到指定的到期时间。如果你得到一个 Last-Modified 响应标题,那么这意味着你应该可以使用 If-Modified-Since 测试它。如果你得到 ETag 响应标题,那么这意味着你应该可以使用 If-None-Match 来测试一下。

If you get an Expires response header, then it just means that you don't need to request anything until the specified expire time. If you get a Last-Modified response header, then it means that you should be able to use If-Modified-Since to test it. If you get an ETag response header, then it means that you should be able to use If-None-Match to test it.

让我们参加 http://cdn3.sstatic.net /stackoverflow/img/favicon.ico 作为示例(Stackoverflow的favicon图像):

Lets take http://cdn3.sstatic.net/stackoverflow/img/favicon.ico as an example (the Stackoverflow's favicon image):

URLConnection connection = new URL("http://cdn3.sstatic.net/stackoverflow/img/favicon.ico").openConnection();
System.out.println(connection.getHeaderFields());

这给出:


{null = [HTTP / 1.1 200 OK],ETag = [9d9bd8b1165cb1:0],日期= [星期三,2011年8月17日17:57:07 GMT],Content-Length = [1150],最后-Modified = [Wed,06 Oct 2010 02:53:46 GMT],Content-Type = [image / x-icon],Connection = [keep-alive],Accept-Ranges = [bytes],Server = [nginx / 0.8.36],X-Cache = [HIT],Cache-Control = [max-age = 604800]}

{null=[HTTP/1.1 200 OK], ETag=["9d9bd8b1165cb1:0"], Date=[Wed, 17 Aug 2011 17:57:07 GMT], Content-Length=[1150], Last-Modified=[Wed, 06 Oct 2010 02:53:46 GMT], Content-Type=[image/x-icon], Connection=[keep-alive], Accept-Ranges=[bytes], Server=[nginx/0.8.36], X-Cache=[HIT], Cache-Control=[max-age=604800]}

现在,做一个 If-Modified-Since Last-Modified

Now, do a If-Modified-Since with the same value as Last-Modified:

URLConnection connection = new URL("http://cdn3.sstatic.net/stackoverflow/img/favicon.ico").openConnection();
connection.setRequestProperty("If-Modified-Since", "Wed, 06 Oct 2010 02:53:46 GMT");
System.out.println(connection.getHeaderFields());

这给出了预期的304:

This gives as expected a 304:


{null = [HTTP / 1.1 304未修改],ETag = [9d9bd8b1165cb1:0],日期= [星期三,2011年8月17日17:57:42 GMT],Last-Modified = [2010年10月6日星期三02:53:46 GMT],Connection = [keep-alive],Server = [nginx / 0.8.36],X-Cache = [HIT],Cache-Control = [max-age = 604800 ]}

{null=[HTTP/1.1 304 Not Modified], ETag=["9d9bd8b1165cb1:0"], Date=[Wed, 17 Aug 2011 17:57:42 GMT], Last-Modified=[Wed, 06 Oct 2010 02:53:46 GMT], Connection=[keep-alive], Server=[nginx/0.8.36], X-Cache=[HIT], Cache-Control=[max-age=604800]}

现在,做一个 If-None-Match ,其值与 ETag

Now, do a If-None-Match with the same value as ETag:

URLConnection connection = new URL("http://cdn3.sstatic.net/stackoverflow/img/favicon.ico").openConnection();
connection.setRequestProperty("If-None-Match", "9d9bd8b1165cb1:0");
System.out.println(connection.getHeaderFields());

这给意外 200:


{null = [HTTP / 1.1 200 OK],ETag = [9d9bd8b1165cb1:0],日期= [Wed,2011年8月17日18:01:42 GMT] ,Content-Length = [1150],Last-Modified = [Wed,06 Oct 2010 02:53:46 GMT],Content-Type = [image / x-icon],Connection = [keep-alive],Accept-Ranges = [字节],服务器= [nginx / 0.8.36],X-Cache = [HIT],Cache-Control = [max-age = 604800]}

{null=[HTTP/1.1 200 OK], ETag=["9d9bd8b1165cb1:0"], Date=[Wed, 17 Aug 2011 18:01:42 GMT], Content-Length=[1150], Last-Modified=[Wed, 06 Oct 2010 02:53:46 GMT], Content-Type=[image/x-icon], Connection=[keep-alive], Accept-Ranges=[bytes], Server=[nginx/0.8.36], X-Cache=[HIT], Cache-Control=[max-age=604800]}

更令人惊讶的是,当两个标头设置为随机垃圾值为 ETag 时,服务器仍然给出304.这表明 http://cdn3.sstatic后面的服务器完全忽略 If-None-Match 。净。这可能是(代理)配置问题或完全明确地完成(不明显的原因imho)。

Even more surprising, when the both headers are set with random garbage value as ETag, the server still gives a 304. This is an indication that the If-None-Match is completely ignored by the server behind http://cdn3.sstatic.net. That might be a (proxy) configuration issue or be done fully awarely (not for obvious reasons imho).

这篇关于我正在尝试使用Java的HttpURLConnection来执行“条件获取”,但我从未获得304状态代码的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆