title: Should nested resources and strong params use 'model' or 'model_attributes' and why? (unpermitted parameter: model)
body: <p>I have a nested form that creates an <code>@address</code> with each successful <code>@purchase</code>. </p>
  
  <p>My schema and model associations are set up so that <code>Purchase</code> holds the foreign keys for everything else:</p>
  
  <p><strong>address.rb</strong></p>
  
  <pre><code>belongs_to :user
  has_many :purchases, foreign_key: :address_id
  has_many :items, foreign_key: :address_id
  </code></pre>
  
  <p><strong>purchase.rb</strong></p>
  
  <pre><code>belongs_to :sender, class_name: "User"
  belongs_to :recipient, class_name: "User"
  belongs_to :address
  belongs_to :item
  accepts_nested_attributes_for :address
  </code></pre>
  
  <p><strong>item.rb</strong></p>
  
  <pre><code>belongs_to :user
  has_many :purchases, foreign_key: :item_id
  belongs_to :address
  </code></pre>
  
  <p>I've found <a href="https://stackoverflow.com/questions/14656812/associationtypemismatch-object-expected-got-hashwithindifferentaccess-in-rail">some answers</a> that suggest whitelisting the nested attribute params in my controller with a <code>.permit(address_attributes: [:name])</code> in the controller instead of <code>.permit(address: [:name])</code>, but neither of the two create the record.</p>
  
  <p><strong>purchases_controller.rb</strong></p>
  
  <pre><code>def confirmation
   @item = Item.friendly.find(params[:item_id])
   @address = @transaction_wizard.transaction.build_address
  end
  
  def confirm
   current_step = params[:current_step]
   @item = Item.friendly.find(params[:item_id])
   @transaction_wizard = wizard_transaction_for_step(current_step)
   @transaction_wizard.transaction.attributes = address_params
   session[:transaction_attributes] = @transaction_wizard.transaction.attributes
  
   if @transaction_wizard.valid?
    next_step = wizard_transaction_next_step(current_step)
    create and return unless next_step
  
    redirect_to action: next_step
   else
    redirect_to action: current_step
   end
  end
  
  def create
   if @transaction_wizard.transaction.save
    redirect_to root_path, notice: "Bid sent. If you would like to cancel before it's approved, you can do so #{view_context.link_to('here', transactions_sent_unapproved_path)}.".html_safe
   else
    redirect_to item_path(@transaction_wizard.transaction.item), notice: 'There was a problem making this bid.'
   end
  end
  
  private
  def address_params
   params.require(:transaction_wizard).permit(address_attributes: [:name, :street, :street_2, :city, :state, :zip_code])
  end
  </code></pre>
  
  <p>Whether I use <code>address_attributes</code> or <code>address</code>, the result is the same:</p>
  
  <pre><code>Parameters: {"transaction_wizard"=&gt;
               {"address"=&gt;
                {"name"=&gt;"name", 
                 "street"=&gt;"123 st", 
                 "street_2"=&gt;"apt 5", 
                 "state"=&gt;"AL", 
                 "zip_code"=&gt;"48489"}
               }, 
               "current_step"=&gt;"confirmation", 
               "commit"=&gt;"Complete offer", 
               "item_id"=&gt;"friendly-item-id"
              }
  Unpermitted parameter: address
  </code></pre>
  
  <p>This is my form:</p>
  
  <pre><code>&lt;%= form_for @transaction_wizard, as: :transaction_wizard, url: confirm_item_transaction_wizard_path(@item) do |f| %&gt;
   &lt;%= f.fields_for :address do |address| %&gt;
    &lt;%= address.text_field :name %&gt;
    &lt;%= address.text_field :street %&gt;
    &lt;%= address.text_field :street_2 %&gt;
    &lt;%= address.text_field :city %&gt;
    &lt;%= address.text_field :state %&gt;
    &lt;%= address.text_field :zip_code %&gt;
   &lt;% end %&gt;
  
   &lt;%= f.submit "Submit" } %&gt;
  &lt;% end %&gt;
  </code></pre>
  
  <p>What gives? How can I make my controller accept these params?</p>
  
  <hr>
  
  <p>Update: Changing <code>address</code> to <code>addresses</code> requires that I change that <code>@address</code> variable in the controller to <code>@address = @transaction_wizard.transaction.build_addresses</code>. This causes an <code>uninitialized constant Transaction::Addresses</code> error. </p>