2017-01-31 4 views
0

sale.rb "親"ネストされたfields_for形は文句を言わない子供がレール5

class Sale < ActiveRecord::Base 
    has_many :branch_history_solds 
    accepts_nested_attributes_for :branch_history_solds, :reject_if => lambda { |a| a[:content].blank? }, 
           :allow_destroy => true 
end 

class SalesController < ApplicationController 
    before_action :set_sale, only: [:show, :edit, :update, :destroy] 

    # GET /sales 
    # GET /sales.json 
    def index 
    @sales = Sale.all 
    end 

    # GET /sales/1 
    # GET /sales/1.json 
    def show 
    end 

    # GET /sales/new 
    def new 
    @sale = Sale.new 
    @sale.branch_history_solds.build 
    end 

    # GET /sales/1/edit 
    def edit 
    end 

    # POST /sales 
    # POST /sales.json 
    def create 
    @sale = Sale.create(sale_params) 
    # @sale.branch_history_solds.build 

    respond_to do |format| 
     if @sale.save 
     format.html { redirect_to @sale, notice: 'Sale was successfully created.' } 
     format.json { render :show, status: :created, location: @sale } 
     else 
     format.html { render :new } 
     format.json { render json: @sale.errors, status: :unprocessable_entity } 
     end 
    end 
    end 

    # PATCH/PUT /sales/1 
    # PATCH/PUT /sales/1.json 
    def update 
    @sale = Sale.find(params[:id]) 

    respond_to do |format| 
     if @sale.update_attributes(sale_params) 
     format.html { redirect_to @sale, notice: 'Sale was successfully updated.' } 
     format.json { render :show, status: :ok, location: @sale } 
     else 
     format.html { render :edit } 
     format.json { render json: @sale.errors, status: :unprocessable_entity } 
     end 
    end 
    end 

    # DELETE /sales/1 
    # DELETE /sales/1.json 
    def destroy 
    @sale.destroy 
    respond_to do |format| 
     format.html { redirect_to sales_url, notice: 'Sale was successfully destroyed.' } 
     format.json { head :no_content } 
    end 
    end 

    private 
    # Use callbacks to share common setup or constraints between actions. 
    def set_sale 
     @sale = Sale.find(params[:id]) 
    end 

    # Never trust parameters from the scary internet, only allow the white list through. 
    def sale_params 
     params.require(:sale).permit(:receipt_no, :customer_name, :phone_number, :email, :branch_id, :paid, branch_history_sold_attributes: [:id, :sold, :branch_product_id]) 
    end 
end 

branch_history_sold.rb "子" をオブジェクト

class BranchHistorySold < ActiveRecord::Base 
    belongs_to :sale 

end 

class BranchHistorySoldsController < ApplicationController 

    def index 
    @search = BranchHistorySold.ransack(params[:q]) 
    @branch_sold_histories = @search.result(distinct: true).group(:name).sum(:sold) 
    end 

    def create 
    @sale = Sale.find(params[:sale_id]) # Find specific branch_product we will be working with 
    @branch_history_sold = @sale.branch_history_solds.create(branch_history_sold_params) # Enable whitelisted attributes to get created 
    flash[:notice] = "New products have been Sold from branch" # flash notice will show immediately after branch_history_sold gets created 
    redirect_to branch_product_path(@branch_product) # redirect to branch_product show page 
    end 

    def destroy 
    @sale = Sale.find(params[:sale_id]) # Find specific branch_product we will be working with 
    @branch_history_sold = @sale.branch_history_solds.find(params[:id]) # Find specific branch_history_sold that will be destroyed 
    @branch_history_sold.destroy # destroy branch_history_sold 
    flash[:notice] = "Newly sold products have been added back to branch" # flash notice will show immediately after branch_history_sold is destroyed 
    redirect_to branch_product_path(@branch_product) # redirect to branch_product show page 
    end 

    private 

    def branch_history_sold_params 
    params.require(:branch_history_sold).permit(:sold, :customer_name) # whitelisted attributes 
    end 

end 

そして最後にfields_for属性

<div class="container"> 
     <div class="row"> 
      <%= form_for @sale, html: { class: "form-horizontal" } do |f| %> 
       <!-- Text input--> 
       <div class="form-group"> 
        <label class="col-md-1 control-label">R/NO</label> 
        <div class="col-md-6"> 
         <%= f.collection_select(:branch_id, Branch.all, :id, :name) %> 
        </div> 
       </div> 
       <!-- Text input--> 
       <div class="form-group"> 
        <label class="col-md-1 control-label">R/NO</label> 
        <div class="col-md-6"> 
         <%= f.text_field :receipt_no, placeholder: "Receipt number", class: "form-control input-md" %> 
        </div> 
       </div> 
       <!-- Text input--> 
       <div class="form-group"> 
        <label class="col-md-1 control-label" >Name</label> 
        <div class="col-md-6"> 
         <%= f.text_field :customer_name, placeholder: "Prince Abalogu", class: "form-control input-md" %> 
        </div> 
       </div> 
       <!-- Appended Input--> 
       <div class="form-group"> 
        <label class="col-md-1 control-label">Number</label> 
        <div class="col-md-6"> 
         <%= f.text_field :phone_number, placeholder: "08185438075", class: "form-control input-md" %> 
        </div> 
       </div> 
       <!-- Appended Input--> 
       <div class="form-group"> 
        <label class="col-md-1 control-label">E-mail</label> 
        <div class="col-md-6"> 
         <%= f.text_field :email, placeholder: "[email protected]", class: "form-control input-md" %> 
        </div> 
       </div> 

       <!-- Appended Input--> 
       <%= f.fields_for :branch_history_solds, @sale.branch_history_solds.build do |b| %> 
        <div class="form-group"> 
         <label class="col-md-1 control-label">Product</label> 
         <div class="col-md-6"> 
         <%= b.number_field :sold, placeholder: "Quantity" %> 
         </div> 
        </div> 
        <div class="form-group"> 
         <label class="col-md-1 control-label"></label> 
         <div class="col-md-6"> 
          <% @branch = BranchProduct.where :branch_id, 19 %> 
          <%= b.collection_select(:branch_product_id, BranchProduct.where(branch_id: params[:branch_id]), :id, :name) %> Select Product 
         </div> 
        </div> 
       <% end %> 

       <!-- Appended Input--> 
       <div class="form-group"> 
        <label class="col-md-1 control-label"></label> 
        <div class="col-md-6"> 
         <%= f.check_box :paid %> Paid 
        </div> 
       </div> 

       <!-- Button (Double) --> 
       <div class="form-group"> 
        <label class="col-md-1 control-label"></label> 
        <div class="col-md-8"> 
         <%= f.button :submit %> 
        </div> 
       </div> 
      <% end %> 
     </div> 
    </div> 
で自分のフォームを作成します

フォームは表示されますが、今は唯一の問題は、私がサブミットした後にブランチ履歴を作成しないということですそれ

答えて

2

問題は、フォーム/モデルがcontent属性を持っていないので、あなたは、ネストされたレコードが拒否されるべきかどうかを評価するために使用しているラムダは、常にtrueを返しますということです。

class Sale < ActiveRecord::Base 
    has_many :branch_history_solds 
    accepts_nested_attributes_for :branch_history_solds, :reject_if => lambda { |a| a[:content].blank? }, 
           :allow_destroy => true 
end 

ます。またね間違った属性をホワイトリストに入れますbranch_history_soldbranch_history_solds

あなたが実際に渡された属性であるためにこれを変更する必要があります:あなたの一般的なセットアップは単なる奇妙であると私はもしそのわずかネーミングを知りませんが、それはあまりをしないしかし

class Sale < ActiveRecord::Base 
    has_many :branch_history_solds 
    accepts_nested_attributes_for :branch_history_solds, :reject_if => lambda { |a| a[:branch_product_id].blank? }, 
           :allow_destroy => true 
end 

センス。

あなたが販売システムやオーダー管理システムのポイントを作成したい場合は、そのようにそれを行うだろう:

class Order 
    belongs_to :customer 
    has_many :line_items 
    has_many :products, through: :line_items 
    accepts_nested_attributes_for :line_items, 
    allow_destroy: true, 
    reject_if: -> { |li| li[:product_id].blank? || li[:quantity].blank? } 
end 

# columns: 
# - order_id [integer, index, foreign key] 
# - product_id [integer, index, foreign key] 
# - quantity [decimal or integer] 
# - price [decimal] 
# - subtotal [decimal] 
class LineItem 
    belongs_to :order 
    belongs_to :product 
end 

class Product 
    has_many :line_items 
    has_many :orders, through: :line_items 
end 

class OrdersController 

    def new 
    end 


    def create 
    @order = Order.new(order_params) do 
     order.customer = current_user 
    end 
    if (@order.save) 

    else 

    end 
    end 

    private 
    def order_params 
    params.require(:order) 
      .permit(:foo, :bar, line_item_attributes: [:product_id, :quantity]) 
    end 
end 

あなただけのユーザーが非常に限られた数を通過させる必要があることを注意パラームの - ユーザーからの価格のようなものを取ることはありません。実際の価格設定ロジックは、モデルレイヤーで実行する必要があります。また、オーダー・モデルからお客様の詳細を切り離すこともできません。そうしないと、すべての繰り返し注文によってデータが複製されます。私は検索のような追加機能を追加する前に、実際のドメインモデルを取得するのに時間を費やすだろう。

+1

在庫を追跡したい場合は、追加のモデルで行う必要があります。上に入れないようにしてください。場所(店舗、支店など)を追跡するモデルと、ある場所にある製品の在庫を追跡するモデルが必要です。 – max

+0

@oklasもう一度読む。ホワイトリストに載っているコントローラにタイプミスがあります。モデルにはありません。あなたのコメントは理にかなっていません。 – max

関連する問題