如何在 has_many 关系中急切加载最新的对象?
Posted
技术标签:
【中文标题】如何在 has_many 关系中急切加载最新的对象?【英文标题】:How can I eager load the most recent object in a has_many relationship? 【发布时间】:2011-06-12 05:52:41 【问题描述】:我有一个 Rails 3 应用程序,其中包含类别和帖子等模型。
类别
has_many :posts
发帖
belongs_to :category
我希望能够显示一个类别列表,其中列出了最近的帖子,而无需循环访问每个类别的数据库并仅拉回每个类别的一个帖子。
我想做与这个问题相同的事情 - SQL join: selecting the last records in a one-to-many relationship - 但希望使用 Active Record。
这是一件愚蠢的事情吗?我是否应该通过急切加载来撤回某个类别的所有帖子?我担心性能,这就是我开始研究这个的原因。
【问题讨论】:
【参考方案1】:如果不自己构建查询,我不确定这是否可行。这样做的问题是,当您开始获得条件或试图限制结果时,rails 处理急切加载的方式并不是那么好。您可以通过创建另一个关联来使包含几乎做您想做的事情:
class Category < ActiveRecord::Base
has_one :last_post, :class_name => "Post", :foreign_key => "category_id", :order => "created_at desc"
end
那么就可以正常使用includes了:
Category.includes(:last_post).all
但是,这样做的问题是,由于生成的 sql,它仍然从类别中选择所有帖子,即使当您调用 category.last_post 时它只返回最后一个帖子。它会生成类似这样的sql:
SELECT `categories`.* FROM `categories`
SELECT `posts`.* FROM `posts` WHERE (`posts`.category_id IN (1,2)) ORDER BY created_at desc
【讨论】:
感谢您的回答 - 所以在您看来,为这类事情构建查询会更好吗?以上是关于如何在 has_many 关系中急切加载最新的对象?的主要内容,如果未能解决你的问题,请参考以下文章