Reputation: 125902
Suppose I've got ActiveRecord models such that User has_one :photo
. In the database, photos
has a t.binary
column which may hold a lot of data, so I don't want to SELECT
that column unless I need to.
I want to do something like:
users.each do |user|
image_tag(user_photo_path) if user.photo.present?
end
However, I don't want to call user.photo.present?
because:
photo
association, including SELECT * from photos
SELECT id FROM photos
to check existence, it's still an N + 1 query.What I really want is to load users
with a single query which gives each one a property telling me whether it has an associated photo or not.
Upvotes: 2
Views: 193
Reputation: 125902
With ActiveRecord 5, this works:
class User < ActiveRecord::Base
scope :with_photo_id, -> {
left_outer_joins(:photo).select(
"users.*, photos.id AS photo_id"
)
}
end
Then I can call User.with_photo_id
and check user.photo_id.present?
.
Prior to AR 5, the join would be uglier:
joins(
"LEFT OUTER JOIN photos ON photos.user_id = users.id"
)
Upvotes: 1