Ich habe die folgenden Modelle, die im Grunde zu verstehen versuchen, dass ein ProfessorWissen vieler Themen für eine bestimmte Ebene hat. Die Fächer sind festgelegt, so dass keine neuen Fächer erstellt werden, sondern nur durch die Wissensjoin-Tabelle mit einem Professor "verbunden" werden.Rails: Einmaligkeit von zwei Attributen in Join-Tabelle verursachen Fehler 500
class Subject < ActiveRecord::Base
# Self Associations
has_many :subcategories, :class_name => "Subject"
belongs_to :category, :class_name => "Subject",:foreign_key => "parent_id"
# Associations
has_many :knowledges
has_many :professors, :through => :knowledges
end
class Professor < ActiveRecord::Base
# Associations
has_many :knowledges
has_many :subjects, :through => :knowledges
...
end
class Knowledge < ActiveRecord::Base
# Associations
belongs_to :professor
belongs_to :subject
has_one :level
attr_accessible :subject_id, :professor_id
validates :subject_id, :uniqueness => { :scope => :professor_id }
end
Ich möchte eine Form haben, die einen Professor lassen wird ein Thema sein Konto hinzuzufügen, und ich beschlossen, eine Form für ein Wissen haben (wie ich will auch eine Ebene einfügen können).
Es sieht wie folgt aus:
<%= simple_form_for @knowledge,:url => professor_knowledges_path, :html => { :class => 'form-horizontal' } do |f| %>
<div class="control-group select optional">
<%= label_tag "Subject Type", nil, :class => "select optional control-label"%>
<div class="controls">
<%= select_tag "Parent Subject", options_from_collection_for_select(@parent_subjects, "id", "name"), :id => "knowledge_parent_subject" %>
</div>
</div>
<%= f.input :subject_id, :collection => @subjects, :label => "Subject" %>
<%= f.input :level %>
<%= f.button :submit, t('add_form'),:class => 'btn-primary' %>
<% end %>
Und in der schaffen Wirkung des Knowledges Controller Ich habe dies:
def create
@knowledge = Knowledge.create(:professor_id => current_professor.id, :subject_id => params[:knowledge][:subject_id])
end
Ich möchte/erwarten ein Active zu bekommen sagen dass dieses Wissen nicht eingefügt werden kann, weil es eine Eindeutigkeitsverletzung gibt, aber nops, ich sehe nur 500 in den Protokollen und ein Rollback, aber es scheint, dass die Ausführung weitergeht. Meine Frage ist also: Was mache ich falsch oder wie könnte ich diese Modellierungssituation verbessern? Ich glaube, das Formular muss mit dem Join-Modell in Beziehung stehen, da ich Felder dieses Modells darauf haben möchte ... Aber vielleicht liege ich falsch, und ich könnte es auf eine einfache/sauberere Weise tun.
EDIT:
Wie in einer der Kommentare gefragt, hier ist das Protokoll der Einreichung des Formulars und der 500-Fehler direkt nach dem Rollback:
Started POST "/professors/1/knowledges" for 127.0.0.1 at 2012-07-01 00:45:39 -0700
Processing by KnowledgesController#create as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"4JVyxWnIh37kyBwLwLGTHk/znsI1c5wrJvaWjKKT5tM=", "Parent Subject"=>"1", "knowledge"=>{"subject_id"=>"1"}, "commit"=>"Añadir", "professor_id"=>"1"}
Professor Load (0.4ms) SELECT `professors`.* FROM `professors` WHERE `professors`.`id` = 1 LIMIT 1
Completed 500 Internal Server Error in 4ms
Ich habe einige Bedingungen in der erstellen Aktion, wie folgt aus:
def create
@knowledge = Knowledge.new(:professor_id => current_professor.id, :subject_id => params[:knowledge][:subject_id])
if @knowledge.save
flash[:notice] = "Success..."
redirect_to professor_path(current_professor)
else
render :action => 'new'
end
end
Und tatsächlich zeigen die s nach rechts nach dem 500:
Completed 500 Internal Server Error in 6ms
ActiveRecord::RecordInvalid (Validation failed: Subject has already been taken):
Ich frage mich, warum die Ausnahme nur statt angehoben wird, um die Fehler in das Objekt hinzufügen und lassen Sie mich diese Situation verwalten. Was sollte die folgende Zeile nicht tun?
Bitte posten Sie die Protokolle, die zu 500 führen. Das wäre hilfreich. – prasvin
Protokolle wurden veröffentlicht :) – Nobita
Ja, die Fehler sollten in das Objekt hinzugefügt worden sein. Ich glaube nicht, dass das den 500 Fehler verursacht. Können Sie die Ausführung vor 'if @ knowledge.save' Zeile in KnowledgesController # create stoppen, mit Debugger oder PRY. Dann versuchen Sie '@ knowledge.save' und' @ knowledge.save! 'Nur um zu bestätigen, dass die Validierungsfehler in' @ knowledge' eingebettet wurden. Sie könnten das sogar von der Konsole aus überprüfen. Auch können Sie bitte einen Kern des gesamten Stack-Trace veröffentlichen. Ich habe das starke Gefühl, dass dies nicht auf die Bestätigung der Einzigartigkeit zurückzuführen ist. – prasvin