1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

#Rails の preload では関連先テーブルの絞り込みはできず、eager_loadでは可能 ( joins / includes の違いや merge の作用を知りたい )

Last updated at Posted at 2020-04-11
# preload では 自分からの検索は可能
users = User.where(id: [1,2,3,4,5]).preload(:books)

# preload では 関連先のテーブルからの検索は不可能
users = User.preload(:books).where(books: { name: "Alice Wonder Land" }).first
# ActiveRecord::StatementInvalid: Mysql2::Error: Unknown column ...


# preload  + joins で関連先のテーブルからの検索が可能だが、 join の作用で 関連先テーブルの数だけ返ってくる結果数も多くなる
# 同じUserのインスタンスが大量に返ってきたり
# merge でも where でも書けるが、どちらでも挙動は変わらないっぽい?
users = User.joins(:books).preload(:books).where(books: { name: "Alice Wonder Land" })
users = User.joins(:books).preload(:books).merge(Book.where(name: "Alice Wonder Land" ))

# preload  + joins 
# uniq すれば User もユニークになるが、なんだか無理やりな気もする
users = User.joins(:books).preload(:books).merge(Book.where(name: "Alice Wonder Land" )).uniq

# eager_load では関連先テーブルからも検索も可能
users = User.eager_load(:books).where(books: { name: "Alice Wonder Land" })


# includes は preload と eager_load のどちらかを自動で切り替えてくれるので、関連先テーブルから検索しようとすると、eager_load と同じクエリ、同じ挙動になる
users = User.includes(:books).where(books: { name: "Alice Wonder Land" })

ヒント

.to_sql メソッドでクエリの中身を見てみたり、そのSQLを直接 DB に発行して、返ってくるDBの結果を見てみよう。

参考

ActiveRecord ~ 複数テーブルにまたがる検索(preload, eager_load, include, joins) - Qiita

Original by Github issue

チャットメンバー募集

何か質問、悩み事、相談などあればLINEオープンチャットもご利用ください。

Twitter

1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?