Old School Cache Invalidation in a world of Rails 5.2 Recyclable Cache Keys

One of the hallmark features of Rails 5.2 was the introduction of recyclable cache keys.

Once the new cache API was integrated into Basecamp, DHH had this to say about it:

We went from only being able to keep 18 hours of caching to, I believe, 3 weeks. It was the single biggest performance boost that Basecamp 3 has ever seen.

Put simply, the previous cache key generation (unless you over-wrote it) used the updated_at timestamp to differentiate the specific version fo the object. So for example [class]/[id]-[timestamp], like users/5-20110218104500 or thing/15-20110218104500, which is what Active Record in Rails used to do by default when you call #cache_key.

With Rails 5.2 this no longer works as you expect. Instead, it’s simply [class]/[id] -the timestamp is dropped.

The basic idea behind it is that the cache object can be updated directly; and thus cache keys can be reused, dramatically lowering the quantity of cache garbage and increasing the amount of useful objects stored in the cache; which should let you see a significant performance hit by increasing your successful cache hits.

The only drawback is that the cache needs to be updated using the new cache API – if you don’t do this, you will suddenly see that your cached objects no longer ‘automatically’ expire.

Whilst I do recommend upgrading your codebase to use the new cache API, you can disable it and return to the older #cache_key style (using update_at timestamp) by simply adding this to your config/environments environment file:

config.active_record.cache_versioning = false

This should get you working in the old way – I will write a post on how to maximise use of the new Rails cache API in a future post.

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.