3

I'm playing with fragment caching, I have read the guides and watched the railscast.

I'm trying to make some fragment caching on a basic show action:

Controller:

class PostsController < ApplicationController
  before_action :set_post, only: [:show]

  def show
  end

  private
    # Use callbacks to share common setup or constraints between actions.
    def set_post
      @post = Post.friendly.find(params[:id])
      # @post = Post.find(params[:id])
    end
end

View:

<% cache @post do %>

  <h1><%= @post.title %></h1>
  <%= @post.content %>

<% end %>

Problem: whereas the fragment is build and read (see the logs below) the database is still hit. Is this a normal behaviour?

I'm suspecting the before action filter to trigger the query before the cache is read.

I was suspecting the friendly id system but the query happen with the classic find too.

How should I cache this to avoid query?

Logs:

Started GET "/articles/article-3" for 127.0.0.1 at 2014-08-27 10:05:14 -0400
Processing by PostsController#show as HTML
Parameters: {"id"=>"article-3"}
Post Load (1.2ms)  SELECT  "posts".* FROM "posts"  WHERE "posts"."slug" = 'article-3'  ORDER BY "posts"."id" ASC LIMIT 1
Cache digest for app/views/posts/show.html.erb: 18a5c19e6efef2fd1ac4711102048e1c
Read fragment views/posts/3-20140730194235000000000/18a5c19e6efef2fd1ac4711102048e1c (0.5ms)
Rendered posts/show.html.erb within layouts/application (4.8ms)
coding addicted
  • 3,422
  • 2
  • 36
  • 47

1 Answers1

1

Unless your application has only one post, I really don't think you would want to cache the first call - fragment caching will cache a given post, but it still needs to know which post is being accessed.

If you did cache this, every time you loaded the post#show page, regardless of what post you asked for, you would see one post - the post that was cached.

dax
  • 10,779
  • 8
  • 51
  • 86
  • I get the point that we need to know which post we are trying to access to to get the right cache. But actually if I do model caching (Rails.cache.fetch() {Myquery}) instead of fragment caching I can check if the cache exists and trigger the query only if it doesn't. But that's more complexity than fragment caching and auto expiration. Every post I read about fragment caching use this kind of exemple with cache @the-object-you're-caching but doesn't talk about the query. Your point is to tell that the query is unavoidable but the caching is still usefull for the gain of time of the rendering? – coding addicted Aug 27 '14 at 15:24
  • probably it depends. your db call is only 1.2 ms, your view takes 4.8 ms. I think that I wouldn't bother with caching for something like this, but it could be you're using a pared down example. The database call isn't going to change (unless more is required from it) - the view could become more complex in which case you might find that the time you save by caching becomes worth your while. – dax Aug 27 '14 at 15:51