Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
PostgreSQL vs Elasticsearch -ファセットカウント編-
Search
forcia_dev_pr
February 21, 2022
Programming
0
660
PostgreSQL vs Elasticsearch -ファセットカウント編-
「FORCIA Meetup #4 高速検索を支えるPostgreSQLのノウハウ」の資料です
forcia_dev_pr
February 21, 2022
Tweet
Share
More Decks by forcia_dev_pr
See All by forcia_dev_pr
第7回ゆるふわオンサイト解説
forcia_dev_pr
0
110
第6回ゆるふわオンサイト解説
forcia_dev_pr
0
170
よくわかるFORCIAのエンジニア旅行SaaSプロダクト開発編
forcia_dev_pr
0
460
よくわかるフォルシアのエンジニア 新卒採用編
forcia_dev_pr
0
2.6k
第5回ゆるふわオンサイト解説
forcia_dev_pr
0
100
よくわかるフォルシアのエンジニア 旅行プラットフォーム部編
forcia_dev_pr
0
4.5k
React hooks を気合で理解する
forcia_dev_pr
0
300
k8sマニフェストを Typescriptで管理したい― cdk8s+を導入してみました ―
forcia_dev_pr
0
290
第4回ゆるふわ競技プログラミングオンサイト解説
forcia_dev_pr
0
480
Other Decks in Programming
See All in Programming
破壊せよ!データ破壊駆動で考えるドメインモデリング / data-destroy-driven
minodriven
16
4k
推し活としてのrails new/oshikatsu_ha_iizo
sakahukamaki
3
1.6k
Jakarta Concurrencyによる並行処理プログラミングの始め方 (JJUG CCC 2024 Fall)
tnagao7
1
230
CSC509 Lecture 09
javiergs
PRO
0
100
Sidekiqで実現する 長時間非同期処理の中断と再開 / Pausing and Resuming Long-Running Asynchronous Jobs with Sidekiq
hypermkt
6
2.7k
Server Driven Compose With Firebase
skydoves
0
390
EventSourcingの理想と現実
wenas
6
2.1k
レガシーな Android アプリのリアーキテクチャ戦略
oidy
1
170
リリース8年目のサービスの1800個のERBファイルをViewComponentに移行した方法とその結果
katty0324
5
3.6k
Vue.js学習の振り返り
hiro_xre
2
130
Pinia Colada が実現するスマートな非同期処理
naokihaba
2
150
Vue3の一歩踏み込んだパフォーマンスチューニング2024
hal_spidernight
3
3.1k
Featured
See All Featured
Making the Leap to Tech Lead
cromwellryan
132
8.9k
5 minutes of I Can Smell Your CMS
philhawksworth
202
19k
How to Think Like a Performance Engineer
csswizardry
19
1.1k
The Myth of the Modular Monolith - Day 2 Keynote - Rails World 2024
eileencodes
13
1.9k
Designing for Performance
lara
604
68k
Designing Dashboards & Data Visualisations in Web Apps
destraynor
228
52k
We Have a Design System, Now What?
morganepeng
50
7.2k
How to Ace a Technical Interview
jacobian
275
23k
The Art of Programming - Codeland 2020
erikaheidi
51
13k
Designing on Purpose - Digital PM Summit 2013
jponch
115
6.9k
GraphQLとの向き合い方2022年版
quramy
43
13k
Scaling GitHub
holman
458
140k
Transcript
PostgreSQL vs Elasticsearch -ファセットカウント編- 籏野 拓 @フォルシア株式会社 2022.02.15 FORCIA Meetup#4
自己紹介 • 籏野 拓 (Taku Hatano) ◦ 新卒4年目 • ソフトウェアエンジニア@フォルシア株式会社
◦ 福利厚生系アプリ中心に自社プロダクトもちらほら • 活動領域 ◦ webアプリケーション (TypeScript, Node.js, React, Next.js, PostgreSQL) ◦ インフラ関連(Ansible, AWS, k8s, docker) 2
フォルシアの検索 3
What is Spook®? 4 各企業が独自に持つ膨大で複雑なデータに合わせて、 最適な検索を実現するための「技術基盤」
Spook®の特長 5 検索対象の属性を軸に絞り込みを行う →PostgreSQLの独自関数を利用し、 より高速な検索を実現
さらなる展開 6 近年、キーワード検索への需要の高まりも感じている ↓ の利用検討中
PostgreSQL vs Elasticsearch 7
キーワード検索編 普通はElasticsearchの方が5倍早い • C言語による拡張機能(extension) ◦ システム開発者向け • 形態素解析器を呼び出せるが 基本的に自作 •
Javaによる拡張機能(plugin) ◦ 応用的・ユーザー志向 • キーワード検索に必要な機能 ワンストップで提供 8 [参考] FORCIA CUBE「Elasticsearch vs. PostgreSQL」 https://www.forcia.com/blog/001551.html
ファセットカウント編 9 「ファセットカウント」 →条件で絞り込む際に 該当の条件が何件であるかを事前に表示する 実際にPostgreSQLとElasticsearchで速度比較してみた
対象データ 10 • 1レコードが複数のカテゴリを持つようなデータを対象とする。 • カテゴリは1~100のランダムな整数 • 1レコードあたり1~10のランダムな数のカテゴリをもつ • postgresはint配列、elasticsearchはNested
Typeでデータを持つ { "_index" : "search", "_type" : "_doc", "_id" : "eFHgw34BVdsiHW0pykMc", "_score" : 1.0, "_source" : { "categories" : [{ "id" : 37}, {"id" : 83}] } } id | categories ----+--------------------------------- 1 | {69,87,96,98}
集計クエリ 11 select unnest(categories) as category ,count(*) from search group
by category order by category { "size": 0, "aggs": { "categories" : { "nested": { "path": "categories" }, "aggs": { "count": { "terms": { "field": "categories.id" , "size": 101, "order": { "_key": "asc" } } } } } } }
計測方法 12 • 以下を10回繰り返して実行時間の平均を算出する ◦ 1万/10万/100万行のランダムなデータを生成する ◦ それぞれにクエリを投げて実行時間を計測 ※あるアプリでは施設数3万件、プラン数120万件くらい
計測結果 13 レコード数 PostgreSQL平均 Elasticsearch平均 10000 0.028s 0.021s 100000 0.130s
0.039s 1000000 1.429s 0.373s • レコード数が少ない場合は同等のスピード • レコード数が多いとElasticsearchに軍配 ◦ NestedTypeは配列の要素ごとに異なるドキュメント(≒レコード)として保 持されているので展開の必要がない
補足: Elasticsearchのオブジェクト配列 14 (公式: https://www.elastic.co/guide/en/elasticsearch/reference/current/nested.html ) 単純なオブジェクトの配列でマッピングされている場合、 フラットな構造に展開されてインデックスされる PUT my-index-000001
/_doc/1 { "group" : "fans", "user" : [ { "first" : "John", "last" : "Smith" }, { "first" : "Alice", "last" : "White" } ] } { "group" : "fans", "user.first" : [ "alice", "john" ], "user.last" : [ "smith", "white" ] } firstとlastの組み合わせが維持されない first = “Alice” and last = “Smith” がヒットしてしまう →
補足: Elasticsearch Nested Type 15 (公式: https://www.elastic.co/guide/en/elasticsearch/reference/current/nested.html ) Nested Typeを利用することで元の組み合わせを保持してインデックスされる
{ "group" : "fans", "user.first" : "john", "user.last" : "smith" } { "group" : "fans", "user.first" : "alice", "user.last" : "white" } 「nested documents are indexed as separate documents」 ←インデックスされるイメージ first = “Alice” and last = “Smith” はヒットしない
Spook®でも計測を行ってみた 16 レコード数 PostgreSQL平均 Elasticsearch平均 Spook®平均 10000 0.028s 0.021s 0.010s
100000 0.130s 0.039s 0.022s 1000000 1.429s 0.373s 0.090s • PostgreSQLでもチューニングにより十二分な速度が出る
まとめ 17 • ElasticsearchのAggregationsという機能を使うことで GROUP BY相当の集計ができる • チューニングなどしなくてもある程度の速度が出る ◦ デフォルトでフラットな構造にしてインデックスしてくれるため
• PostgreSQLでもチューニングを行うことで高速化は可能
EOF