

### 現在、Railsのアプリを作成しています。以下、costsテーブルの「signカラムの最小値 → 最大値」
で並び替えをしたいのですがどのようにすれば良いでしょうか？

「signカラムの最小値 → 最大値」で並び替えをしたいと思った理由は、RailsのGem
cocoonを使用しているのですが、formで登録後、show.html.erbを見ると、formで登録した順番と表示が異なっているからです。

・環境  
Rails 4.2.3

・Gem  
cocoon  
<https://github.com/nathanvda/cocoon>  
<http://rails.densan-labs.net/form/relation_register_form.html>

【subjects/_form.html.erb】内の「明細を追加」ボタンを押すと、パーシャルファイル( _cost_fields.html.erb
)の内容が追加されます。

### signカラム データ型：string

[code]

    id: 125,
    quantity: "1",
    product: "商品B",
    created_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    updated_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    sign: "2",
    subject_id: 93
    
    id: 125,
    quantity: "3",
    product: "商品A",
    created_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    updated_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    sign: "1",
    subject_id: 93
    
    id: 125,
    quantity: "5",
    product: "商品C",
    created_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    updated_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    sign: "3",
    subject_id: 93
    
[/code]

### 並び替え後、viewでは以下の順番で表示したいです(signカラムの最小値→最大値)。

[code]

    id: 125,
    quantity: "3",
    product: "商品A",
    created_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    updated_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    sign: "1",
    subject_id: 93
    
    id: 125,
    quantity: "1",
    product: "商品B",
    created_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    updated_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    sign: "2",
    subject_id: 93
    
    id: 125,
    quantity: "5",
    product: "商品C",
    created_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    updated_at: Tue, 13 Sep 2016 15:53:42 JST +09:00,
    sign: "3",
    subject_id: 93
    
[/code]

【subjects_contoroller.rb】

[code]

    class SubjectsController < ApplicationController
      before_action :set_subject, only: [:show, :edit, :update, :destroy]
    
      # GET /subjects/1
      # GET /subjects/1.json
      def show
      end
    
      private
        # Use callbacks to share common setup or constraints between actions.
        def set_subject
          @subject = Subject.find(params[:id])
        end
    
      end
    
    end
    
[/code]

【subject.rb】

[code]

    class Subject < ActiveRecord::Base
      has_many :costs, dependent: :destroy
      accepts_nested_attributes_for :costs, allow_destroy: true     
    end
    
[/code]

【cost.rb】

[code]

    class Cost < ActiveRecord::Base
      belongs_to :subject
    end
    
[/code]

【subjects/_form.html.erb】

[code]

    <%= form_for(@subject) do |f| %>
      <%= f.error_messages! %>
      <table>
        <tr>
          <td class="customer_right_space">
            <div class="field form-group">
              <%= f.label :顧客 %><br>
              <%= f.text_field :customer, class: 'form-control', placeholder: 'Sample㈱' %>
            </div>
          </td>
          <td>
            <div class="field form-group">
              <%= f.label :件名 %><br>
              <%= f.text_field :subject, class: 'form-control', placeholder: 'Sample㈱ SNO.720' %>
            </div>
          </td>
        </tr>
      </table>
        <%= f.fields_for :costs do |costs_form| %>
          <%= render 'cost_fields', f: costs_form %>
        <% end %>
        <div class="text-center">
          <%= link_to_add_association '明細を追加', f, :costs %>
        </div>
        <div class="actions text-center">
          <%= f.submit '登録', class: 'btn btn-default btn-success visited_white' %>
        </div>
    <% end %>
    
[/code]

【subjects/_cost_fields.html.erb】 ※ 上記の「明細を追加」ボタンをクリックしたときに追加される内容です。

[code]

        <div class="nested-fields">
          <table class="table table-bordered">
            <tr class="success">
              <th class="text-center">符号</th>
              <th colspan="3" class="text-center">材質・品名</th>
              <th class="text-center">圧力</th>
              <th class="text-center">サイズ</th>
              <th colspan="3" class="text-center">備考</th>
            </tr>
            <tr>
              <td rowspan="3" class="vertical_center"><%= f.text_field :sign, class: 'form-control' %></td><!-- 符号 -->
              <td colspan="3" class="field form-group"><%= f.text_area :product, class: 'form-control', placeholder: '商品A' %></td><!-- 材質・品名 -->
              <td class="field form-group"><%= f.text_field :pressure, class: 'form-control' %></td><!-- 圧力 -->
              <td class="field form-group"><%= f.text_field :size, class: 'form-control' %></td><!-- サイズ -->
              <td colspan="3" class="field form-group"><%= f.text_area :remarks, placeholder: "備考", class: 'form-control'  %></td><!-- 備考 -->
            </tr>
            <tr>
              <th class="text-center">数量</th>
              <th class="text-center">HVK</th>
              <th class="text-center">Fujii</th>
              <th class="text-center">Imamoto</th>
              <th class="text-center">原価</th>
              <th class="text-center">原合計</th>
              <th class="text-center">売価</th>
              <th class="text-center">売合計</th>
            </tr>
            <tr class="up_area">
              <td class="field form-group"><%= f.text_field :quantity, id: "num01", class: 'form-control num' %></td><!-- 数量 -->
              <td class="field form-group"><%= f.text_field :hvk, id: "num02", class: 'form-control hvk num' %></td><!-- HVK -->
              <td class="field form-group"><%= f.text_field :fujii, id: "num03", class: 'form-control fujii num' %></td><!-- Fujii -->
              <td class="field form-group"><%= f.text_field :imamoto, id: "num04", class: 'form-control imamoto num' %></td><!-- Imamoto -->
              <td class="field form-group"><%= f.text_field :unit_price, id: "ans01", class: 'form-control unit_price' %></td><!-- 原価 -->
              <td class="field form-group"><%= f.text_field :price_total, id: "ans02", class: 'form-control price_total' %></td><!-- 原合計 -->
              <td class="field form-group"><%= f.text_field :selling_price, id: "num05", class: 'form-control selling_price_total num' %></td><!-- 売価 -->
              <td class="field form-group"><%= f.text_field :selling_price_total, id: "ans03", class: 'form-control selling_price_total' %></td><!-- 売合計 -->
            </tr>
            <tr>
              <td><%= link_to_remove_association '削除', f, class: 'btn btn-default' %></td>
            </tr>
          </table>
        </div>
    
[/code]

【subjects/show.html.erb】

[code]

    <table>
     <tr>
       <th>符号</th>
       <th>数量</th>
       <th>製品</th>
       <th>圧力</th>
       <th>サイズ</th>
     </tr>
    
    <% @subject.costs.each do |cost| %> 
     <tr>
       <td><%= cost.sign %></td>
       <td><%= cost.quantity %></td>
       <td><%= cost.product %></td>
       <td><%= cost.pressure %></td>
       <td><%= cost.size %></td>
     </tr>
    <% end %>
    </table>
    
    <%= link_to 'Edit', edit_subject_path(@subject) %>
    <%= link_to 'Destroy', @subject, method: :delete, data: { confirm: 'Are you sure?' } %>
    <%= link_to 'Back', subjects_path %>
    
[/code]


CC BY-SA 3.0
2016-09-13T13:23:20.043
28862
2016-09-13T22:57:07.237
2016-09-13T13:29:20.823
12323
12323
question
ruby-on-rails ruby rails-activerecord
Railsのアプリを作成しています。ActiveRecordで、カラムの最小値 → 最大値 で並び替えをする方法を教えてください。


質問と直接関係はありませんが、適切な場面では`params`を直接使うのでなく`Strong Parameters`を使いましょう。

## 回答

適切なところで`.costs.order(:sign)`して `sign`でソートすれば欲しい並びを得られます。

Viewで`order`を呼ぶことに抵抗がないのであれば  
`<% @subject.costs.order(:sign).each do |cost| %>`  
で解決するはずです（本来はコントローラ側で適切に呼び出せるようにリファクタした方がよいと思います。また`order`と直接の関係はありませんが、おそらく今のソースだとN+1問題も発生します。）。

`costs.order(:sign)`ではなく、`.includes(:cost).order('costs.sign')`を適切な箇所で呼ぶという案もあると思います（おそらくこちらの方法だとN+1問題も解消しますし、コントローラで`order`が呼べます）。  
こちらで試しようがないですが`Subject.find(取得したいID).includes(:cost).order('costs.sign')`といったような形になると思います。


CC BY-SA 3.0
2016-09-13T13:34:13.673
28863
2016-09-13T22:57:07.237
2016-09-13T22:57:07.237
9008
9008
28862
answer