この記事で説明したいこと
before_destoryのprependオプションについて
背景
has_many :hogehoges, dependent: destroyとなっているhogehogesがある。
このとき、親のレコードの削除に伴い、紐づくhogehogesがdestroyされる前に行いたい処理があった。
例えば、
class Like < ApplicationRecord
module Likable
extend ActiveSupport::Concern
included do
has_many :likes, dependent: :destroy
end
end
end
class Article < ApplicationRecord
include Like::Likable
before_destroy :logging_final_likes
def logging_final_likes
puts likes.size
end
end
想定としては、logging_final_likesを実行したあとに、likesがdestroyされてほしかった。
しかし、これを実行してみると、logging_final_likesは0になり、destroy前に実行されていないことが分かった。
以下のドキュメントによると、before_destroyよりも先にdestroyが実行されているらしい。(ただし、transactionは同じ)
これを回避するには、prepend: trueオプションがあり、これをbefore_destoryにつけると動きました。
class Article < ApplicationRecord
include Like::Likable
- before_destroy :logging_final_likes
+ before_destroy :logging_final_likes, prepend: true
def logging_final_likes
puts likes.size
end
end