Techioz Blog

アソシエーション has_many に関する複数レベル/三重ネストされたフォーム

概要

Product、ProductVariant、Component の 3 つのクラスがあり、Product のビューを呼び出すときに Product、ProductVariant、および Component の値を設定できるようにするために、三重にネストされたフォームを適用したいと考えています。

モデル

class Product < ApplicationRecord
  has_many :product_variants
  accepts_nested_attributes_for :product_variants
end

class ProductVariant < ApplicationRecord
  has_many :components
  accepts_nested_attributes_for :components
end

class Component < ApplicationRecord
end

製品のコントローラー

 # GET /products/new
  def new
    @product = Product.new
    @product.product_variants.build.components.build
  end

  # POST /products or /products.json
  def create
    @product = Product.new(product_params)

    respond_to do |format|
      if @product.save
      ...
      end
      ...
    end
  end
...
    def product_params
      params.require(:product).permit(:name, product_variants_attributes: [:category, components: [:form]])
    end
end

製品の見方

<%= form_with(model: product) do |form| %>
  ...
  <div>
    <%= form.label :name, style: "display: block" %>
    <%= form.text_field :name %>
  </div>
  <%= form.fields_for :product_variant do |va| %>
    <%= va.label :category, style: "display: block" %>
    <%= va.text_field :category %>
    <%= va.fields_for :components do |co| %>
      <%= co.label :form, style: "display: block" %>
      <%= co.text_field :form %>
    <% end %>
  <% end %>
  <div>
    <%= form.submit %>
  </div>
<% end %>

オブジェクト ProductVariant を初期化して保存することは可能ですが、コンポーネントの場合は Unpermitted パラメーター::components_attributes が表示されますが、その理由がわかりません。

解決策

製品バリアントと同じ方法でコンポーネント パラメータを渡し、_attrbiutes サフィックスを追加する必要があります。

以下を変更します。

params.require(:product).permit(:name, product_variants_attributes: [:category, components: [:form]])

に:

params.require(:product).permit(:name, product_variants_attributes: [:category, components_attributes: [:form]])

https://translate.google.com/translate?hl=ja&sl=en&tl=ja&u=https://api.rubyonrails.org/classes/ActiveRecord/NestedAttributes/ClassMethods.html - One-to-many