2011年1月16日日曜日

meta_where を使った検索

検索というかなんというか。

u1 = User.new :name => "user1"
u1.comments << Comment.create :message => "hoge hoge"
u1.comments << Comment.create :message => "hoge moge"
u1.save


u2 = User.new :name => "user2"
u2.comments << Comment.create :message => "hoge fuga"
u2.save


u3 = User.create :name => "user3"

こんな感じのデータがあったとして、

User.search("user") # => [u1, u2, u3]
User.search("hoge") # => [u1, u2]

というような結果を求めるとき、 User.search の実装は以下のようになる。

scope :search, lambda {|query|
  includes(:comments).group("users.id").where(:name.like => "%#{query}%" | :comments => {:message.like => "%#{query}%"})
}

Comment に複数の属性があるときは :comments => [{:message.like => "%#{query}%"} | {:updated_at.lt => Date.today}] のように渡せばいい。ゴチャゴチャするけど。

ちなみに includes ではなく joins を使うと、検索結果にコメントの設定されていない u3 がヒットせず、 group を付けないと、 "hoge" の検索結果が [u1, u1, u2] になってしまうので、 users.id でグループ化する必要がある。らしい。

押してねっ→BlogPeople「趣味の世界」ブログランキング

0 件のコメント:

コメントを投稿