Lately, I’ve been much concerned with improving my cache-hit ratios on CDNs. And I recently discovered the “stale-while-revalidate” directive. While a CDN like Cloudflare is easy to set up and use, they don’t provide much in the way of statistics. Specifically, you can’t easily get cache hit ratios for static assets, because we don’t know if their analytics graph includes requests for dynamic pages.
Moreover, I have a suspicion that Cloudflare doesn’t hold your static assets for very long in their EDGE cache if there aren’t too many requests. For example, by default, the Time to Live (TTL) on Cloudflare servers is a measly 120 minutes – or just two hours. For this reason, I’m experimenting with other CDN providers, where I can get accurate statistics.
What Does “stale-while-revalidate” Do?
Simply put, the “stale-while-revalidate” directive allows a CDN to serve an expired asset to a client, while it revalidates the file in the background.
So let’s say we have a CSS file that’s lying on the EDGE cache and expires in one week. Under normal circumstances, after one week, the first request for that CSS file will take longer than usual to service. Because the CDN will see that it has expired, request the origin for the new file, wait for the response, and then send the fresh one to the client.
And when you have dozens or even hundreds of static assets, with say 20 POPs all over the world, that’s a very large number of requests that take a long time to get going.
Instead of this, we can use “stale-while-revalidate” to tell the server: “Look, I know this file has expired. But for now, let the client have the older version of the file, just this once. In the meantime, revalidate the file from the origin in the background, so that the next client to request the file will have the fresh one”.
In essence, “stale-while-revalidate” allows you to have extremely short “max-age” directives, because it removes the disadvantage of longer wait times for clients if the file needs to be refreshed. Now that can happen in the background without impacting load times.
This goes hand in hand with the other related directive.
Sometimes for one reason or the other, your origin server will return an error to the CDN for a static file. Normally if this happens, the CDN will pass on the error to the client. That’s not good!
Now you can instruct your CDNs to continue serving the stale cached file even if the origin returns an error. And you can specify a time in seconds to tell the CDN for how long it should keep doing this before returning an error.
Both the “stale-while-revalidate” and the “stale-if-error” directives are great for improving your cache hit ratio and delivering great speeds to your customers.
Implementing the “stale” Directives in .htaccess
Here’s what I use in my .htaccess file to implement these instructions:
Add cache control and stale while revalidate or error directives <filesMatch ".(ico|pdf|flv|jpg|jpeg|png|gif|js|css|swf)$"> Header set Cache-Control "max-age=2592000, stale-while-revalidate=604800, stale-if-error=604800" </filesMatch>
Make sure this doesn’t conflict with any other cache control headers you might be sending. Specifically, check your plugins, and any other directives in .htaccess which might give different directions.
Integrating with Cloudflare
You can use a CDN in conjunction with Cloudflare. I do. In which case, you want Cloudflare to meddle as little as possible with the responses sent from your origin. To make sure of this, go to the “Caching” section of Cloudflare and scroll down to the “Browser Cache Expiration” section. Set the dropdown box to “Respect Existing Headers” as shown here:
Now Cloudflare will pass your headers onto your CDN as expected.
Verifying the Headers
If all goes well, you should be able to check the status of each static file in your browser via the Chrome Development tools under the Network tab like this:
As you can see, the “stale-while-revalidate” headers are making it correctly from the .htaccess file!
I’m a NameHero team member, and an expert on WordPress and web hosting. I’ve been in this industry since 2008. I’ve also developed apps on Android and have written extensive tutorials on managing Linux servers. You can contact me on my website WP-Tweaks.com!