Drupal HTTP Cache

Drupal doesn't support HTTP caching out of the box like Plone, but it can be extended for this, using a small patch and some Apache2.2 configuration.

Apache 2.2 Configuration

First, the apache configuration file httpd.conf needs to be configured to allow HTTP caching via mod_cache and mod_disk_cache.

  # configure disk caching directory
  CacheRoot               /var/cache/apache2/mod_disk_cache/WEBSITENAME
  # enable caching for topmost URLs
  CacheEnable             disk /
  # disable caching for some sub URLs
  CacheDisable            /pipermail
Drupal-5.3 Modifications

Second, the attached diff /exchange/httpcache-5.3.diff needs to be applied, it changes a couple things:

  1. Allow specification of anon_http_cache_seconds in the config section of drupal-5.3/sites/default/settings.php. A value >0 causes anonymously accessed pages to be HTTP-cached for this number of seconds.
  2. The logic in drupal-5.3/includes/bootstrap.inc is adapted to avoid always forcing html page expiration and allow HTTP caching for anon_http_cache_seconds seconds.
  3. A rewrite rule is added to drupal-5.3/.htaccess to allow caching of the Drupal root URL.
  4. Also, bootstrap.inc is adapted to avoid caching if the X-Script-Chrome: header is specified, this is needed in case a theme is used that changes look in correspondence to this header.
Benchmarking

To verify the usefulness and quantify the gain of the above caching setup, the Apache Benchmarking Tool can be used, for example like this:

    ab -n 100 http://testbit.eu/book/Rapicorn-Tutorial

The first benchmark is executed with Drupal caching completely turned off (adjustable under drupal-5.3/admin/settings/performance). This means that each page is rerendered completely in PHP:

  # Caching-mode:Disabled Aggregate-and-compress-CSS-files:Disabled
  Time taken for tests:   81.608534 seconds
  Complete requests:      100
  Total transferred:      843900 bytes
  HTML transferred:       780800 bytes
  Requests per second:    1.23 [#/sec] (mean)
  Time per request:       816.085 [ms] (mean)
  Transfer rate:          10.10 [Kbytes/sec] received

Then with normal Drupal caching enabled, cached pages are delivered from a page-cache MySQL-DB table with very little PHP code executed:

  # Caching-mode:Normal Aggregate-and-compress-CSS-files:Enabled
  Time taken for tests:   8.862656 seconds
  Complete requests:      100
  Total transferred:      767100 bytes
  HTML transferred:       706200 bytes
  Requests per second:    11.28 [#/sec] (mean)
  Time per request:       88.627 [ms] (mean)
  Transfer rate:          84.51 [Kbytes/sec] received

Page delivery is roughly 9 times faster now.

Finally, the HTTP cache is enabled e.g. by a value like anon_http_cache_seconds = 60 in settings.php and by CacheEnable in the Apache configuration:

  # Caching-mode:Normal Aggregate-and-compress-CSS-files:Enabled CacheEnable-disk-/
  Time taken for tests:   0.264496 seconds
  Complete requests:      100
  Total transferred:      769600 bytes
  HTML transferred:       707900 bytes
  Requests per second:    378.08 [#/sec] (mean)
  Time per request:       2.645 [ms] (mean)
  Transfer rate:          2839.36 [Kbytes/sec] received

With Apache handling the majority of page deliveries now, delivery is sped up by a factor of 300, compared to the cacheless setup (and still 33 times faster than with normal Drupal caching).

Side Effects

It should be noted that Drupal modules (or PHP code in general) that takes action upon equal anonymous page requests will be called less often with activated HTTP caching. That is because Drupal isn't even activated when cached pages can be served by Apache. In practice, no significant problems are expected from active HTTP caching, but for examples page counters can be too small by an order of magnitude. If accurate page access numbers are needed, they should be generated from statistics extraction from Apache's log files (cached page delivery is still regularly logged by Apache).

AttachmentSize
httpcache-5.3.diff4.53 KB

Comment viewing options

Select your preferred way to display the comments and click "Save settings" to activate your changes.

Drupal.org submission

Submission of this page and the patch to drupal.org against drupal-5.3 is pending. I'd like to work out the caching details here first and provide solid documentation with regards to the effects.