Say I have two production webservers (web1
and web2
) and a static asset origin server (origin1
), and I want to deploy new code that references new css/js/images.
After updating web1
and putting it back on rotation, and right before I take web2
out of rotation, there'll be a brief window when the load balancer will send requests to both web1
with new code and web2
with old code:
web1
serves html that requestshttp://somecdn/images/foo.jpg?v=newhash
web2
serves html that requestshttp://somecdn/images/foo.jpg?v=oldhash
So in this brief window, there's a chance that somecdn
might request for foo.jpg?v=oldhash
, but actually gets served the new image that just got deployed to origin1
. That's not good.
The obvious solution seems to be keeping both versions of the assets available:
- Version the releases like
/2.1/images/foo.jpg
and/2.2/images/foo.jpg
, which defeats the purpose of cache-busting using the file hash, or - Keep both versions by adding the hash to the file name, eg. keep both
/images/foo.oldhash.jpg
and/images/foo.newhash.jpg
in the file system, which would leave a bunch of old files that needs pruning. - Setup Varnish to keep older versions of css/js/images around (feels iffy).
Is there a better strategy, assuming that I can't disable the site completely while deploying?
(StackExchange uses this file hash approach for cache-busting…)