Rails 3.1:has_many,:通过复杂的排序

时间:2012-01-09 18:15:45

标签: ruby-on-rails ruby-on-rails-3

我有一个带有line_items和供应商的订单模型。在显示订单时,我想按供应商对line_items进行分组。

class LineItem < ActiveRecord::Base
  belongs_to :order
  belongs_to :vendor
end

class Order < ActiveRecord::Base
  has_many :line_items
  has_many :vendors, :through => :line_items
end

class Vendor < ActiveRecord::Base
  has_many :line_items
end

我想显示供应商和订单项的已排序列表:

You have placed an order for the following items:

  Vendor 1
    Line item 1
    Line item 2
    Line item 3

  Vendor 2
    Line Item 4
    Line Item 5

  ...

我目前的想法是

order.vendors.each do |a_vendor|
  a_vendor.name
  !!?? AND THEN WHAT GOES HERE ??!!
end

请帮忙。我无法弄清楚这一点。也许这可以通过排序来完成?

如果订单只有一个供应商,那么我只想展示一个供应商。

2 个答案:

答案 0 :(得分:5)

这个怎么样:

<% @order.line_items.all.group_by{|i| i.vendor}.each do |vendor, items| %>
  <%= content_tag :h2, vendor.id %>
  <ul>
  <% items.each do |i| %>
       <%= content_tag :li, i.id %>
  <% end %>
  </ul>
<% end %>

[编辑]

sort_by(&amp;:vendor)与sort_by {| v |相同v.vendor},但块式语法为您提供了更多的灵活性。例如,您可以使用以下命令在控制器中按供应商名称进行排序:

@sorted = @order.line_items.all.group_by(&:vendor).sort_by{|vendor, items| vendor.name}

然后在视图中:

<% @sorted.each do |vendor, items| %>
  <%= content_tag :h2, vendor.name %>
  <ul>
  <% items.each do |i| %>
       <%= content_tag :li, i.id %>
  <% end %>
  </ul>
<% end %>

答案 1 :(得分:1)

或者,可以通过添加SQL片段对模型进行排序 到has_many关联的:order选项。

(参见:http://api.rubyonrails.org/classes/ActiveRecord/Associations/ClassMethods.html#method-i-has_many

class Order < ActiveRecord::Base
  has_many :line_items, :order => "item_number"
  has_many :vendors, :through => :line_items, :order => "name"
end

然后你的观点非常简单:

<% @order.vendors.each do |vendor| %>
  <h3><%= vendor.name %></h3>
  <ul>
    <% vendor.line_items.where(:order_id=>@order.id).each do |item| %>
      <li><%= item.description %></li>
    <% end -%>
  </ul>
<% end -%>