Rails 4.2中has_many的条件?

时间:2016-06-11 15:30:47

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

我有一个帖子模型has_many:authors和has_many:标签通过:tag_posts,一个作者模型has_many:posts和has_many:标签通过:posts,以及一个标签模型has_many:posts through:tag_posts。

帖子必须通过审核(存储为枚举Post.status)才能在网站上显示。版主可以通过查找具有不同Post.status的帖子来查看未经审核的帖子,但普通用户永远不能看到它们。

有什么方法可以过滤所有这些关联,以确保它们只返回主持人已批准的帖子?

例如:如果我现在调用Author#tags,它会返回作者写过的所有帖子上的所有标签,但我只希望它返回已批准的帖子上的标签作者写了。假设作者有两个帖子,第一个被批准并被标记为章鱼',第二个尚未被批准并标记为' squid':呼叫#tags on作者应该只返回章鱼标签,而不是squid标签。

2 个答案:

答案 0 :(得分:0)

  

我有一个帖子模型has_many:authors和has_many:标签通过:tag_posts,一个作者模型has_many:posts和has_many:标签通过:posts,以及一个标签模型has_many:posts through:tag_posts。

首先,让我们整理这些关系。我相信这是你真正想要的:

class Post < ActiveRecord::Base
  belongs_to :author  # NOT has_many
  has_and_belongs_to_many :tags # use an implicit join table
end

class Author < ActiveRecord::Base
  has_many :posts
end

class Tag < ActiveRecord::Base
  has_and_belongs_to_many :posts # use an implicit join table
end
  

我有什么方法可以过滤所有这些关联,以确保他们只返回主持人已批准的帖子?

是。在不详细说明的情况下,关键技术是在scope模型上定义Post;像这样的东西:

class Post < ActiveRecord::Base
  scope :approved -> { where(status: Post.statuses['approved']) }
end

然后,您可以通过Post.approved仅显示已批准的帖子;或仅通过Post.where(user: foo).approved为特定用户批准的帖子。

为了显示标签列表,您可以例如执行:

Post.where(user: foo).approved.map(&:tags).uniq

这只会为您提供Array,而不是ActiveRecord::Collection。但就你的目的而言,这可能已经足够了。

答案 1 :(得分:0)

您可以自定义easy_perform()范围。 例如

has_many