Static Caching

Description

The static driver is blazing fast. It is the fastest driver available in CE Cache, but it may not always be the right tool for the job. Unlike the other drivers, the static driver caches an entire page, and does not allow for fragment caching. For this reason, you cannot escape certain parts of your template to remain dynamic when using the static driver. If you have pages that do not have dynamic content (like displaying content when a user is logged in or out), then the static driver should be a good fit.

How It Works

The server will check to see if the static driver has already made a flat html file of the requested page in the past. If a flat file is found, it will serve it up, completely bypassing ExpressionEngine®. If it has not, or if the page has expired, then the page will be requested from ExpressionEngine® and cached to a flat html file.

Usage

To use the static driver, you simply need to add the static tag to your template (view the static tag documentation for more information):

{exp:ce_cache:stat:ic}

It does not matter where in the template the tag occurs, as the entire page will be cached. If an embed or snippet contains the tag, then the entire page will still be cached.

Control Panel

All of the goodness of the control panel is available to the static driver, including optionally refreshing items when deleting them. Cache breaking also works the same way it does with the other drivers.

Installation

Note: Log into the control panel and navigate to Add-Ons -> Modules -> CE Cache -> Static Driver Installation for site-specific installation instructions

The generic instructions are included below, but you'll still need to get the code from the static driver installation page in order to get your site's unique code.

These instructions are for setting up the CE Cache static driver for the current site only. Since these settings are dependent on the site’s name for uniqueness, if you change the site’s name (by going to Admin -> General Configuration -> Name of your site on a standalone installation, or by editing the Site Label for an MSM site), you will need to update these settings.

Step 1 - Create The Static Cache Directory

If you haven’t already, create a directory named static in your site’s web root directory. Make sure the directory is writable by Apache and can display the files (permissions of 0775 should do).

Step 2 - Update The Cache Handler Path

If you haven’t already, upload the _static_cache_handler.php file to your site’s web root directory. Change this line:

private $cache_folder = '';

to this:

private $cache_folder = 'static/xxxxx';

Be sure to replace the xxxxx text with the code you get from the Static Driver Installation page of the module.

Step 3 - Set Up The Rewrite Rules

Apache Configuration

If it doesn’t exist already, create an .htaccess file in your web root. Merge the following rules into the .htaccess file:

<IfModule mod_rewrite.c>
    RewriteEngine On

    #------------------- remove trailing slash (optional, but recommended) -------------------
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_URI} ^(.+)/$
    RewriteRule ^(.+)/$ /$1 [R=301,NE,L]

    #------------------- remove index.php -------------------
    #see http://ellislab.com/expressionengine/user-guide/urls/remove_index.php.html
    RewriteCond %{THE_REQUEST} ^GET.*index\.php [NC]
    #RewriteCond %{REQUEST_URI} !^/system [NC]
    RewriteRule (.*?)index\.php/*(.*) /$1$2 [R=301,NE,L]

    #------------------- CE Cache Static Driver -------------------
    RewriteCond %{REQUEST_METHOD} GET
    RewriteCond $1 !\.(css|js|gif|jpe?g|png) [NC]
    #RewriteCond %{REQUEST_URI} !^/system [NC]
    RewriteCond %{QUERY_STRING} !ACT|URL|CSS|preview [NC]
    RewriteCond %{DOCUMENT_ROOT}/static/xxxxx/static/$1/index\.html -f
    RewriteRule ^(.*?)/?$ /_static_cache_handler.php/$1/index.html [NE,L,QSA]

    #------------------- rewrite requests to index.php -------------------
    #see http://ellislab.com/expressionengine/user-guide/urls/remove_index.php.html
    RewriteCond $1 !\.(css|js|gif|jpe?g|png) [NC]
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteRule ^(.*)$ /index.php/$1 [L,QSA]
</IfModule>

Be sure to replace the xxxxx text with the code you get from the Static Driver Installation page of the module.

Note 1: The order of the .htaccess rules is important and should be preserved.

Note 2: If you are using a folder as your control panel login (as opposed to the default admin.php file), uncomment the #RewriteCond %{REQUEST_URI} !^/system [NC] lines above (by removing the octothorp # from the beginning of the lines). If your folder has a different name than the default ("system"), be sure to update those lines to reflect the correct folder name.

nginx Configuration

The following rules are closely based on the nginx config that Vector put together in their nginx configuration for ExpressionEngine repo.

You would add these rules in your server block, directly above your other location rules:

# Remove trailing slash
if ($request_method = GET) {
    rewrite ^/(.*)/$ /$1 permanent;
}

# Makes sure CE Cache won't work for non-GET requests
if ($request_method !~* GET) {
    set $request_var nonget;
}

# Do not trigger CE Cache for a URL containing ACT or URL
if ($args ~* (ACT|URI)) {
    set $uri_var acturl;
}

if (-e $document_root/static/ce_cache/xxxxxx/static/$request_uri$request_var$uri_var/index.html) {
    rewrite ^(.*) /_static_cache_handler.php?$1/index.html last;
}

Be sure to replace the xxxxx text with the code you get from the Static Driver Installation page of the module.

Step 4 - Add The Configuration Setting

Open up the config.php file (located in the /system/expressionengine/config directory by default), and add in the setting to enable static caching:

$config['ce_cache_static_enabled'] = 'yes';

Step 5 - Test

If the Static Driver cache directory is found, the driver should appear in the drivers table on the CE Cache Module home page. If it is not showing up, you can override the path in config.php with the following setting:

$config['ce_cache_static_path'] = '/server/path/to/web_root/static';

You'll want to replace that value with the actual path to your static folder.

Now add {exp:ce_cache:stat:ic} to one of your templates, and visit a URL that uses that template. The page should now be cached, and when you refresh the page again, it should be faster than ever. If it is not working, take a look at the next section (below) for troubleshooting tips.

Troubleshooting

Debug Mode

If something is not working (like a redirect loop, or the page redirects to the homepage), or you want to see how fast the page is being rendered by the driver, you can enable debug mode by opening /_static_cache_handler.php and changing private $debug = false; to private $debug = true;. Debug messages will now be shown in an HTML comment at the bottom of the rendered pages (view source to see). Don’t forget to set this back to false when you are done debugging.

Query String Tweak

If your site links return 404 pages, a "No Input File Specified" error, or all links return the same content, you may need to modify your .htaccess file. You’ll want to replace this line:

RewriteRule ^(.*)$ /index.php/$1 [L,QSA]

with this:

RewriteRule ^(.*)$ /index.php?/$1 [L,QSA]

and replace this line:

RewriteRule ^(.*?)/?$ /_static_cache_handler.php/$1/index.html [NE,L,QSA]

with this:

RewriteRule ^(.*?)/?$ /_static_cache_handler.php?/$1/index.html [NE,L,QSA]

(notice the added question marks after .php).

.htaccess Variable Issue

Several people have reported that they have problems with htaccess variables on Rackspace hosting (this could potentially be an issue with other hosts as well). In particular, the %{DOCUMENT_ROOT} variable is not set to the correct value and will need to be replace with the actual server path to the document root (ex: /path/to/web/root).

Logged Out Only

If you only want static caching to only be enabled when users are not logged in, you can add:

$config['ce_cache_static_logged_out_only'] = 'yes';

to your ExpressionEngine config.php file, and then add this conditional to your .htaccess:

RewriteCond %{HTTP_COOKIE} !exp_sessionid= [NC]

(add that line directly after the line RewriteCond %{QUERY_STRING} !ACT|URL|CSS|preview [NC]). If you are using a different cookie prefix (other than exp_), be sure to update your rewrite conditional accordingly.

Static Flat File Caching (Optional, Not Recommended)

The static driver normally utilizes the _static_cache_handler.php script to give the static driver some extra functionality (such as outputting the original page's headers and expiring the cache as needed). However, if you would rather not have any PHP overhead (though it’s quite negligible already), you can bypass the cache handler script completely. By doing this, all files cached with the static driver will not expire on their own; it effectively sets seconds="0" for every cache item. Cache breaking, tagging, and everything else should still work as expected though.

To use static flat file caching, you’ll need to add this to config.php:

$config['ce_cache_static_flat'] = 'yes';

Next, clear your static driver cache in the control panel. This is important, as the cache files will now be flat HTML (as opposed to containing serialized data). Finally, you’ll want to replace this line in your .htaccess file:

RewriteRule ^(.*?)/?$ /_static_cache_handler.php/$1/index.html [NE,L,QSA]

with this:

RewriteRule ^(.*?)/?$ /static/ce_cache/d09ba3/static/$1/index.html [NE,L,QSA]

to ensure that the .htaccess rule serves the static cache files.

How To Rename The Static Directory

By default, the static driver caches to the static directory in your web root. If you wish to change the name of the directory to something new, like new_name for example, you would do so by making changes in the following three places:

Step 1 - .htaccess

Change the instance of /static/ce_cache/ to /new_name/ce_cache

Step 2 - _static_cache_handler.php

Change this:

private $cache_folder = 'static';

to this:

private $cache_folder = 'new_name';

Important: Do not set the cache folder to the same directory as your web root directory, or set this as a blank string (eg: ''). The directory needs to be a dedicated cache directory. When the cache is cleared, all files in it are deleted.

Step 3 - config.php

Add the following config item:

$config['ce_cache_static_path'] = $_SERVER['DOCUMENT_ROOT'] . '/new_name';

or alternatively add:

$config['ce_cache_static_path'] = FCPATH . 'new_name';