Caching Query Strings in Apache Proxy – How to

apache-2.2mod-cache

I had problems getting disk_cache to work, and I was not able to see why. This was the relevant section from my config

# Caching
CacheRoot   "/var/cache/apache2/"
CacheEnable disk /

I was timing a request such as the following, but caching seemed not to take effect, since the response used 7 seconds no matter what.

time curl -k https://customer1.myhosts.com/appserver/slow_request?param1=fooBar

After enabling debug logging I found the following statement in the logs, explaining why no caching was being done:

[Fri Aug 24 17:22:01 2012] [debug] mod_cache.c(552): cache: not cached. Reason: Query string present but no explicit
expiration time

It turns out this is mentioned in the Apache Caching Guide:

If the URL included a query string (e.g. from a HTML form GET method)
it will not be cached unless the response specifies an explicit
expiration by including an "Expires:" header or the max-age or
s-maxage directive of the "Cache-Control:" header, as per RFC2616
sections 13.9 and 13.2.1.

OK, so I add the following (taken from this article) in Apache

Header set Cache-Control "max-age=290304000"

It still does not work, this time I get the message

"… not cached. Reason: No Last-Modified, Etag, or Expires headers"

Now, this is a different story. How can I solve this without touching the application server code?

Best Answer

The only way I could get Apache to cache the responses from the application server was by actually adding the headers Apache asked for in the log to the responses. It turned out to be quite easy by creating a JAX-RS filter.

So after adding Last-Modified and an Expires header, the only thing needed was the following two lines in my apache config.

CacheRoot   "/var/cache/apache2/"
CacheEnable disk /