2016年12月16日
LuceneSolr勉強会 第19回 #SolrJP
ヤフー株式会社 石川 貴大
SolrのAtomicUpdateを
50000倍速くした話
自己紹介
氏名
石川 貴大
所属
ヤフー株式会社
D&S統括本部
サイエンス本部リーダー
LuceneSolrRevolution2016で
撮ってもらった
今日のはなし
今日の話のながれ
• AtomicUpdateについて
• AtomicUpdateを速くした話(Solr-9592)
• 現状のSolrにおける部分更新処理の整理
AtomicUpdate?
既に存在するDocumentに対して、下記の操作をAtomicに実
行することができる機能
操作 概要
set 値の置き換え
add Multivalueなフィールドに値を追加
remove 値の削除
removeregex 正規表現にマッチする値の削除
inc 数値の和算
https://cwiki.apache.org/confluence/display/solr/Updating+Parts+of+Documents
AtomicUpdate?
{"id":"mydoc",
"price":{"set":99},
"popularity":{"inc":20},
"categories":{"add":["toys","games"]},
"promo_ids":{"remove":"a123x"},
"tags":{"remove":["free_to_try","on_sale"]}
}
具体的な更新データは例えば以下のような形
AtomicUpdateの仕組み
Solr
id:1のデータ全部ちょうだい(realtime get)
id:1, xxx:100, yyy:0,,,,,
id:1, xxx:100, yyy:1,,,,,
AtomicUpdate
AtomicUpdateの実態は、ざっくり言うと該当IDの全フィールド
を取得してから、再フィードし直す機能
AtomicUpdateを速くした話
AtomicUpdateを使うに至った経緯
• サービス向けに性能評価をしていて、部分更新が必要
だった
• SOLR-8276で、docValuesにも対応していたので、
docValuesで使用
AtomicUpdateを速くした話
性能評価時のセットアップ
• Solr 6.0.0
• SolrCloudで、40台クラスタ(zookeeper別)
• 2replica 40shard構成
• 各shard 500MByte程度のIndex
• Non Stored DocValuesの割合が多い
性能試験結果
部分更新の性能試験結果
• そもそも、性能うんぬん以前に、数十秒返ってこな
い
• しいて言えば、0.1dpsくらい。。
• 1割遅くなるとかそれくらいだと思ってた・・・
•これはヤバい
検証
いろいろ検証
• JFRのホットメソッド
• RemoteDebug
• ソースコード読む
• -> どうやら、RealtimeGetが遅いらしい
• 環境から、Indexを抜いてきて、Luceneからロードし
て検証
• -> MultiValueのDocValueの取得が特に遅い
検証
検証
ソースをたどっていくと
SlowCompositeReaderWrapperの文字が。。
検証
ん?
検証
SlowCompositeReaderWrapper?
検証
javadocより引用
NOTE: this class almost always results in a performance
hit. If this is important to your use case, you'll get better
performance by gathering the sub readers using
IndexReader.getContext() to get the leaves and then
operate per-LeafReader, instead of using this class.
結局起こっていたこと
Seg1 Seg2 Seg3 Seg4 Seg5
Lucene
SolrIndexSearcher
LeafReader LeafReader LeafReader LeafReader LeafReader 各Segment毎に
アクセスするの
が今のトレンド
SlowCompositeReaderWrapper
擬似LeafReader 動的にいろいろmergeして、複数
のleafを1つのleafに無理やり見せ
る
結局起こっていたこと
Seg1 Seg2 Seg3 Seg4 Seg5
Lucene
SolrIndexSearcher
LeafReader LeafReader LeafReader LeafReader LeafReader 各Segment毎に
アクセスするの
が今のトレンド
SlowCompositeReaderWrapper
擬似LeafReader 動的にいろいろmergeして、複数
のleafを1つのleafに無理やり見せ
る
DocValuesのmultivalueだと、さらに悲
惨
sort列 sort列 sort列 sort列 sort列
全体のsort列 <- ここの処理遅い
結局起こっていたこと
Seg1 Seg2 Seg3 Seg4 Seg5
Lucene
SolrIndexSearcher
LeafReader LeafReader LeafReader LeafReader LeafReader 各Segment毎に
アクセスするの
が今のトレンド
それぞれのleafから直接取るように修正
改善結果
Solr-9592 Contributed
6.3.0系から反映ずみ
副次的にこんな効果も
検索時のデータ取得部分も共通の処理だったため
•検索パフォーマンスも20%程度改善
233qps 600qps
改善による検索パフォーマンス
改善前 改善後
今回の教訓
振り返ってみると、新しい機能を使っていた(docValues)ために、この問題に、ぶつ
かったと言えなくもない
しかし、設定をごちゃごちゃしたりして誤魔化すのではなく、きっちりと内部の理解
を進め、改善を促すことで、他の部分も諸々改善ができた
有名なOSSも関心事が異なっていたりするので、信用しすぎないほうが良い
世の中をよりよくしていくためにも、保身に走るのではなく、新しいものをきっちり
使い、その上でさらなる改善をしていくという姿勢が良いのではないでしょうか
余談:Solrの部分更新について
聞いていてこう思った人いるはず
In-Place Updateってないんだっけ?
-> LUCENE-5189, SOLR-5944
LuceneにはnumericDocValuesに限り、InPlaceUpdate
(本当は違うけど)が実装済み
Solrへの取り込みは現在実装が進められている
余談:Solrの部分更新について
ただし、PostingListは更新できない
-> 基本的には検索できない
用途は限定的
余談:Solrの部分更新について
Flipkartの取り組み
http://www.slideshare.net/lucidworks/near-real-time-indexing-presented-by-umesh-prasad-thejus-v-m-flipkart
かなり力技感
まとめと今後
DocValuesを使っている場合は、6.3から、検索性
能含めて、かなり安定感が増す(と思う)
Storedのアクセスに比べて、DocValuesの方が
効率的になったので、Solr6.3以降、Stored Field
の用途は限定的に
結論
Solr-6.3で、AtomicUpdateしよう
最後に宣伝
We are Hiring!

SolrのAtomicUpdateを50000倍速くした話