Railsでスイーパーを使ってみる
kaeruspoonにスイーパーを導入してみました。実はずいぶん昔に使っていたことがあったのだけど、この新しいkaeruspoonになってからはまだ導入してなかったのです。
スイーパーというのは、主にキャッシュと併用して使うものです。オブサーバとDBのフックメソッドを使って実現されていて、フックメソッドにとらえられるようなイベント(DBへのCRUD)のときにやりたい処理(expireを使ったキャッシュの失効しかないと思うけど)を一箇所にまとめることができます。
2007年05月10日の日記の日記にフラグメントキャッシュのことを書いているけど、スイーパーを使うともっとシンプルにできます。スイーパーはDBを監視するやつなので、普通はRAILSROOT/app/modelsの下に置きます。
class SidebarSweeper < ActionController::Caching::Sweeper
observe AmazonList, YoutubeList, Tag
def after_save(dumy)
free_fragment
end
def after_destroy(dumy)
free_fragment
end
private
def free_fragment
expire_fragment 'sidebar_contents'
end
end
スイーパーはActionController::Caching::Sweeperのサブクラスとして定義します。監視したいテーブルをobserveを使って指定します。これはオブサーバと一緒ですね。フックメソッドを定義するところも同じです。
キャッシュする箇所は、ビューで指定します。
<% cache 'sidebar_contents' do -%>
<%= view_amazon_items @amazon_items %>
<%= view_youtube_items @youtube_items %>
<%= view_all_tags @all_tags %>
<% end %>
フラグメントキャッシュはそれを識別するためにコントローラとアクションを指定することが多いと思いますが、ここでキャッシュしたいものは複数のアクションから呼ばれるので、単に名前をつけるだけにしています。こっちのほうが結局シンプルでいいかも。
このままではスイーパーは働いてくれません。四六時中監視するわけじゃなくて、こちらが指定したときにしか監視してくれないのです。それはコントローラで指定してあげます。
require 'sidebar'
class AdminDiariesController < ApplicationController
cache_sweeper :sidebar_sweeper, :only =>[:update, :destroy]
....(省略)....
cache_sweeperを使って、働かせたいスイーパーと、どのアクションのときに働かせるかを指定します。これですべてOK。requireしているのは、Railsがsidebar_sweeperを見つけられないときがあるためです。