PHP/Ajax "Vary: X-Requested-With"对我不起作用!

标签 php ajax caching header vary

我正在尝试根据它是否是 ajax 请求来提供可缓存的内容。

场景:

一个小的 PHP 脚本“/test.php”提供一些 HTML 输出并设置以下 header :

Expires         Wed, 23 Feb 2011 13:30:06 GMT
Cache-Control   public, max-age=60
Vary            X-Requested-With,Accept-Encoding

输出取决于 $_SERVER['HTTP_X_REQUESTED_WITH'] 状态。

当我的 Firefox 指向 Url 时,我得到了输出,在下一分钟,我从浏览器缓存中得到了相同的结果,而不是访问服务器。好的,到此为止。

当我通过 XMLHttpRequest(带有 X-Requested-With: XMLHttpRequest header )请求相同的资源时,我的 Firefox 不请求服务器,而是提供(错误)来自缓存的响应!

反之亦然。资源上的 Ajax 调用填充缓存,随后的浏览器请求服务于来自缓存的(错误)响应。

有没有人有这方面的经验?我认为这应该是一个足够普遍的问题 - 根据是否使用 ajax 来提供内容(在相同的 URL 上)。

问候,伊利亚

最佳答案

我可以重现这个,但前提是我不在 ajax 响应中包含 X-Requested-With header 。如果我为 ajax 调用设置 header ,它大部分会按预期工作,尽管 ajax 调用会清除常规请求的缓存,反之亦然 - 内容不会被缓存,但你永远不会得到内容错误。

我的 PHP 文档如下所示:

<?
    putenv('TZ=PST8PDT');
    date_default_timezone_set('America/Los_Angeles');

    header('Expires: '.gmdate("D, d M Y H:i:s").' GMT');
    header('Cache-Control: public, max-age=60');
    header('Vary: X-Requested-With,Accept-Encoding');

    echo 'it is now '.date('Y-m-d H:i:s');
?>

我的测试页是这样的:

<a href="resource.php" target="ifr">load into frame</a><br />
<iframe name="ifr" width="400" height="100"></iframe>

<hr />

<a href="#" onclick="return load();">load into div via ajax</a><br />
<div id="di" style="border: 1px solid black; width: 400px; height: 100px;"></div>

<script>

function load(){

    var req = new XMLHttpRequest();
    req.onreadystatechange = function(){

        if (req.readyState == 4){
            document.getElementById('di').textContent = req.responseText;
        }
    }

    req.open('GET', 'resource.php', 1);
    req.setRequestHeader("X-Requested-With", "XMLHttpRequest");
    req.send(null);

    return false;
}

</script>

当我点击第一个链接时,它向服务器请求。当我再次点击它时,它来自缓存。每个后续点击都来自缓存,最多 60 秒。

当我点击第二个链接时,请求发送到服务器。当我再次点击它时,它来自缓存。每个后续点击都来自缓存,最多 60 秒。

如果我点击链接 1,然后点击链接 2,它们都会转到服务器。如果我再次点击链接 1,它将再次转到服务器(这是错误的)。演示序列(假设全部在 60 秒内):

Reg  : server
Reg  : cache
Reg  : cache
Reg  : cache
Ajax : server
Ajax : cache
Reg  : server
Ajax : server

结果是,如果您想在通过 ajax 服务时以不同方式可靠地缓存内容,请在发出 ajax 请求时使用不同的 URL(?ajax=1 可以正常工作)。

我正在测试最新的 FF 4.0

关于PHP/Ajax "Vary: X-Requested-With"对我不起作用!,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5091701/

相关文章:

caching - 通过自定义响应 header 绕过 Nginx 缓存

php - CodeIgniter 连接到数据库

php - Laravel Postgre 无效文本表示

node.js - cURL 的 --form 的 axios 或 ajax 等效项是什么?

java - 如何在rest webservice中接收编码的字节数组并对其进行解码并在java中另存为图像

css - 相同的样式表在浏览器和存储它的服务器上显示不同

php - 基于复选框的多个sql条件

php - 如何使用 php 5.5.17 像 JSON for Google 图表一样从 postgres 9.5 中排列结果

javascript - 为什么 $.load( handler(eventObject) ) 对 Ajax 请求后从服务器返回的数据不起作用,试图让它等待所有图像加载

c# - ASP.NET 无法缓存空值