tl;dr:
Devise::RegistrationsController は関連付けられたポリモーフィック モデルをインスタンス化しません。それを解決する最善の方法は何ですか?
設定:
私はさまざまなエンティティ (人、企業など) に関連付けている住所モデルを持っているため、ポリモーフィックな関係を使用しています。
class Person < ActiveRecord::Base
has_one :address, :as => :addressable
accepts_nested_attributes_for :address # to make fields_for work
end
class Address < ActiveRecord::Base
belongs_to :addressable, :polymorphic => true
end
Person モデルを Devise モデルとして使用しましたが、新しいアカウントにサインアップするときに Address オブジェクトがインスタンス化または保存されないという問題に遭遇しました。
私の知る限り、Devise RegistrationController (ルーティング: ) に置き換えられた Person コントローラーには、Devisenew_person_registration GET /person/sign_up(.:format) devise/registrations#new
の使用を開始する前にトリックを行っていたそれぞれのオブジェクトをインスタンス化するコードがありました。
class PeopleController < ApplicationController
[...]
def create
@person = Person.new(params[:person])
@person.address = Address.new(params[:address])
[...some checking...]
@person.save
@person.address.save
end
def new
@person = Person.new
@person.address = Address.new
end
end
Devise::RegistrationsController が Address オブジェクトを作成していないようです。
提案された解決策の 1 つは、コールバックを使用してオブジェクトを初期化することでした。したがって、私の個人モデルは次のようになります。
before_create :instantiate_all
before_save :save_all
def save_all
self.address.save
self.save
end
def instantiate_all
if self.address.nil?
self.address = Address.new
end
end
それで私はまだ得ます
NoMethodError (undefined method `address' for nil:NilClass):
app/models/person.rb:25:in `save_all'
RegistrationController をオーバーライドすることを検討していましたが、呼び出すsuper
と、それぞれの親メソッドのブロック全体が実行されるため、目的のアクションを挿入できないようです。
最後に、コントローラーをオーバーライドし、そのコードをコピーしてコードを追加することは、これを行う唯一の方法としてはあまりにも間違っているようです。
それについてのあなたの考えに感謝します。