【问题标题】:How to use Rails 3 scope to filter on habtm join table where the associated records don't exist?如何使用 Rails 3 范围过滤不存在​​关联记录的 habtm 连接表?
【发布时间】:2011-04-21 23:49:44
【问题描述】:

我有一个Author 模型,它是 habtm :feeds。使用 Rails 3 想要设置一个范围来查找所有没有关联提要的作者。

class Author < ActiveRecord::Base

    has_and_belongs_to_many :feeds
    scope :without_feed, joins(:feeds).where("authors_feeds.feed_id is null")

end

...似乎不起作用。感觉是一件很简单的事情。我在这里错过了什么?

【问题讨论】:

  • 感觉就像 joins(:feeds) 正在执行内部连接,只有在他们首先有提要时才会选择作者?
  • 它确实在做一个内连接:SELECT authors.* FROM authors INNER JOIN authors_feeds ON authors_feeds.author_id = authors.id INNER JOIN feeds ON feeds.id = authors_feeds.feed_id WHERE (authors_feeds.feed_id is null) 而我想要的是一个外连接。有什么帮助吗?

标签: activerecord ruby-on-rails-3 scope join where


【解决方案1】:

在 Rails >= 5 中,您可以这样做:

scope :without_feed, -> {
  left_outer_joins(:feeds)
  .where(authors_feeds: { author_id: nil })
}

scope :with_feed, -> {
  left_outer_joins(:feeds)
  .where.not(authors_feeds: { author_id: nil })
}

【讨论】:

  • 是的,使用 Arel 是更好的方法。 Glad Rails 5+ 让我们可以做到这一点。
【解决方案2】:

据我所知,ActiveRecord/Arel 没有定义外连接的方法。因此,您必须编写比平常更多的 SQL。像这样的东西应该可以解决问题:

    scope :without_feed, joins('left outer join authors_feeds on authors.id=authors_feeds.author_id').where('authors_feeds.feed_id is null')

我当然是在猜测您的表名和外键。但这应该会给你图片。

【讨论】:

  • 是的,做到了。谢谢!
  • 要与此相反(仅返回确实有 X 的作者)但使用简单的作者 has_many 地址,这个疯狂的东西(从这篇文章和this blog comment 拼凑在一起)似乎有效:@ 987654323@
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-03-21
  • 2017-01-18
  • 1970-01-01
  • 2022-10-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多