如何从PHP更新浏览器缓存?

时间:2012-11-22 07:37:49

标签: php html caching optimization

我有一个PHP文件 get_css.php ,它生成的CSS代码长度超过60 KB。此代码不会经常更改。我希望将此代码缓存在用户的浏览器中。 现在,当我多次访问一个包含 get_css.php url的HTML页面来获取css时,我的浏览器每次访问该页面时都会从服务器加载所有CSS内容。

只有在服务器端更改CSS代码时,浏览器才能从服务器获取内容。如果未更改css代码,浏览器将使用浏览器缓存中的css代码。 我无法使用服务器安全模式中不允许的任何PHP功能。

有可能吗?我怎样才能做到这一点?

4 个答案:

答案 0 :(得分:1)

您无法强制客户端轻松重新验证其缓存。

将变量查询字符串设置为其资源不能很好地与代理一起使用,但似乎足以满足浏览器的要求。如果查询字符串发生变化,浏览器往往只会重新下载css文件。

 <link rel="stylesheet" type="text/css" href="/get_css.php?v=1.2.3"> 

可能您可以使用CSS的命名,例如添加数字,但这不是一个很好的选择。

答案 1 :(得分:1)

您无法控制PHP的浏览器行为,但您可以使用HTTP代码告诉浏览器。

如果未更改CSS,只需回复304 Not Modified响应代码:

if ($css_has_not_changed && $browser_has_a_copy) {
    http_response_code(304);
} else {
    // regenerate CSS
}

这样,浏览器询问文档(您无法控制),但是您告诉他使用缓存副本。

当然这需要测试,因为我现在已经知道它将如何“第一次”浏览器请求文件(可能请求标题可以告诉你更多)。一个快速的firebug测试显示,Firefox在请求新副本时请求Cache-Control: no-cache,在有缓存时请求Cache-Control: max-age=0

答案 2 :(得分:0)

在包含get_css.php时添加正常的GET参数

<link rel="stylesheet" type="text/css" href="get_css.php?v=1">

浏览器会认为它是新链接并会再次加载。

并在get_css.php中使用此制作浏览器缓存数据

<?php
header("Content-type: text/css");
header('Cache-Control: public');
header('Expires: ' . gmdate('D, d M Y H:i:s', strtotime('+1 year')) . ' GMT');
ob_start("ob_gzhandler");

//echo css here

答案 3 :(得分:0)

浏览器希望默认缓存您的文档,但您必须提供足够的信息才能实现这一点。一种相当简单的方法是发送Last-Modified标头,其中包含上次更改脚本的日期/时间。您还需要通过检查传入的Last-Modified日期,将其与脚本的实际修改日期进行比较,并返回304 Not Modified响应(响应为空)来正确处理浏览器的“重新验证”请求body),如果文件没有改变。

确保您的服务器不“神奇地”发送任何其他“无缓存”指令也是一个好主意。最简单的方法是发送一个Cache-Control指令,告诉浏览器确切的行为。

Here是对每个Cache-Control选项的快速解释。

以下内容应该可以解决问题:

<?php
// this must be at the top of your file, no content can be output before it

$modified = filemtime(__FILE__);
if(isset($_SERVER['HTTP_IF_MODIFIED_SINCE'])) {
  $if_modified_since=strtotime($_SERVER["HTTP_IF_MODIFIED_SINCE"]);
  if( $modified > $if_modified_since ) {
    header('HTTP/1.0 304 Not Modified');
    exit();
  }
}
header('Cache-Control: must-revalidate');
header('Last-Modified: '.date("r",$modified));

// ... and the rest of your file goes here...

以上示例主要基于示例和写作found here