如何在Rails 4中使用Join而不是子查询来编写此ActiveRecord查询

时间:2014-06-30 14:32:25

标签: sql ruby-on-rails postgresql activerecord ruby-on-rails-4

请考虑以下事项:

class User < ActiveRecord::Base
  has_many :events
end

class Event < ActiveRecord::Base
  belongs_to :user #this user is the event owner
  has_many :members
end

class Members < ActiveRecord::Base
  belongs_to :user
  belongs_to :event
end

现在,我需要列出current_user为所有者的所有成员。所以我想出了这个:

@members = Member.where event_id: current_user.events

产生以下查询:

SELECT "members".* FROM "members" WHERE "members"."event_id" IN (SELECT "events"."id" FROM "events" WHERE "events"."user_id" = 1)

这可以按预期工作,但使用子查询而不是JOIN。有没有人知道更好的方法来编写同样的查询?

4 个答案:

答案 0 :(得分:2)

通过关联添加has_many:到您的用户模型:

class User < ActiveRecord::Base
  has_many :events
  has_many :members, :through => :events
end

现在,您可以通过成员关联查询所有用户的成员:

user.members

生成的SQL类似于:

SELECT "members".* FROM "members" INNER JOIN "events" ON "members"."id" = "events"."member_id" WHERE "events"."user_id" = 1

答案 1 :(得分:0)

转换为JOIN语法(使用表别名使其更短且更易于阅读):

SELECT m.*
FROM   events e
JOIN   members m ON m.event_id = e.id
WHERE  e.user_id = $1

答案 2 :(得分:0)

我想这会奏效。

Member.joins(:event).where("events.user_id = ?" , current_user.id)

答案 3 :(得分:0)

您可以执行以下操作:

Member.joins(:event).where(events: {user_id: current_user.id})