[英]How to eager load one row from `has_many` association
我有这些模特
class User < ActiveRecord::Base
has_many :agent_logins
def active_login
agent_logins.active.order('created_at DESC').first
end
end
class AgentLogin < ActiveRecord::Base
belongs_to :user
scope :active, -> { where(active: true) }
end
我有这个序列化器的API控制器
class API::UsersController < API::APIController
def index
respond_with User.all
end
end
class UserSerializer < ActiveModel::Serializer
attributes :id, :pin, :voicemail, :name, :active_login
end
当然,这会产生N + 1问题
User Load (7.7ms) SELECT `users`.* FROM `users`
AgentLogin Load (2.7ms) SELECT `agent_logins`.* FROM `agent_logins` WHERE `agent_logins`.`user_id` = 3 AND `agent_logins`.`active` = 1 ORDER BY created_at DESC LIMIT 1
AgentLogin Load (3.8ms) SELECT `agent_logins`.* FROM `agent_logins` WHERE `agent_logins`.`user_id` = 16 AND `agent_logins`.`active` = 1 ORDER BY created_at DESC LIMIT 1
AgentLogin Load (3.8ms) SELECT `agent_logins`.* FROM `agent_logins` WHERE `agent_logins`.`user_id` = 18 AND `agent_logins`.`active` = 1 ORDER BY created_at DESC LIMIT 1
有没有解决此问题的首选方法? 谢谢。
试试这个不太好用的解决方案。
制作一个单独的类,称为ActiveLogins
class User
has_one :active_login
end
class ActiveLogins
belongs_to :user #=> foregin key :user_id
end
每次创建AgentLogin时,还创建一个相同的ActiveLogin,并删除所有其他具有相同:user_id的ActiveLogins。
然后,您可以调用User.all.includes(:active_login)(希望不会出现N + 1个问题)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.