页眉/页脚中的信息源自数据库中的一堆字典表,并且数据很少会更改。我认为这是缓存的绝佳机会,这样就渲染页眉/页脚而言,每个页面都不会接触数据库。
Rails 指南给出了片段缓存的示例,因此我认为我的导航链接会类似于...
<% @categories.each do |category| %>
<% cache category do %>
<li class="nav-link">
<%= link_to category.name, category_path(category) %>
</li>
<% end %>
<% end %>
但我不明白这如何阻止与数据库的联系或优化任何内容。 Controller 在 View 渲染之前调用 @categories,这意味着每个页面请求都会进行 SQL 查询...一些 HTML 正在被缓存,但是即使对于较大的代码片段,渲染过程是否真的能节省大量时间?我觉得数据库的压力是您真正想要限制的,特别是在处理大量并发流量时。
对于页脚/导航部分等内容,适当的缓存策略是什么?
最佳答案
Rails Guides 的片段缓存示例仅指缓存生成的用于显示对象的 View ,而不是查询,这就是为什么您看不到它缓存查询的位置,因为它没有。
您可以使用低级缓存来缓存 @categories
查询 https://guides.rubyonrails.org/caching_with_rails.html#low-level-caching
它可以缓存任何类型的信息,因此,您可以拥有类似的内容
class Category < ActiveRecord::Base
def self.for_navbar
Rails.cache.fetch("#{nav_cache_key}/categories_for_navbar", expires_in: 1.week) do
self.whatever_scope_you_need
end
end
end
您需要更改的是用于标识缓存的 nav_cache_key
var。我不确定这方面的最佳实践,但我会在第一次需要时使用当前 time_stamp 设置一个类变量,并在应该删除缓存时更新它。
类似的东西
def self.navbar_cache_key
@@navbar_cache_key ||= Time.now
end
after_update :change_cache_key
def change_cache_key
@@navbar_cache_key = Time.now
end
这样,每次更新类别时,都会更改该类的@@navbar_cache_key
,并且缓存将针对新键进行更新。我不确定需要更新缓存的真实条件是什么,也许 after_update
回调不是最好的,或者您需要一些额外的操作。
这将仅缓存查询(不确定您是否需要缓存数组或缓存查询的工作原理相同,可能您最后需要一个 .to_a
),您仍然可以使用片段如果您也想缓存 li
元素,请进行缓存。
我想你甚至可以缓存类别的完整 html,因为低级缓存接受任何类型的信息,你只需要找到正确的位置来使用 Rails.cache.fetch
和保存/更新缓存 key 的正确位置。
关于ruby-on-rails - Rail 片段缓存如何使您的应用程序受益,即防止数据库调用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52031517/