Cha*_*les 31 ruby mysql ruby-on-rails-3
在带有mysql的Rails 3中,假设我有两个模型,Customers和Purchases,显然是购买belongs_to客户.我想找到2个或更多订单的所有客户.我可以简单地说:
Customer.includes(:purchases).all.select{|c| c.purchases.count > 2}
Run Code Online (Sandbox Code Playgroud)
但实际上,上面的行会查询Customer.all和Purchase.all的大小,然后在ruby中执行"select"类型处理.在一个大型数据库中,我更愿意避免在ruby中进行所有这些"选择"计算,并让mysql进行处理,只给我合格客户列表.这要快得多(因为mysql更多地调整了这一点)并且显着减少了数据库的带宽.
不幸的是,我无法用rails中的构建块(where,having,group等)来实现代码,以实现这一点,这些内容符合(psudo-code):
Customer.joins(:purchases).where("count(purchases) > 2").all
Run Code Online (Sandbox Code Playgroud)
我将满足于直接的MySql解决方案,尽管我更喜欢在优雅的rails框架中解决这个问题.
Jam*_*msi 73
无需安装宝石即可实现此功能(尽管metawhere很酷)
Customer.joins(:purchases).group("customers.id").having("count(purchases.id) > ?",0)
Run Code Online (Sandbox Code Playgroud)
关于这些东西的文档在这一点上相当稀少.如果你要做更多与此类似的查询,我会考虑使用Metawhere.使用Metawhere,你可以这样做(或类似的东西,不确定语法是否完全正确):
Customer.includes(:purchases).where(:purchases => {:count.gte => 2})
Run Code Online (Sandbox Code Playgroud)
这样做的好处是,MetaWhere仍然使用ActiveRecord和arel来执行查询,因此它可以使用'new'trail3 3进行查询.
此外,您可能不希望.all最后调用,因为这将导致查询ping数据库.相反,您希望使用延迟加载而不是命中数据库,直到您实际需要数据(在视图中,或处理实际数据的其他方法).
| 归档时间: |
|
| 查看次数: |
13781 次 |
| 最近记录: |