我正在通过使用Rails4的敏捷Web开发工作,我刚刚阅读了(第一部分)有关缓存视图部分的内容,以避免压倒数据库。 我当然在开发环境的配置中将缓存选项设置为true。
问题在于缓存似乎无法正常工作。 这是我的app / views / store / index.html.erb文件,与本书中给出的文件完全相同,以启用缓存:
<% if notice %>
<p id="notice"><%= notice %></p>
<% end %>
<h1>Your Pragmatic Catalog</h1>
<% cache ['store', Product.latest] do %>
<% @products.each do |product| %>
<% cache ['entry', product] do %>
<div class="entry">
<%= image_tag(product.image_url) %>
<h3><%= product.title %></h3>
<%= sanitize(product.description) %>
<div class="price_line">
<span class="price"><%= number_to_currency(product.price) %></span>
</div>
</div>
<% end %>
<% end %>
<% end %>
这是rails服务器日志,清楚地显示数据库被多次访问(尽管一行提到了缓存):http://pastebin.com/v2jGiHKL
这是我的app / views / store / index.html.erb文件,其中我尝试了其他用于缓存的内容:
<% if notice %>
<p id="notice"><%= notice %></p>
<% end %>
<h1>Your Pragmatic Catalog</h1>
<% cache('caching') do %>
<% @products.each do |product| %>
<div class="entry">
<%= image_tag(product.image_url) %>
<h3><%= product.title %></h3>
<%= sanitize(product.description) %>
<div class="price_line">
<span class="price"><%= number_to_currency(product.price) %></span>
</div>
</div>
<% end %>
<% end %>
以下是相应的日志,显示缓存成功(因为未查询数据库):http://pastebin.com/ZTk9A9RA
有人可以解释为什么一个似乎工作而不是另一个,或者第一个应该如何工作?谢谢:))
请注意,在本书中,它表示启用了缓存后,如果更改是在缓存块内进行的,则重新加载商店页面不应显示store / index.html.erb的新部分;但两种情况都有。有什么想法吗?
答案 0 :(得分:1)
传递给cache
api的参数是缓存密钥。该密钥的散列函数是存储缓存片段的位置,以及它将在何处查找。
在您的代码(cache('caching')
)中,缓存密钥是硬编码的,并且永远不会更改,因此,除非缓存无效(在代码中手动执行,或者其TTL已通过) - 相同的片段将被发送给客户。
在本书的代码(cache ['store', Product.latest]
)中,密钥取决于最新产品。这意味着如果最新产品发生更改(另一个产品已添加或更新),则下一个调用将自动“知道”不从缓存中获取页面,而是重新创建缓存。
日志中显示的内容:
[1m[35mProduct Load (0.3ms)[0m SELECT "products".* FROM "products" ORDER BY "products"."updated_at" DESC LIMIT 1
实际上是Product.latest
的{{1}},不是的结果。
总结一下 - 两个代码片段都被缓存,但在示例代码中, 一个(小)命中数据库以验证缓存的有效性,无论页面是缓存的还是不
如果您自己使缓存失效,您可以保留代码的硬编码版本,但如果没有,您最好考虑失效方案,无论是示例代码建议还是别的。