2

これは私のモデルです:

class Speaker < ActiveRecord::Base
  belongs_to :session, :foreign_key => :session_id, :class_name => :Session
  belongs_to :speakable, :polymorphic => true
end  

class Session < ActiveRecord::Base
  has_many :speakers
  accepts_nested_attributes_for :speakers
end

class Person < ActiveRecord::Base
  has_many :speakers, :as => :speakable
end       

class Company < ActiveRecord::Base
  has_many :speakers, :as => :speakable
end  

私が今やりたいことは、次のようなものです: app/views/sessions/edit.html.erb

  <% f.fields_for :speakers do |sf| %>
    <p>
      <%= sf.label :speaker %><br />
      <%= sf.collection_select :speakable, Company.all + Person.all, :id, :full_name %>  
    </p>
  <% end %>

しかし、ポリモーフィック割り当てのために機能していません。どうすればこの問題にアプローチできますか?

編集: エラーは次のとおりです。

undefined method `base_class' for String:Class

パラメータは次のとおりです。

"speaker"=>{"speakable"=>"1063885469", "session_id"=>"1007692731"}

speakable に渡される値は、Speaker/Company の ID です。はい、これがcollection_select返すように指定した値ですが、どうすれば両方の値 (speakable_idspeakable_type) を指定できますか?

4

2 に答える 2

1

を使用してhidden_fieldを保存できますspeakable_type。このようにhidden_field、選択したオプションが変更されるたびにの値を変更する必要があります。これが最善のアプローチかどうかはわかりませんが、機能します...

お役に立てば幸いです。

編集

:onchange選択でオプションを定義する必要があります。

<%= sf.collection_select :speakable, Company.all + Person.all, :id, 
   :full_name, {}, {:onchange => "setSpeakableType()"} %>  

は値hidden_fieldから始まりnilます。

<%= sf.hidden_field :speakable_type, :value => nil %>

そして、あなたのsetSpeakableType()関数は適切なを設定する必要がありますspeakable_type

于 2010-05-11T17:35:38.937 に答える
0

これを解決した2つの方法。

1 つ目は、id がどのタイプから始まるかを把握できるように、フォーム内のコレクションを変更することです。これに似たもの:


そして、コントローラーアクションで:

def action
  if params[:speaker][:speakable].begins_with?("Person:")
     speak_type = 'Person'
     speak_id = params[:speaker][:speakable].split(":")[1].to_i
  elsif params[:speaker][:speakable].begins_with?("Company:")
     speak_type = 'Company'
     speak_id = params[:speaker][:speakable].split(":")[1].to_i
  end
  params[:speaker].delete(:speakable)
  obj = Speaker.new(params[:speaker])
  obj.speaker_type = speak_type
  obj.speaker_id = speak_id
  ... rest of action ... 
end

2 つ目は、javascript を使用して、ページで非表示になっている非表示フィールド speakable_type と speakable_id を変更することです。オートコンプリータを使用してこのフィールドに入力することになったので、選択が行われたときに JavaScript を呼び出すのは簡単でした。2 番目の方法は、コントローラーをよりクリーンにします。

于 2010-05-11T17:49:46.107 に答える