微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

sql – 为什么当一个包罗万象的SELECT已经运行时,各个SELECT查询会运行? (轨道/ ActiveRecord的)

我有以下代码(请注意includes和.each):
subscribers = []
mailgroup.mailgroup_members.opted_to_receive_email.includes(:roster_contact,:roster_info).each { |m|
  subscribers << { :EmailAddress => m.roster_contact.member_email,:Name => m.roster_contact.member_name,:CustomFields => [ { :Key => 'gender',:Value => m.roster_info.gender.present? ? m.roster_info.gender : 'X' 
                                    } ] 
                  } if m.roster_contact.member_email.present?
}
subscribers

相应地,我在我的日志中看到以下内容(即从ROSTER_INFO … IN(…)中选择*):

SELECT `ROSTER_INFO`.* FROM `ROSTER_INFO` WHERE `ROSTER_INFO`.`ID` IN ('1450','1000','1111')

然后,在上一个查询的IN列表中已经指定的每个ID之后立即从ROSTER_INFO中选择*:

RosterInfo Load (84.8ms)  SELECT `ROSTER_INFO`.* FROM `ROSTER_INFO` WHERE `ROSTER_INFO`.`ID` = '1450' LIMIT 1
RosterInfo Load (59.2ms)  SELECT `ROSTER_INFO`.* FROM `ROSTER_INFO` WHERE `ROSTER_INFO`.`ID` = '1000' LIMIT 1
RosterInfo Load (56.8ms)  SELECT `ROSTER_INFO`.* FROM `ROSTER_INFO` WHERE `ROSTER_INFO`.`ID` = '1111' LIMIT 1

如果在所有感兴趣的ID(IN(…))上已经在ROSTER_INFO上完成了select *,为什么对于每个相同的ID再次执行另一个select *? ActiveRecord是否已经知道每个ID的所有ROSTER_INFO列?

(同时,对于ROSTER_CONTACT没有单独的查询,但如果我从includes方法删除:roster_contact,则不会再次查询ROSTER_INFO,但ROSTER_CONTACT是.)

RosterInfo模型(删节)

class RosterInfo < ActiveRecord::Base
  self.primary_key = 'ID'
end

RosterContact模型(删节)

class RosterContact < ActiveRecord::Base
  self.primary_key = 'ID'

  has_many :mailgroup_members,foreign_key: 'rosterID'
  has_many :mailgroups,through: :mailgroup_members

  has_one :roster_info,foreign_key: 'ID'     # can use this line
  #belongs_to :roster_info,foreign_key: 'ID' # or this with no difference

  def member_name                             # I added this method to this
    roster_info.member_name                   # question only *after* having
  end                                         # figured out the problem.
end

RosterWeb模型(删节)

class RosterWeb < ActiveRecord::Base
  self.primary_key = 'ID'
end

邮件组模型(删节)

class Mailgroup < ActiveRecord::Base
  self.primary_key = 'ID'

  has_many :mailgroup_members,foreign_key: 'mailCatID'

  has_one :mailing_list,foreign_key: :legacy_id
end

MailgroupMember模型(删节)

class MailgroupMember < ActiveRecord::Base
  self.primary_key = 'ID'

  belongs_to :mailgroup,foreign_key: 'mailCatID'
  belongs_to :roster_contact,foreign_key: 'rosterID'
  belongs_to :roster_info,foreign_key: 'rosterID'
  belongs_to :roster_web,foreign_key: 'rosterID'

  scope :opted_to_receive_email,joins(:roster_web).where('ROSTER_WEB.receiveEmail=?',1)
end

解决方法

该问题与m.roster_contact.member_name有关 – 不幸的是,我使member_name成为roster_contact的一个方法,它自己(间接)查询roster_info.member_name.我通过改变线来解决这个问题
:Name => m.roster_contact.member_name,

直接查询roster_info如下

:Name => m.roster_info.member_name,

对不起,我很抱歉!

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐