9

Nach dem Upgrade von Rails 3,2-4,1, der folgende Code, der zur Arbeit verwendet Einsparung jetzt versagt:Nach dem Upgrade 4.1, neue polymorphe Assoziationen Rails sind ungültig, wenn sie zusammen mit ihren Eltern

in einem Controller/spec:

post = user.posts.build 
post.contacts << contact # contact is a persisted record 
post.save! # now fails 

ich versuche im Grunde zusammen mit seinem zugehörigen Kontakt den Posten zu speichern, die einen contact_publishment Rekord on-the-fly erstellen sollten. Der Fehler ist auf den neuen contact_publishment Rekord: „Veröffentlichbar darf nicht leer sein“

das Modell:

class Contact 
    ... 
    has_many :contact_publishments 
    ... 
end 

class ContactPublishment 
    ... 
    belongs_to :publishable, polymorphic: true 
    belongs_to :contact 
    validates_uniqueness_of :publishable_id, :scope => [:contact_id, :publishable_type] 
    validates_presence_of :contact, :publishable 
    ... 
end 

class Post 
    ... 
    has_many :contact_publishments, as: :publishable 
    has_many :contacts, through: :contact_publishments 
    ... 
end 
+0

Sie erhalten den Fehler auf der '' speichern oder auf der '' << Linie!? – nathanvda

+0

in der 'speichern!'. –

+0

Wäre hilfreich, um Ihre Validierungen zu sehen – Benj

Antwort

9

In Rails 3.2 Inhabermodell wurde vor der Validierung verschachtelt Verein, in 4.1 Validierung vor Modell gespeichert ausführen gespeichert, und weil Post nicht gespeichert, Validierung

class ContactPublishment 
    validates_presence_of :publishable 

nicht Validierung passieren läßt (post nicht in db gespeichert)

Für beheben dieses Problems können Sie Validierung in Post-Modell (Validierung auf ContactPublishment deaktivieren wurde von Kontakt-Modell genannt)

class Post < ActiveRecord::Base 
     has_many :contact_publishments, as: :publishable, validate: false 

oder ersetzen Präsenz Validierung wie folgt aus:

class ContactPublishment < ActiveRecord::Base 
    validates_associated :publishable 

change_column :contact_publishments, :publishable_type, :string, null: false 
change_column :contact_publishments, :publishable_id, :integer, null: false 

oder tun es durch proxy_association

+0

Vielen Dank! es funktionierte! außer den 'change_table' Befehlen, die ich in' change_column' ändern musste. Großes Dankeschön, ich war für ein paar Tage dran. –

+0

Natürlich wäre es korrekt change_column, als er schrieb, über ALTER TABLE nachgedacht. Vielen Dank! – Vakiliy

+0

Wow, das ist eine seltsame Sache für sie, sich in Rails zu ändern ...: P –

1

Ich denke, die Vereinigung nicht aktualisiert, weil Sie nicht inverse_of Setup zwischen dem Kontakt haben und contact_publishing.

From the docs about setting up a :through

Wenn Sie die Zuordnung ändern gehen (und nicht nur von sie lesen), dann ist es eine gute Idee, die festlegen: inverse_of Option auf dem Quelle Verein auf dem Join-Modell . Dadurch können die zugehörigen Datensätze erstellt werden, die automatisch die entsprechenden Join-Modell-Datensätze erstellen, wenn sie gespeichert werden.

+1

Versuchte es und es hat nicht funktioniert. Egal, das Problem liegt nicht beim 'contact', sondern bei' contact_publishing' und 'post'. Außerdem funktioniert 'inverse_of' nicht mit polymorphen Assoziationen, so dass es im Falle des' post' nicht funktioniert. –