在Rails中按组获取帖子

时间:2015-01-10 04:15:28

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

在我的应用中,我拥有属于群组的用户,可以创建帖子。

在每个群组页面上,我试图显示该特定群组中用户的所有帖子(从最新到最旧)。这是我到目前为止尝试过的代码,但无论用户属于哪个群组,它都会显示每个用户的所有帖子。

这里是groups_controller.rb

class GroupsController < ApplicationController
  def show
    @group = Group.find(params[:id])
    if logged_in?
      @feed_items = Post.latest_posts_by_group(@group)
    end
  end
end

post.rb

class Post < ActiveRecord::Base
  belongs_to :user

  def self.latest_posts_by_group(group_id)
    Post.find_by_sql(['select posts.*
      from groups
      inner join users
      on users.group_id = groups.id
      inner join posts
      on posts.user_id = user_id
      where groups.id = ?
      order by created_at desc', group_id])
  end
end

user.rb(好吧,至少是协会):

class User < ActiveRecord::Base
  belongs_to :group
  has_many :posts
end

group.rb(再次,只显示关联):

class Group < ActiveRecord::Base
  has_many :users
end

2 个答案:

答案 0 :(得分:2)

我会使用内置在关联助手中的rails而不是手动构建SQL查询。在这种情况下

class  Post < ActiveRecord::Base
  belongs_to :user
  has_one :group, through: :user

class  User < ActiveRecord::Base
  belongs_to :group
  has_many :posts

class  Group < ActiveRecord::Base
  has_many :users
  has_many :posts, through: :users

当您正确构建这些关联时,rails会自动为您生成@group.posts等方法。

但是,您应该注意,外键必须以某种方式命名以使关联起作用,但是从SQL查询中我看到您已经通过命名外键group_id和{分别在user_idUsers表格中{1}}。

供进一步参考:http://edgeguides.rubyonrails.org/association_basics.html#the-has-many-through-association

答案 1 :(得分:1)

您可以使用范围执行此操作。加入:user关联并在users.group.id上添加条件。以下代码应该这样做。

class Post < ActiveRecord::Base
  belongs_to  :user
  has_one :group, through: :user

  scope :latest_posts_by_group, ->(group) {
    joins(:user).
    where(users: {group_id: group.id}).
    reorder(created_at: :desc)
  }
end

这会创建一个这样的SQL:

SELECT posts.* FROM posts
  INNER JOIN users ON users.id = posts.user_id
WHERE users.group_id = ?
ORDER BY posts.created_at DESC

如果需要,您还可以考虑groups表。但是没有必要,因为group_id表中有users

class Post < ActiveRecord::Base
  belongs_to  :user
  has_one :group, through: :user

  scope :latest_posts_by_group, ->(group) {
    joins(:group).
    where(groups: {id: group.id}).
    reorder(created_at: :desc)
  }
end

这会创建一个这样的SQL:

SELECT posts.* FROM posts
  INNER JOIN users ON users.id = posts.user_id
  INNER JOIN groups ON groups.id = users.group_id
WHERE groups.id = ?
ORDER BY posts.created_at DESC

有关详细信息,请查看Rails Guides