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
N+1 問題の解決と computed_model
Search
gedorinku
October 05, 2023
Programming
0
31
N+1 問題の解決と computed_model
gedorinku
October 05, 2023
Tweet
Share
More Decks by gedorinku
See All by gedorinku
Wantedly のバックエンドの将来に向けた取り組みと課題 - Wantedly Tech Night 2024/5
gedorinku
0
31
Porting mruby/c for the SNES (Super Famicom) - RubyKaigi 2024
gedorinku
0
3.2k
部内での競プロ用ジャッジシステム
gedorinku
0
1.6k
部内ジャッジを作る話
gedorinku
1
85
プロラボ年度末報告会 HackDay / Hack U 福岡
gedorinku
0
150
Kotlin入門しました
gedorinku
0
260
Other Decks in Programming
See All in Programming
めざせ!WKWebViewマスター! / WKWebView Master
marcy731
3
480
REXML改善のその後
naitoh
0
150
フロントエンドのテストからアクセシビリティをしれっと広めていく
nano72mkn
3
700
The Future of Frontend i18n : Intl.MessageFormat
sajikix
1
2.4k
BasicBasic認証
sadnessojisan
5
2.5k
ウォンテッドリーにおけるモバイルアプリ開発 / iOSDC Japan 2024 Sponsor Session
kubode
0
220
ゲームボーイアドバンスでSwiftを動かそう
k_koheyi
0
510
(非公開スライド追加)座談会 「Strict ConcurrencyとSwift 6が開く新時代: 私たちはどう生きるか?」
shiz
1
140
状態管理ライブラリZustandの導入から運用まで
k1tikurisu
2
240
Meet BrowserEngineKit
swiftty
0
190
Playwrightから始めるVisual Regression Testingのススメ by とっと
totto2727
2
1.8k
どうしてこうなった?から理解するActive Recordの関連の裏側
willnet
5
510
Featured
See All Featured
Sharpening the Axe: The Primacy of Toolmaking
bcantrill
33
1.7k
The Invisible Side of Design
smashingmag
295
50k
How STYLIGHT went responsive
nonsquared
93
5.1k
From Idea to $5000 a Month in 5 Months
shpigford
378
46k
Why Our Code Smells
bkeepers
PRO
333
56k
The Psychology of Web Performance [Beyond Tellerrand 2023]
tammyeverts
34
1.9k
GraphQLの誤解/rethinking-graphql
sonatard
65
9.7k
Refactoring Trust on Your Teams (GOTO; Chicago 2020)
rmw
29
2.5k
Principles of Awesome APIs and How to Build Them.
keavy
125
16k
Save Time (by Creating Custom Rails Generators)
garrettdimon
PRO
22
580
Designing for Performance
lara
604
68k
Why You Should Never Use an ORM
jnunemaker
PRO
53
8.9k
Transcript
© 2023 Wantedly, Inc. N+1 問題の解決と computed_model Oct. 5 2023
- Ryota Egusa (@gedorinku)
Wantedly のアーキテクチャ © 2023 Wantedly, Inc. Rails のマイクロサービス GraphQL のデータソースなどに使われる、汎用
的な API を持つ
加工した値を返すモデルのメソッド class User < ApplicationRecord has_many :work_experiences # => "ウォンテッドリー株式会社
/ エンジニア" def position_description work_experience = work_experiences.max_by { _1.started_at } "#{work_experience.company_name} / #{work_experience.position}" end end © 2023 Wantedly, Inc.
Preload と N+1 問題 class User < ApplicationRecord has_many :work_experiences
… end User.where(...).map(&:position_description) User.preload(:work_experiences).where(...).map(&:position_description) © 2023 Wantedly, Inc.
computed_model による解決方法 class User define_primary_loader :raw_user do ... end define_loader
:work_experiences do ... end dependency :work_experiences computed def position_description work_experience = work_experiences.max_by { _1.started_at } "#{work_experience.company_name} / #{work_experience.position}" end end © 2023 Wantedly, Inc. 依存関係をここに書く ここに書かれていないものを使うと エラーになる
Active Record をデータソースとして使う例 class User define_primary_loader :raw_user do |_, ids:,
**| RawUser.where(id: ids).map do |raw_user| User.new(raw_user) end end define_loader :work_experiences do ... end end © 2023 Wantedly, Inc.
他サービスの API をデータソースとして使う例 class User define_primary_loader :raw_user do ... end
define_loader :work_experiences, key: -> { id } do |user_ids, _, **| WorkExperienceApiClient.list(user_ids: user_ids).group_by(&:user_id) end end © 2023 Wantedly, Inc.
computed_model からデータを読む 指定していないフィールドを使うとエラーになる users = User.batch_get(user_ids, [:position_description]) users.map(&:position_description) users.map(&:name) #
=> error © 2023 Wantedly, Inc.
まとめ 1. 抽象化を損なわず依存関係解決 ◦ N+1問題を防ぎ、必要なデータだけ読み込む 2. データソースには Active Record に限らず
HTTP API なども使える © 2023 Wantedly, Inc. https://github.com/wantedly/computed_model