Solrのpdateについて思ったこと。

最近自分が関わっている会社の案件で、検索機能のバックエンドにSolr使うことになりました。僕がSolrのSchemaを書いていたのですが、日付型のpdate(solr.DateField)について少し気になったことがあったので書いてみようと思います。

Solr使ってみた感想

そもそも僕は検索エンジンはSennaぐらいしか使ったことが無かったのですが、Solrは全文検索以外に、検索結果のフィルタやファセット検索が簡単に使えたりと個人的にはSennaよりも好印象です。

Solrの日付型の一つpdateについて

検索の要件に特定の日付を基準にして検索したりソートしたりということは結構あると思います。僕のお仕事でも日付型を使う要件があります。Solrの日付型はいくつかあると思うのですが、僕はとりあえずschemaを書きたいと思って目についたpdateを使ってみることにしました。pdateはデフォルトだとsolr.DateFieldクラスです。

FieldType that can represent any Date/Time with millisecond precision.

pdateはミリ秒まで扱えるらしいのですが、僕の要件では秒まで扱えればいいので特にそこは重要視したところではありませんでした。単純に使ってみただけです。pdateはUTCで表現できる感じだったので、http://ja.wikipedia.org/wiki/ISO_8601をもとにフォーマットを次のようにしてみました。

  • YYYY-MM-DDTHH:MM:SSZ+0900 (JSTなので+9時間)

結果は文書の追加時にフォーマットが間違っているということで怒られてしまいました。どうも、+0900や+09:00といった表現はSolrのsolr.DateFieldでは扱えないようです。

  • YYYY-MM-DDTHH:MM:SSZ

上記のフォーマットだと、例外も発生せずにちゃんと文書の追加も行えました。でもこれだとJSTは表現できない?と思ってもうちょっとちゃんとドキュメントを読んでみるとDateMathParserのフォーマットを使って日付の計算が出来るようでした、UTCの時刻を表現しようとすれば次のように表現できます。

  • YYYY-MM-DDTHH:MM:SSZ-9HOUR

この日付の表現で文書を追加すると検索結果では-9時間した値が返ってきます。上記のwikipediaにある様なJSTの表現(YYYY-MM-DDTHH:MM:SSZ+0900)は難しいようです。(やり方はある?)
このことからSolrのsolr.DateFieldは複数のタイムゾーンを表現するには向いていないように思えました。なのでSolrに入れる日付については本来ならJSTの時間から -9時間したものをSolrには入れておき、検索時には検索クエリの日付にDateMathParserの表現でをつけてJST-9HOURするとかすればいいのかもしれないですが、それだと検索結果の日付filedの値を+9時間したりする必要があったりと結構複雑になりそうです。

  • インデックス
    • JST-9HOUR => UTCで保存
  • 検索クエリ
    • JST-9HOUR => UTCで検索
  • 検索結果
    • UTC+9HOUR => JSTで表示

しかし、本当に上記のように複雑なことをする必要があるのかなと思って自問自答してみました。実際案件で使ってる日付表現はJSTです。JSTとしてあつかった方が変換の必要も無く簡単です。
他のタイムゾーンが増えてもその差異はアプリケーション側で統一できますし、その際に決まった表現がUTCだった場合はそのルールでインデックスを作り直せばいいだけなので問題無いかなと思い結局JSTの日時をそのまま入れて検索することにしました。たぶん、検索エンジンとしても異なるタイムゾーンを同時に扱うなんて面倒なことはおそらくしたくないんだろうなぁと思いました。

ちょっと書きなぐる感じになってしまいましたが、pdateを使うときに+0900の様な表現が使えなくて焦ったけど、まあいいかという話でした。

solr.TrieDateFieldも余裕があれば試してみようかなと思います。