Headers and caching

I am finishing up development of my first Yii website, and I would like to ask if someone can check the following bit of code. The action below should either display an image in the browser, or force a download of the image. Images that have been uploaded (to a non-web-accessible directory) will not be modified, other than possibly being deleted. I would like a browser to use a cached version of the image as much as possible.

Like I said, this is my first Yii project, but it is also my first larger complete project. So I have been learning a lot about Yii, PHP, JavaScript and so on. Caching is important so that my site reduces bandwith as much as needed, but Googling for headers and cache-control seems to bring up a lot of different code fragments. This is the best I could figure out so far.

The below is dumbed down a bit, but the important parts are shown. The $model variable contains an Image model that holds information about the image path, mime type and so on.


public function actionImage($model, $forceDownload)

{

    $lastModified = filemtime($model->path);

    $ClientHeaders = apache_request_headers();


    if (isset($ClientHeaders["If-Modified-Since"]) && (strtotime($ClientHeaders["If-Modified-Since"]) >= $lastModified))

        header("Last-Modified: " . gmdate("D, d M Y H:i:s", $lastModified) . " GMT", true, 304);

    else

    {

        header('Content-Type: ' . $model->mime);

        header('Content-Disposition: filename="' . $model->filename . '"');

        header('Cache-Control: private, must-revalidate, max-age=31536000');

        header("Last-Modified: " . gmdate("D, d M Y H:i:s", $lastModified) . " GMT", true, 200);


        if ($forceDownload)

        {

            header('Content-Description: File Transfer');

            header('Content-Length: ' . filesize($model->path));

            header('Content-Disposition: attachment; filename="' . $model->filename . '"');

        }


        readfile($model->path);

    }


    exit;

}

Any input on what is right, wrong, and how to improve it would be very much appreciated. Thanks!

Regarding the http cache headers: Maybe we could combine our efforts? ;)

When it comes to sending those images to the browser: Using PHP for this is a bit off and might turn into a resource hog. Maybe X-Sendfile is something for you?

Hi Da:Sourcerer,

My head is just not coorporating with me today, so I’ll leave coding for tomorrow. I will look through your post in detail tomorrow as well and see what I can make of it. As for X-Sendfile, I am affraid that is not an option, as my host does not have it installed.

My site is not a very busy site (I primarily use it for myself and a handful of others), so fortunately I have a bit of slack in ‘wasting’ resources. Then again, whatever I can prevent from being wasted is a gain.

Thanks for the link, and I’ll check it out when I’m a bit sharper. :)