0

我想实现一个在请求的文件(图像)上生成缩略图的脚本。以下是了解脚本工作的简单操作列表:

  • 向服务器请求url/preset/filename.jpg
  • 检查文件是否已被翻阅
  • 如果没有,则生成新文件并返回该文件。如果存在,则返回缩略图文件。

这很完美,但问题是浏览器没有缓存图像。我对缓存不太熟悉。我认为通过返回304 Not modified会触发浏览器从缓存中获取图像,但它挂在挂起状态。

有人知道如何缓存这些图像吗?

这是我脚本的展示部分:

private function _show_image($file_path, $filename, $new = FALSE) {
        $this->load->helper('file');

        if($new) { 
            header($_SERVER['SERVER_PROTOCOL'] . ' 200 OK');
        } else {
            //header('HTTP/1.1 304 Not Modified');
            header($_SERVER['SERVER_PROTOCOL'] . ' 304 Not Modified');  
        }

        header('Cache-Control: public'); // needed for i.e.
        header('Content-type: ' . get_mime_by_extension($file_path));
        header('Content-Transfer-Encoding: Binary');
        header('Content-Length:' . filesize($file_path));
        //header('Content-Disposition: attachment; filename=' . $filename);
        header('Content-Disposition: inline; filename=' . $filename);
        readfile($file_path);
        exit(); 
    }

更新

我更新了代码,以便它首先检查是否$_SERVER['HTTP_IF_MODIFIED_SINCE']已设置,如果是,则执行所有检查内容。但问题是浏览器永远不会发送该标头..

这是访问文件时发送和接收的标头。

要求

Accept:*/*
Accept-Encoding:identity;q=1, *;q=0
Accept-Language:nl-NL,nl;q=0.8,en-US;q=0.6,en;q=0.4
Connection:keep-alive
Cookie:PHPSESSID=heiog0hdasg181l45cfbm7u353; __jwpusr=264f6c61-3752-4682-a61b-e02b822c7815
Host:domain.local
Range:bytes=0-
Referer:http://domain.local/test
User-Agent:Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/27.0.1453.94 Safari/537.36

回复

Cache-Control:public
Connection:Keep-Alive
Content-Description:File Transfer
Content-disposition:inline
Content-Length:24103476
Content-Transfer-Encoding:binary
Content-Type:video/mp4
Date:Thu, 30 May 2013 14:07:02 GMT
Expires:0
Keep-Alive:timeout=5, max=98
Last-Modified:Wed, 29 May 2013 09:03:30 GMT
Server:Apache/2.2.22 (Win32) PHP/5.3.13
X-Frame-Options:SAMEORIGIN
X-Powered-By:PHP/5.3.13
X-XSS-Protection:1; mode=block 
4

3 回答 3

2

如果客户端向您发送了 If-Modified-Since 标头,则您只能发送 304“未修改”,例如:

If-Modified-Since: 1994 年 10 月 29 日星期六 19:43:31 GMT

或 If-None-Match:

如果无匹配:“737060cd8c284d8af7ad3082f209582d”

您无法知道图像是否仍在浏览器的缓存中,或者是否已被清除。正确的操作是在创建缩略图时返回图像。如果缩略图存在,检查 If-Modified-Since 标头(这是浏览器指示它当前在其缓存中具有文件),如果文件没有更改,则返回 304 Not Modified。否则返回文件,因为它不会在浏览器的缓存中。

If-None-Match 系统使用 eTags,如果您不需要处理它们,最好避免使用它们。

于 2013-05-18T12:24:16.923 回答
2

如果您使用的是 Apache,最好添加 mod_rewrite。您可以创建一个重写规则,仅当请求的图像不存在时才将请求重定向到 PHP。

缩略图目录中的 .htaccess 文件:

RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule .* /thumbnailer.php

thumbnailer.php 然后需要检查 $_SERVER['REDIRECT_URL'] (或一些类似的变量,检查 phpinfo)以查看需要生成哪个文件。

于 2013-05-30T14:25:44.353 回答
1

我的第一个提示是,如果可以的话,将缓存留给 Apache 本身。它最清楚如何发送标头和响应缓存请求。

如果您真的想自己执行此操作,则需要确定浏览器何时请求图像或仅检查是否有更改(If-Modified-Since)。

您没有设置过期时间或最大年龄,因此它可能根本没有缓存图像。

Expires Mon, 16 Oct 2012 11:07:06 GMT
Cache-Control   public, max-age=120

当它发出一个新请求(没有If-Modified-Since)时,你只是发回了一个它没想到的 304。

于 2013-05-18T12:23:28.533 回答