简体   繁体   中英

Rails cannot delete or update a parent row: a foreign key constraint fails

I want to delete something from my database. The value references some other tables.

Error is:

Mysql2::Error: Cannot delete or update a parent row: a foreign key constraint fails

How can I resolve this properly?

If I add some constraints like on delete cascade the other values won't be deleted right?

Edit:

def delete
   @vid = Movie.find params[:id]
   @vid.delete
   redirect_to :action => :add
end

Update Models

movie.rb

class Movie < ActiveRecord::Base
  has_many :comments, :dependent => :destroy
  has_many :ratings
  belongs_to :channel
  has_and_belongs_to_many :tags
  has_and_belongs_to_many :categories
  mount_uploader :video, MovieUploader

comment.rb

class Comment < ActiveRecord::Base
  belongs_to :movie
  belongs_to :user
  belongs_to :rating

If you've created the foreign keys using ActiveRecord::Migration , it'll use ON DELETE RESTRICT by default (ie, the opposite of what you want: row entry will be NOT deleted if there are entries with references from other tables).

You need to change your migration to use ON DELETE CASCADE :

class CreateChild < ActiveRecord::Migration
  def change
    create_table :child do |t|
      t.references :parent, foreign_key: {on_delete: :cascade}
    end
  end
end

Make sure your parent Model.rb has

has_many :model, :dependent => :delete_all 

this makes sure all your data gets deleted once you delete a parent Model.

Like for instance you have Post.rb and Comment.rb

Post.rb

has_many :Comments, :dependent => :delete_all

So, When you delete a Post, all corresponding Comments will be deleted as well.

Hope it helped

Cheers

You are using delete , from the documentation :

To enforce the object's before_destroy and after_destroy callbacks or any :dependent association options, use #destroy.

So you need to use destroy instead so that the proper callback from rails to remove dependent records is executed:

def delete
   @vid = Movie.find params[:id]
   @vid.destroy
   redirect_to :action => :add
end

Because your Comment records depend on the Movie record that you are trying to delete, hence, since rails is just trying to remove the movie before the comments the database engine complains if there is a foreign key from the comment table to the movie table.

Error: Mysql2::Error: Cannot delete or update a parent row: a foreign key constraint fails

Solution:

I think you have used .delete or delete_all,

Instead of .delete or delete_all use .destroy

.destroy will delete all associated values with that model

Could you post the applicable database schema?

If you set up a delete cascade constraint, then the other values will be deleted. If this isn't the desired outcome, then you might need to rethink the referential integrity of the database.

Perhaps, instead you might want to consider using the ActsAsParanoid gem to soft delete the elements instead?

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM