You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

ActiveRecord两级关联查询问题:Factory关联Worker查询报错及优化咨询

问题场景与需求

模型关联关系

Factory、Worker、JobRole三者为has_many :through关联,具体模型代码如下:

Factory 模型

has_many :workers, through: :job_roles

Worker 模型

has_many :job_roles
has_many :factories, through: :job_roles

JobRole 模型

belongs_to :worker
belongs_to :factory

尝试的查询与问题

我尝试执行以下查询语句:

factory.job_roles.where(heavy_lifting:true, sensitive_area: false).workers.where.not(confirmed_at:nil).pluck(:work_capacity)

但factory.job_roles.where(...)返回的是ActiveRelation实例,直接调用.workers方法会报错。

需求

获取某工厂内满足以下条件的Worker的work_capacity字段值:

  • 关联的JobRole满足heavy_lifting: true且sensitive_area: false
  • Worker已确认(confirmed_at不为空)

请问除了循环遍历的方式(如下示例代码),是否有更高效的实现方法?

循环遍历示例代码

applicable_job_roles = factory.job_roles.where(heavy_lifting:true, sensitive_area: false)

work_capacities = []

applicable_job_roles.each do |job_role|
  if job_role.worker.confirmed_at != nil
    work_capacities << job_role.worker.work_capacity
  end
end

注:原代码中job_role.confirmed_at应为job_role.worker.confirmed_at,confirmed_at是Worker模型的字段


解决方案

可以通过ActiveRecord构造单条SQL查询语句,避免N+1查询和内存循环处理,以下是几种可行写法:

方法1:从Worker模型直接查询

直接从Worker模型入手,通过关联筛选工厂和JobRole的条件:

Worker.joins(:job_roles)
      .where(job_roles: { factory_id: factory.id, heavy_lifting: true, sensitive_area: false })
      .where.not(confirmed_at: nil)
      .pluck(:work_capacity)

方法2:基于Factory实例的关联查询

利用Factory的workers关联,结合joins和merge合并JobRole的筛选条件:

factory.workers
       .joins(:job_roles)
       .merge(JobRole.where(heavy_lifting: true, sensitive_area: false))
       .where.not(confirmed_at: nil)
       .pluck(:work_capacity)

这种写法更贴合从Factory实例出发的查询逻辑,merge可以将JobRole的查询条件无缝整合到关联查询中。

方法3:预加载关联后内存筛选(备选)

如果需要同时获取Worker对象,可通过includes预加载关联避免N+1,再在内存中筛选,但性能不如前两种直接生成SQL的方式:

factory.job_roles
       .where(heavy_lifting: true, sensitive_area: false)
       .includes(:worker)
       .select { |jr| jr.worker.confirmed_at.present? }
       .map { |jr| jr.worker.work_capacity }

内容的提问来源于stack exchange,提问作者daveasdf_2

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.25 21:33:16