2017-07-19 54 views
1

在我的Ruby on Rails应用程序,我有以下型号:ActiveRecord的 - 查找记录,它的关联计数为0

class SlideGroup < ApplicationRecord 
    has_many :survey_group_lists, foreign_key: 'group_id' 
    has_many :surveys, through: :survey_group_lists 
end 

我想找到所有孤立的幻灯片组。孤立幻灯片组是与任何调查无关的幻灯片组。我一直试图下面的查询,但它不返回任何东西,我敢肯定,我在我的测试数据库中的孤立记录:

SlideGroup.joins(:surveys).group("slide_groups.id, surveys.id").having("count(surveys.id) = ?",0) 

这会产生下面的SQL查询:

SlideGroup Load (9.3ms) SELECT "slide_groups".* FROM "slide_groups" INNER JOIN "survey_group_lists" ON "survey_group_lists"."group_id" = "slide_groups"."id" INNER JOIN "surveys" ON "surveys"."id" = "survey_group_lists"."survey_id" GROUP BY slide_groups.id, surveys.id HAVING (count(surveys.id) = 0) 
+1

这里你需要一个'outer join',因为'inner join'不会返回孤儿。 – mudasobwa

回答

2

你”重新使用joins,这是INNER JOIN,而你需要的是一个OUTER JOIN - includes

SlideGroup.includes(:surveys).group("slide_groups.id, surveys.id").having("count(surveys.id) = ?",0) 

一点清洁查询:

SlideGroup.includes(:surveys).where(surveys: { id: nil }) 
+4

Rails 5还增加了一个'left_outer_joins'方法 - https://github.com/rails/rails/pull/12071 –

1

查找孤儿记录已被其他人解释。

我看到这种方法的问题:

  • 不应有摆在首位任何孤儿
  • 一个survey.id的存在并不能保证有关SurveyGroupListSurvey
  • 什么存在即是孤儿吗?

所以适当的解决方案是确保没有孤儿留在数据库中。通过执行适当的逻辑的外键添加到数据库中删除级联。您还可以将dependent: :destroy选项添加到您的关联中,但只有在模型上使用#destroy(而不是delete)时才可使用,如果直接通过SQL删除,则此功能当然不起作用。

相关问题