railsからsolrを使っているとき、インデックス作成は避けて通れないですね。
rails側とsolr側でそれぞれどのくらいかかっているか気になったので調べてみました。
設定
bundle exec rake sunspot:reindex
でのインデックス作成を検証します。
- Solr 5.4
- sunspot 2.0.0
- ruby 2.1.5
- java 1.8
- メモリ4GB
- 2コア
- クロック周波数3GHz
- CentOS 6.4
sunspot:reindexの仕組み
デフォルトでは、ドキュメント50個ずつ、それを登録するためのリクエストをSolrに投げます。
つまり、ドキュメントの総数 / 50 回のリクエストをするということです。
まとめる件数はつぎのようにして変更できます。
sunspot:reindex[500]
くわしくはこちらを。
https://github.com/sunspot/sunspot#reindexing-objects
色々試した結果、10000ずつでやることにしました。
シングルコアの場合
ドキュメントの件数は50万件、できあがったインデックスのサイズは60MBになりました。
対象のテーブルによってデータサイズがかわってくるのですが、大体は下記の範囲におさまりました。
- sunspotがリクエストをつくるまで: 10~12秒
- solrがリクエストを処理するまで: 0.4~0.8秒
sunspot側の方がめっちゃ時間かかっていたようです。
コレクション1の2shard
埋め込みのzookeeprをつかって、SolrCloudモードにして2shardでもやってみました。
結果は上記とたいして変わらず。
ただ、SolrCloudにしたことで、インデックス登録のリクエストの振り分けがされて動きが変わっています。
10000個のドキュメントを、だいたい100個ずつに分けられて、1,2のshardに均等に分けられて登録されます。その結果が10000件の登録リクエストのレスポンスとしてでてきます。
つまり、秒間100リクエストくらいはSolrはさばけるということのようです。
まとめ
まずは、sunspot側を改善するしかないようです。メモリ、コア数、クロック周波数を上げると改善されはしました。メモリを増やせば、reindexのバッチサイズを上げての速度改善が見込めるようです。
直列がやっているのがつらいので、並列化するgemもあるようです。
ともあれ、Solr側で時間がかかっているかどうかの切り分けが、sunspotをつかっているときのポイントのようです。