Help us understand the problem. What is going on with this article?

form_tagとform_forの違い

More than 1 year has passed since last update.

form_for

「モデルの新規インスタンスに値を追加して保存」したい場合はform_for

form_forは、特定の「モデル」を編集・追加するためのフォームを生成するヘルパーメソッド。
特定のテーブルにレコード(モデルクラスのインスタンス)だけを新規作成、更新するときに利用する。

このような特性があるので、form_tagとform_forは下記のように使い分ける。

■form_for: 任意のモデルに基づいたformを作るときに使う(投稿フォームなど)
→フォームに入力した情報をモデルを通じて、テーブルに追加・編集する
■form_tag: モデルに基づかないformを作るときに使う(検索フォームなど)
→検索は別にモデルに編集やインスタンスの追加をする必要はない

(使い方)

form_for.rb
<%= form_for(モデルクラスのインスタンス) do |f| %><% end %>

form_forは引数のインスタンスが何も情報を持っていなければ自動的にcreateアクションへ、すでに情報を持っている場合はupdateアクションへ自動的に振り分けてくれる。form_tagのようにルーティングパスを指定する必要がないのでラク。

モデルクラスのインスタンスはコントローラで予め定義しておくこと!

form_for内で使うメソッドは、f.htmlタグ名 :カラム名の形で指定

【form_forにおけるメソッドの例】

メソッド           用途           
f.label labelのlabelタグを表示 
f.text_field textのinputタグを表示
f.date_select モデルで設定したフィールドをselectタグで選べるようにして表示  
f.check_box checkboxのinputタグを表示
f.number_field numberのinputタグを表示
f.submit submitのinputタグを表示

参照URL:http://railsdoc.com/form

sample.rb
    <%= form_for [@product, @review] do |f| %>
          <div style="margin: 8px 0">
            <%= f.label :nickname, style: { 'margin-right' => 8 } %>
            <%= f.text_field :nickname, placeholder: 'nickname', value: '' %>
          </div>
          <div style="margin: 8px 0">
            <%= f.label :評価, style: { 'margin-right' => 8 } %>
            <%= f.number_field :rate, placeholder: '評価', value: 1, max: 10, min: 1, html: { class: "search__query", style: 'text-align: right;' } %>
          </div>
          <div style="margin: 8px 0">
            <%= f.text_area :review, placeholder: 'レビューを書いてね!', style: 'width: 100%;height: 300px;' %>
          </div>
          <div class="row">
            <div class="col10 push1">
              <%= button_tag type: "submit", class: "btn btn--block" do %>
              投稿する<i class="icon-arrow-right"></i>
              <% end %>
            </div>
          </div>
      <% end %>

1行目のform_forの引数が配列になっている。配列の1つ目の要素のインスタンスのidがパスの:product_idに入る。今回はパスのネストが2段階なので、form_forの引数のインスタンスは2つ。

form_forの引数について

resourcesを2回ネストした場合

routes.rb
resources :users do
  resources :products do
    resources :reviews
  end
end
controller.rb
def new
  @user = User.find(4)
  @product = Product.find(2)
  @review = Review.new
end
new.html.erb
<%= form_for ( [@user, @product, @review ] ) do |f| %>
  (中略)
<% end %>
送られるリクエスト
↓↓
# HTTPメソッド
POST
# パス
/users/4/product/2/reviews

form_tagとform_forでのパラメータへの保存方法の違い

binding.pryを使ってparamsを見るとよく分かるが、form_forはparamsのハッシュの中に別のハッシュが内包されており、ハッシュの二重構造が存在している状態になっている。

alt

ターミナルで見るとこんな感じ
↓↓↓↓

>>>new.html.erb
<%= form_for(@book) do |f| %>
  <%= f.text_field :name %>
  <%= f.text_area :detail %>
<% end %>

>>>ターミナル
params
# { book: { name: "入力された名前", detail: "入力された詳細" } }

※上の例のbookはモデル名

なので、これらをハッシュをまずは分離してあげる必要がある。そこで使用するので、「require」メソッド。これを利用することで、ストロングパラメータを設定することができる。

<requireメソッド>
params.require(:モデル名).permit(:カラム名)
→これでparamsの中からモデル名(book)のハッシュ({ name: "入力された名前", detail: "入力された詳細" })を呼び出している

【参照URL】
https://qiita.com/tsubasakat/items/4ececaba4efc928c0792
https://www.sejuku.net/blog/13163

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした