7

複雑なネストされたフォームを管理するために、次のフォーム オブジェクトがあります。

= simple_form_for(@profile_form, :url => profiles_path) do |f|
  ...

ルート

resources :profiles

コントローラ

class ProfilesController < ApplicationController
  def new
    @profile_form = ProfileForm.new
  end

  def edit
    @profile_form = ProfileForm.new(params[:id])
  end

  def create
    @profile_form = ProfileForm.new
    if @profile_form.submit(params[:profile_form])
      redirect_to @profile_form.profile, notice: 'Profile was successfully created.'
    else
      render action: "new"
    end
  end

  def update
    @profile_form = ProfileForm.new(params[:id])
    if @profile_form.submit(params[:profile_form])
      redirect_to @profile_form.profile, notice: 'Profile was successfully updated.'
    else
      render action: "edit"
    end
  end
end

フォーム オブジェクト

class ProfileForm
  include ActiveModel::Validations
  include ActiveModel::Conversion
  extend ActiveModel::Naming

  def initialize(profile_id = nil)
    if profile_id
      @profile = Profile.find(profile_id)
      @person = profile.person
    end
  end
  ...
  def submit(params)
    profile.attributes = params.slice(:available_at)
    person.attributes = params.slice(:first_name, :last_name)

    if valid?
      profile.save!
      person.save!
      true
    else
      false
    end
  end
  def self.model_name
    ActiveModel::Name.new(self, nil, "Profile")
  end

  def persisted?
    false
  end
end

しかし、今、このフォームcreateアクションを使用してオブジェクトを編集しているときに呼び出されます。次に、このフォームをどのようにリファクタリングする必要がありますか? 以下のコードは、update別の Profile オブジェクトを作成します。

4

3 に答える 3

6

simple_form_forform_forジョブを実行するために内部的に使用します。form_forメソッドpersisted?を使用して、オブジェクトがデータベースにすでに永続化されているかどうかを判断します。すでに永続化されている場合はform_for、メソッドPUTを使用してフォームを生成し、オブジェクトを更新します。それ以外の場合は、メソッドPOSTを使用してフォームを生成し、新しいオブジェクトを作成します。persisted?したがって、フォーム オブジェクトのメソッドを実装する必要があります。次のように実装できます。

class ProfileForm
  # ...
  def persisted?
    @person.persisted? && @profile.persisted?
  end
  # ...
end

更新の場合、つまり に関連付けられていない@person場合、に関連付ける新しい を作成するとします。この場合、 a は少なくとも the is と同じ長さであると想定しても安全です。したがって、次のようになります。nilPersonProfilePerson@profileProfileFormpersisted?@profilepersisted?

class ProfileForm
  # ...
  def persisted?
    @profile.persisted?
  end
  # ...
end

更新エラーを回避するには、次のように のメソッドundefined local variable or method `id'を定義する必要があります。idProfileForm

class ProfileForm
  # ...
  def id
    @profile.id
  end
  # ...
end
于 2013-06-12T12:14:14.380 に答える
0

こちらをご覧ください: http://apidock.com/rails/ActionView/Helpers/FormHelper/apply_form_for_options!

フォームでレコードを更新する場合は、メソッドProfileForm#persisted?が返されるように記述する必要があります。true

于 2013-06-12T11:58:04.853 に答える