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
見せてもらおうか、 OpenSearchの性能とやらを!
Search
shunta ichikawa
March 19, 2026
Programming
300
1
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
見せてもらおうか、 OpenSearchの性能とやらを!
shunta ichikawa
March 19, 2026
More Decks by shunta ichikawa
See All by shunta ichikawa
メンテが命: PHPフレームワークのコンテナ化とアップグレード戦略
shunta27
0
760
20240711_RAGを用いたシンプルな 社内情報検索システムを導入した話とつらみ
shunta27
2
5.6k
Other Decks in Programming
See All in Programming
さぁV100、メモリをお食べ・・・
nilpe
0
140
JJUG CCC 2026 Spring: JSpecify で実現する Kotlin フレンドリーな Java API 設計
ternbusty
1
180
代数的データ型って何が嬉しいの? #frontend_phpcon_do
kajitack
8
3.7k
Composerを使ったサプライチェーン攻撃の様子を眺めてみる #phpstudy
o0h
PRO
2
250
jQueryをバージョンアップする前に使いたいjQuery Migrate
matsuo_atsushi
0
560
[2026年度第1回ORセミナー] 計画最適化ベンチャーと競技プログラミング人材
terryu16
0
270
Hunting Vulnerabilities in Symfony with LLMs
vinceamstoutz
0
550
Oxlintのカスタムルールの現況
syumai
6
1.1k
Oxcを導入して開発体験が向上した話
yug1224
4
320
JavaDoc 再入門
nagise
1
360
AI 輔助遺留系統現代化的經驗分享
jame2408
1
270
Webフレームワークの ベンチマークについて
yusukebe
0
170
Featured
See All Featured
State of Search Keynote: SEO is Dead Long Live SEO
ryanjones
0
210
The Illustrated Guide to Node.js - THAT Conference 2024
reverentgeek
1
390
Bridging the Design Gap: How Collaborative Modelling removes blockers to flow between stakeholders and teams @FastFlow conf
baasie
0
590
The Director’s Chair: Orchestrating AI for Truly Effective Learning
tmiket
1
200
Visualization
eitanlees
152
17k
Principles of Awesome APIs and How to Build Them.
keavy
128
18k
Cheating the UX When There Is Nothing More to Optimize - PixelPioneers
stephaniewalter
287
14k
Lightning talk: Run Django tests with GitHub Actions
sabderemane
0
200
Statistics for Hackers
jakevdp
799
230k
Color Theory Basics | Prateek | Gurzu
gurzu
0
370
A brief & incomplete history of UX Design for the World Wide Web: 1989–2019
jct
2
400
Impact Scores and Hybrid Strategies: The future of link building
tamaranovitovic
0
310
Transcript
PHPerKaigi 2026
自己紹介 市川 俊太 いちかわ しゅんた (39歳) 株式会社助太刀 開発本部 開発部長 CTO
• 猫が好き • 趣味はサッカー観戦、ポケカ • Ruby/PHPなどのLL言語が好き
工事会社の人手不足を マッチング と正社員採用 で解決 会社紹介 受注者と発注者をつなぐ ビジネスマッチングサービス 建設業経験者向けの 求人サービス
OpenSearchとは • オープンソースの検索エンジン ◦ 2021年にAWSがElasticsearchをフォークして開発 ◦ ダッシュボード機能も存在(OpenSearch Dashboards) ◦ ドキュメント指向データベース
• 主な用途 ◦ 検索機能 ◦ ログ検索・分析 ◦ データ分析・ダッシュボード
Index / Document • Index = データの集合 • Document =
1件のデータ RDB OpenSearch Database Cluster Table Index Row Document Column Field Primary Key _id 基本構造(RDB / OpenSearch) Document Index
検索エンジンの仕組み(転置インデックス) 文書群から「単語」をキーにして「出現する文書IDや位置」を高速に検索するための索引構造 ID 職種 1 型枠大工 2 内装大工 3 型枠職人
単語 ID 型枠 [1, 3] 大工 [1, 2] 内装 [2] RDB OpenSearch LIKE '%型枠%' → 全件チェック 型枠 → [1, 3]
検索クエリの違い 「北海道で、型枠の仕事に関係する候補者を探す」 OpenSearchクエリ SQL
助太刀はマッチングプラットフォーム 🤝 主な検索機能 • 取引先検索 ◦ 例:職人さんを探す • 求人検索 ◦
例:建設会社の正社員求人を探す • 求職者検索 ◦ 例:企業が職人をスカウト ユーザ体験は「検索」から始まる
助太刀はマッチングプラットフォーム 🤝 主な検索機能 • 取引先検索 ◦ 例:職人さんを探す • 求人検索 ◦
例:建設会社の正社員求人を探す • 求職者検索 ◦ 例:企業が職人をスカウト (当時)検索機能は RDB(MySQL)を利用
結果 Laravelリクエストレイテンシ 約3秒 → 約500ms に改善
検索機能が抱えていた問題 • 検索条件の増加でSQLが巨大化 • Indexが効きづらい検索条件 ◦ LIKE / OR /
多段JOINなど • ページング用のCOUNTクエリが非常に重い → 結果として検索処理が遅い(平均3秒以上) SELECT … FROM candidates LEFT JOIN ... LEFT JOIN ... LEFT JOIN … WHERE speciality LIKE '%型枠%' OR ...
サービス展開の拡大 • Web版の提供 • ログイン前でも検索できるように変更 ◦ 検索流入・検索回数の増加 → 上記の施策が進行... 検索トラフィック増加!
サービス展開の拡大 • Web版の提供 • ログイン前でも検索できるように変更 ◦ 検索流入・検索回数の増加 → 上記の施策が進行... 検索トラフィック増加!
検索基盤としてOpenSearchを導入 • 提供しているサービスは Laravel で構築 • 検索機能は Eloquent を通して MySQL
を利用 Laravel / Eloquent と共存しながら 検索エンジンを OpenSearch に置き換え
OpenSearch と RDB を組み合わせた検索処理フロー OpenSearch RDB 1. 検索クエリ 2. ID一覧
3. Eloquent問い合わせ 4. レコード取得 検索サービス 北海道で、型枠の仕事に 関係する候補者を検索 検索はOpenSearch、正しいデータはRDB
OpenSearch と RDB を組み合わせた検索処理フロー
検索用データをOpenSearchに同期する OpenSearch RDB id name birth area speciality 123 市川工業
1987-02-07 北海道 型枠大工 Usersテーブル 同期 職種 Usersインデックス { "hits": { "hits": [ { "_id": "123", "_source": { "name": "市川工業", "area": "北海道", "speciality": "型枠大工" } }, …… ] } }
Laravel → OpenSearch OpenSearch RDB 1. 検索クエリ 2. ID一覧 3.
Eloquent問い合わせ 4. レコード取得 検索サービス
Laravel → OpenSearch Composerライブラリを利用 公式クライアント:opensearch-project/opensearch-php DSLクエリビルダー:shyim/opensearch-php-dsl
SQL検索をOpenSearchで表現する { "query": { "bool": { "must": [ { "wildcard":
{ "speciality": "*型枠*" } } ], "filter": [ { "term": { "area": "北海道" } } ] } }, "size": 10, "from": 0 } SELECT * FROM users WHERE speciality LIKE '%型枠%' AND area = '北海道' LIMIT 10 OFFSET 0; 1. SQL 2.OpenSearch DSL 3. クライアント実装
OpenSearch DSLをクエリビルダーライブラリで書く 3. クライアント実装 4. DSLライブラリ実装
DSLクエリービルダーライブラリを使う利点 • タイポ・構造ミスを防げる ◦ オブジェクトなら構造が保証される ▪ 配列だと must / filter
の入れ子を間違え やすい • 条件を動的に追加しやすい ◦ $query->add() のように積み上げられる ▪ 配列だとマージ処理が複雑 • IDE補完が効く ◦ クラス・メソッドが補完される 4. DSLライブラリ実装
Laravel → RDB OpenSearch RDB 1. 検索クエリ 2. ID一覧 3.
Eloquent問い合わせ 4. レコード取得 検索サービス
OpenSearchはID検索だけに使う OpenSearchの検索結果に含まれるID(_id)を 使ってEloquentで再取得する 検索結果のレスポンス構造 RDB id name birth area speciality
123 市川工業 1987-02-07 北海道 型枠大工 Usersテーブル 職種 同じIDで同期
OpenSearchはID検索だけに使う OpenSearchの検索結果に含まれる ID(_id)を使ってEloquentで再取得する 検索結果のレスポンス構造 • keyBy('id') で ID をキーにしたコレクションに 変換
• OpenSearch の並び順に合わせて map() で並び替える IDで再取得
• データの一貫性 ◦ OpenSearchはMySQLのレプリカで更新ラグがあるため、 Eloquentで再取得し最新データを保証。 • Eloquentのエコシステムをそのまま利用 ◦ OpenSearchのレスポンスは配列でありモデルマッピングが必要だが、 Eloquentで再取得すること
でリレーション・スコープ・アクセサなどの Laravel機能を利用可能。 • OpenSearchのスキーマを最小限に ◦ 検索に必要なフィールドのみ OpenSearchに持たせ、インデックスのメンテコストを削減。 • 責務が明確 ◦ OpenSearch:検索条件に合うIDリストを返す(全文検索、フィルタ、スコアリング) ◦ RDB (MySQL):そのIDに紐づくユーザーデータを返す(プロフィール、リレーションなど) OpenSearchをID検索だけに使うメリット
OpenSearchをID検索だけに使うデメリット • データストアに2回アクセスによるオーバーヘッド増大 • データ同期のタイミングによる不整合が発生しうる ◦ OpenSearch と RDB のデータが一時的に一致しないことがある
まとめ OpenSearchで検索性能は大きく改善できた Laravelと共存する現実的な移行もできた
OpenSearchで検索性能は大きく改善できた Laravelと共存する現実的な移行もできた でも、性能改善だけでは事業KPIは伸びなかった まとめ
OpenSearchで検索性能は大きく改善できた Laravelと共存する現実的な移行もできた でも、性能改善だけでは事業KPIは伸びなかった だからこそ、 技術課題と事業課題を切り分けて考えることが大事 まとめ
皆様、ご清聴ありがとうございました!