検索エンジンのsunspotを使ってみた。
モデル定義
class Post < ActiveRecord::Base
searchable do
text :title, :body
boolean :featured
integer :blog_id
integer :author_id
integer :category_ids, :multiple => true
double :average_rating
time :published_at
time :expired_at
end
end
こんな感じで定義する
relationの定義を行いたいときは
text :comments do
comments.map { |comment| comment.body }
end
string :comment_title, multiple: true do
comments.map { |comment| comment.title }
end
string :author_name do
author.name
end
こんな感じで。text型はmultipleオプションを付けられない。
アソシエーション先がnilの場合があるのであれば、tryとか使ってうまく回避。
検索してみる
search = Post.solr_search do |query|
fulltext('hoge', fields: :title)
end
単純にtext型の複合(AND)条件であれば、
search = Post.solr_search do |query|
fulltext('hoge', fields: :title)
fulltext('fuga', fileds: :body)
end
これでOK
OR条件にするのであれば
search = Post.solr_search do |query|
query.any do
fulltext('hoge', fields: :title)
fulltext('fuga', fileds: :body)
end
end
fulltext以外の項目ならば、any do がany_of doに変わります・・・。
search = Post.solr_search do |query|
query.any_of do
with(:blog_id, 111)
with(:author_id, 222)
end
end
これらを組み合わせて使うと・・・
search = Post.solr_search do |query|
query.any do
fulltext('hoge', fields: :title)
fulltext('fuga', fileds: :body)
end
query.with(:blog_id, 111)
query.with(:author_id, 222)
end
ページネートにも対応しているので、
項目を追加してやると良いです。
ちなみにデフォルトでページネートされ、1ページに全件を指定はできないそうなので、
その場合はper_pageに最大値の1000万を指定するか、Post.countとか渡して対応しましょう
paginate(page:1, per_page:50)
あとは結果を取得するだけ(results or hits)
search.results
管理画面なども用意されているので、ブラウザでアクセスして
クエリやindexの確認ができます。
なかなか使う機会は限られるかもしれませんが、参考まで。