So I have to use the cached_books method in the controller as follows:
Yes, you can. Although there are some mistakes you should be aware of. Book - ActiveRecord . When you call Book.something (e.g. Book.all or just even Book.order(:title) ), it returns ActiveRecord::Relation , which is basically a wrapper for the Book array (this wrapper prevents unnecessary queries from running, increasing performance) .
You cannot save the entire query result in Redis. Say you can save a JSON string of a hash array with model attributes, for example.
[{ id: 1, title: 'How to make a sandwich", author: 'Mr. cooker' }, { id: 2, title: 'London Bridge', author: 'Fergie' }]
And then you can "decrypt" this thing in the array after. Sort of
def cached_books(key) # I suggest you to native wrapper if result = $redis.hget 'books_cache', key result.map do { |x| Book.new(x) } end end
And you also have to serialize the attributes before putting them in the cache.
So now you have collections that can be repeated in a view with the same data, although you cannot call order in a cached collection, since it is a simple array (you can call sort , but the idea is to cache already sorted data).
Well ... is it worth it? In fact, not really. If you need to cache this part - perhaps the best way is to cache the displayed page, rather than the query result.
If you use cached_title and cached_author - this is a good question. First of all, it depends on what cached_title can be. If it is a line - there you cannot cache. You get a Book request through the database, or you get a Book from the cache - the title will be presented in some way, as this is a simple type. But let's take a closer look at author . Most likely, this will be related to another author model, and this is the place where the cache blends perfectly. You can override the author method inside the book (or define a new one and avoid the unpleasant effects that Rails may have in complex queries in the future) and see if there is a cache. If so, return the cache. If not, request the database, save the result in the cache and return it.
def author Rails.cache.fetch("#{author_id}/info", expires_in: 12.hours) do
Or less convenient, but more "safe":
def cached_author Rails.cache.fetch("#{author_id}/info", expires_in: 12.hours) do author end end