如何在Rails中缓存无限数量的静态页面

时间:2015-07-30 15:14:05

标签: ruby-on-rails caching

我有一个Rails应用程序,允许用户创建无限数量的静态页面(我将这些页面存储在postgres数据库中),因为这些页面是静态的我想使用页面缓存,但我不确定是什么限制数量/ Rails中缓存页面的大小,我可以缓存无限数量的页面吗?

2 个答案:

答案 0 :(得分:1)

我们在https://reinteractive.net的主要公司博客上执行此操作。

您可能想要做的是在要缓存的页面的show动作上执行片段缓存。这有一些陷阱,如果底层页面发生变化,其中最大的一个就是缓存。

它的工作原理如下:

routes.rb文件中:

AppName::Application.routes.draw do
  get "page/:id" => "pages#show"
end

在控制器(app/controllers/pages_controller.rb)中:

class PagesController < ApplicationController::Base
  def show
    @page = Page.find(params[:id])
  end
end

请注意,在控制器中,您在每次请求时都会访问数据库,但这应该是一个非常快速的请求,并且具有正确的索引。

然后在视图中(app/views/pages/show.html.erb):

<% cache("pages/show/#{@page.id}-#{@page.updated_at.to_i}") do %>
  <%# Render your complex page here %>
<% end %>

通过缓存这样的片段获得的是渲染的输出存储在缓存中,如果此页面需要一段时间来渲染,您可以节省大量时间,特别是如果渲染需要100毫秒或更长时间页面及其所有部分,您第一次付费,然后在几毫秒内加载。

注意我们正在检查页面的最后更新时间?这样,如果您想要使此缓存失效(并再次渲染),您需要做的就是在页面对象上调用page.touch以更新updated_at时间。

如果您还有其他任何可以更新的对象(比如说page.header_image或者其他东西),那么您也可以将这些相关对象上的updated_at也放入缓存键,或者当您使用时将它们手动过期更新页面。

updated_at添加到缓存键中的替代方法是在模型中使它们到期,如下所示:

class Page < ActiveRecord::Base
  after_save :expire_cache
  def expire_cache
    Rails.cache.delete("CACHE_KEY")
  end
end

但这有它自己的挑战。

祝你好运!

答案 1 :(得分:1)

@MikelLindsaar的答案很好,但对于可以更轻松处理的事情来说有点太多工作,ActiveRecord对象有一个名为cache_key的方法,如果记录被触及,则自动为每条记录生成一个唯一的密钥。更新后,生成的密钥将不同,此密钥用于生成整个视图缓存密钥,这是一个具有很多参数的函数,如对象id,updated_at (来自cache_key,以及视图的hash (如果更新视图文件,缓存会失效,而不仅仅是数据库),所以不用担心任何过时的数据,所有你需要做的就是:

控制器

class PagesController < ApplicationController::Base
  def show
    @page = Page.find(params[:id])
  end
end

视图

<% cache @page do %>
  <%# Render your page here %>
<% end %>

如果您有多个页面使用相同的页面对象,则可以使用复合缓存键,例如

<% cache(prefix: 'page/show', page: @page) %>

和rails将处理缓存密钥的生成。

有关此内容的更多信息http://guides.rubyonrails.org/caching_with_rails.html#fragment-caching