使用 PHP 设置过期标题

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/5776971/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-25 22:27:43  来源:igfitidea点击:

Setting up Expire Headers with PHP

phpheader

提问by alex

could anyone help me with setting up Expire Headers using PHP only, .htaccess is no good, because my host won't enable mod_expires on apache.

任何人都可以帮助我仅使用 PHP 设置过期标头,.htaccess 不好,因为我的主机不会在 apache 上启用 mod_expires。

So basically I'm looking for a way to do:

所以基本上我正在寻找一种方法:

Expire Header
<FilesMatch "\.(ico|jpg|jpeg|png|gif|js|css|swf)$">
ExpiresDefault "access plus 365 days"
</FilesMatch>

with php only.

仅使用 php。

its also important to have different expire periods for different filetypes, so I tried using something like:

为不同的文件类型设置不同的过期时间也很重要,所以我尝试使用以下内容:

header ("content-type: image/jpg; charset: UTF-8");
header ("cache-control: must-revalidate");
$offset = 48 * 60 * 60;
$expire = "expires: " . gmdate ("D, d M Y H:i:s", time() + $offset) . " GMT";
header ($expire);

for each type of files, but nothing happened.

对于每种类型的文件,但什么也没发生。



the headers after adding the PHP code, and taken from private session:

添加 PHP 代码后的标题,并取自私人会话:

Response Headersview source
Date    Mon, 25 Apr 2011 19:47:10 GMT
Server  Apache/2.2.14 (Unix) DAV/2 mod_ssl/2.2.14 OpenSSL/0.9.8l PHP/5.3.1 mod_apreq2-20090110/2.7.1 mod_perl/2.0.4 Perl/v5.10.1
X-Powered-By    PHP/5.3.1
P3P CP="NOI ADM DEV PSAi COM NAV OUR OTRo STP IND DEM"
Expires Mon, 1 Jan 2001 00:00:00 GMT
Cache-Control   no-store, no-cache, must-revalidate, post-check=0, pre-check=0
Last-Modified   Mon, 25 Apr 2011 19:47:10 GMT
Content-Encoding    gzip
Pragma  no-cache
Keep-Alive  timeout=5, max=100
Connection  Keep-Alive
Transfer-Encoding   chunked
Content-Type    text/html; charset=utf-8
Request Headersview source
Host    localhost
User-Agent  Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9.2.16) Gecko/20110323 Ubuntu/10.10 (maverick) Firefox/3.6.16 ( .NET CLR 3.5.30729) FirePHP/0.5
Accept  text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language en-us,en;q=0.7,he;q=0.3
Accept-Encoding gzip,deflate
Accept-Charset  ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive  115
Connection  keep-alive
Referer http://localhost/-----------------
Cookie  fboard_settings[current_view]=flat; style_cookie=null; phpbb3_4s1go_k=; phpbb3_4s1go_u=2; phpbb3_4s1go_sid=8a3835a63834e9851b0cde3e2f6cff63; jw_clean_pro_tpl=jw_clean_pro; acpSearchCookie[searchphrase]=any; acpSearchCookie[acpSearch]=%D7%97%D7%A4%D7%A9+...; acpSearchCookie[cid]=0; acpSearchCookie[field_city]=0; 14a2bb08766d6180968b7925b7902d70=bgd3h1uj5dctoevtdiaj1jtmg6; 3e2fd857422e2463a01f9631f718017a=nbdjbmjsn9ee8ng90ui816hec2
x-insight   activate

回答by Jürgen Thelen

According to your comment in the question it looks like your system is running with a PHP setting of session.cache_limiter = nocache. This would automatically send the following headers:

根据您在问题中的评论,您的系统似乎正在运行 PHP 设置为session.cache_limiter = nocache. 这将自动发送以下标头:

Expires: Thu, 19 Nov 1981 08:52:00 GMT
Cache-Control: no-store, no-cache, must-revalidate, post-check=0, pre-check=0
Pragma: no-cache

Only the Expiresheader you mention differs a bit (afaik Joomla uses that very datetime, if i'm not mistaken). But all in all it makes no difference, because both dates are in the past.

只有Expires您提到的标题有所不同(如果我没记错的话,afaik Joomla 使用了那个日期时间)。但总而言之,这没什么区别,因为这两个日期都是过去的。

You should try with session_cache_limiter(false);in your code, to stop PHP sending its default caching headers:

您应该session_cache_limiter(false);在代码中尝试使用,以阻止 PHP 发送其默认缓存标头:

function sendHeader($sType, $iLastModified, $iSecondsToCache)
{

    $aType = array(
        'ico'   => 'image/x-icon',
        'jpg'   => 'image/jpeg',
        'png'   => 'image/png',
        'gif'   => 'image/gif',
        'js'    => 'text/javascript',
        'css'   => 'text/css',
        'swf'   => 'application/x-shockwave-flash'
    );
    if (!isset($aType[$sType]))
        die('No mime type found for ' . $sType);

    //$sLastModified = gmdate('r', $iLastModified);
    $sLastModified = gmdate('D, d M Y H:i:s', $iLastModified) . ' GMT';

    if (isset($_SERVER['HTTP_IF_MODIFIED_SINCE']))
    {
        if ($_SERVER['HTTP_IF_MODIFIED_SINCE'] == $sLastModified)
        {
            header('HTTP/1.1 304 Not Modified');
            exit;
        }
    }

    session_cache_limiter(false);
    //header('Expires: ' . gmdate('r', $iLastModified + $iSecondsToCache));
    header('Expires: ' . gmdate('D, d M Y H:i:s', $iLastModified + $iSecondsToCache) . ' GMT');
    header('Cache-Control: public');
    header('Last-Modified: ' . $sLastModified);
    header('Content-Type: ' . $aType[$sType]);

}

date_default_timezone_set('Europe/Berlin');

$iLastModified = strtotime('2011-04-25 07:08:09');
$iSecondsToCache = 48 * 60 * 60;
sendHeader('jpg', $iLastModified, $iSecondsToCache);

// stream sample image/jpeg content
$rGD = imagecreatetruecolor(100, 20);
$iColor = imagecolorallocate($rGD, 255, 255, 255);
imagestring($rGD, 1, 5, 5,  'Image to be cached', $iColor);
imagejpeg($rGD);
imagedestroy($rGD);
exit;

EDIT:

编辑

Meanwhile it's more probable to me, that Joomla is causing the problem. If the test code has access to Joomla libraries, try inserting:

同时,对我来说更有可能是 Joomla 导致了问题。如果测试代码可以访问 Joomla 库,请尝试插入:

jimport('joomla.environment.response');
JResponse::allowCache(true);

at the very top of the function and replace each headerinstruction with JResponse::setHeader.

在函数的最顶部,并将每条header指令替换为JResponse::setHeader.

回答by Yuriy Vikulov

That helps me for ajax queries:

这有助于我进行 ajax 查询:

header( 'Expires: Sat, 26 Jul 1997 05:00:00 GMT' );
header( 'Last-Modified: ' . gmdate( 'D, d M Y H:i:s',time()+60*60*8 ) . ' GMT' );
header( 'Cache-Control: no-store, no-cache, must-revalidate' );
header( 'Cache-Control: post-check=0, pre-check=0', false );
header( 'Pragma: no-cache' );