1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

Rails paranoia dependent 親レコード消す際 子レコードが論理削除されている場合対応

Posted at

親レコード消す際 子レコードが論理削除されているたらdependent: :destoryがうまく動かんかった

最終的な対応

親レコード削除前に子レコードを削除するというパワープレイになりました。
いい方法があれば

class EntryLimit < ApplicationRecord
  has_many :entry_lists, dependent: :delete_all
  before_destroy :entry_lists_depend_paranoia


  def entry_lists_depend_paranoia
    entry_lists.with_deleted.map(&:really_destroy!)
  end

構成

親モデル

class EntryLimit < ApplicationRecord
  has_many :entry_lists, dependent: :destroy

子モデル

class EntryList < ApplicationRecord
  acts_as_paranoid

  belongs_to :entry_limit

削除しようとした時エラーが発生

entrylimit=EntryLimit
entrylimit.destroy
=>ActiveRecord::InvalidForeignKey: Mysql2::Error: Cannot delete or update a parent row: a foreign key constraint fails

対応1 dependentをdestroyからdelete_allにしてみよう

has_many :entry_lists, dependent: :delete_all

結論だめでした。

対応2 before_destroyで消す前に論理削除されたレコードを物理削除かましてみよう

class EntryLimit < ApplicationRecord
  has_many :entry_lists, dependent: :delete_all
  before_destroy :entry_lists_depend_paranoia

  def entry_lists_depend_paranoia
    entry_lists.with_deleted.map(&:really_destroy!)
  end

結果消せました

 entrylimit.destroy

 (2.2ms)  BEGIN
 EntryList Destroy (1.1ms)  DELETE FROM `entry_lists` WHERE `entry_lists`.`id` = 30
 EntryLimit Destroy (1.2ms)  DELETE FROM `entry_limits` WHERE `entry_limits`.`id` = 6
 (1.9ms)  COMMIT

まとめ

今回はパワープレイで行きました
もっといい感じに消す方法があったら教えてほしいです。

dependentで削除する場合 paranoiaの影響で通常デリートが動くが
論理削除になってしまう しかし親は消えるので関連キーがないよエラーがでてると認識してます。

ただparanoia使っていても
論理削除されたレコードが一件もないと特に問題なく削除はうごきました🤔

1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?