如何在Ruby on Rails中修改ActiveRecord_Relation输出

时间:2015-12-30 12:24:21

标签: ruby-on-rails ruby foreach acts-as-taggable-on

我有一个Post模型与gem Acts_as_Taggable_on相结合。

我想显示包含所有标签的所有帖子,但标签应按其使用次数(使用特定标签标记的帖子数量)进行排序。

为此,我通过ActiveRecord_Relation循环并对Tags列进行了排序:

def index
  temp_posts = Post.all.order('updated_at DESC')
  temp_posts.each_with_index do |temp_post, index|
    temp_posts[index].tags = temp_post.tags.sort_by {|tag| -tag.taggings_count}
  end
  @show = temp_posts.first.tags.sort_by {|tag| -tag.taggings_count} # according to this control output it should work
  @posts = temp_posts
end

查看控件输出@show时,标签会根据需要进行排序,但不会保存到temp_posts变量中。因此输出未排序。

我能做些什么来节省'我在循环中做出的改变?

2 个答案:

答案 0 :(得分:0)

由于你有Tag#taggings_count,你可以通过它来订购你的关联。我不知道这是否会与ActsAsTaggable的内容发生冲突,但这就是它在vanilla Rails中的样子。也许ActsAsTaggable有一些选择来完成同样的事情。

class Post < ActiveRecord::Base
  has_many :taggings
  has_many :tags, through: :taggings, -> { order(taggings_count: :desc) }
end

有关详细信息,请参阅Scopes for has_many

如果您不希望全局适用该订单,andrykonchin's idea是一个不错的订单。编写Post#sorted_tags方法,您可以根据需要在Post上访问该方法。将其记忆为实例变量将阻止额外的数据库查询。

class Post < ActiveRecord::Base
  def sorted_tags
    @sorted_tags ||= tags.sort_by(&:taggings_count).reverse
  end
end

答案 1 :(得分:0)

问题最终只是使用无效变量来保存已排序的标签。

Acts as Taggable on使用变量tag_list来存储与Tag模型关联的标记。相反,我错误地使用了变量tags

我的代码的完整正确版本:

def index
  temp_posts = Post.all.order('updated_at DESC')
  temp_posts.each_with_index do |temp_post, index|
    // CHANGE: temp_posts[index].tags => temp_posts[index].tag_list
    temp_posts[index].tag_list = temp_post.tags.sort_by {|tag| -tag.taggings_count}
  end
  @posts = temp_posts
end