PostgreSQL
 sql >> Datenbank >  >> RDS >> PostgreSQL

PG::ForeignKeyViolation:FEHLER:Aktualisieren oder Löschen von Tabelle xxx verletzt die Fremdschlüsselbeschränkung

Aus dem feines Handbuch :

Also :delete_all kümmert sich zwar um Fremdschlüssel, aber da keine Rückrufe aufgerufen werden, geht es nur eine Ebene tief. Also das in Company :

has_many :projects, dependent: :delete_all

bedeutet, dass #destroy aufgerufen wird auf ein Unternehmen werden die zugehörigen projects direkt gelöscht aus der Datenbank. Aber das wird das nicht sehen:

has_many :tasks, dependent: :delete_all

die Sie in Project haben und Sie versuchen schließlich, Projekte zu löschen, auf die noch in tasks verwiesen wird wie die Fehlermeldung anzeigt.

Sie könnten alle Ihre Assoziationen auf dependent: :destroy umstellen , wird dies alles aus der Datenbank ziehen, bevor sie zerstört werden, und Rückrufe werden aufgerufen (die mehr Dinge aus der Datenbank laden, nur um sie zu zerstören, wodurch mehr Dinge aus der Datenbank geladen werden ...). Das Endergebnis wird eine Menge Datenbankaktivität sein, aber alle Fremdschlüssel werden korrekt befolgt.

Alternativ können Sie die Logik dort in die Datenbank einfügen, wo sie normalerweise hingehört, indem Sie on delete cascade auf die Fremdschlüsseleinschränkungen :

Ihr add_foreign_key Anrufe würden wie folgt aussehen:

add_foreign_key "projects", "companies", on_delete: :cascade
add_foreign_key "tasks", "projects", on_delete: :cascade
add_foreign_key "task_times", "tasks", on_delete: :cascade

in diesem Fall. Wahrscheinlich möchten Sie dependent: :delete_all belassen s in Ihren Modellen als Erinnerung daran, was los ist, oder Sie können selbst einen Kommentar hinterlassen.