Posted by
最近在ptt的Ruby板,有板友在討論刪除資料時如何進行驗證,原po的問題大致上是說倘若某一筆資料跟其他的資料有所關聯,該如何顯示錯誤訊息給使用者、告知因為有資料的關聯參照存在所以無法刪除。
看到這個問題,我心中第一個想到的是「就用CASCADE的方式把資料一口氣刪光啊!」XD不過隨即想想,大多數的資料可不是說想刪就能隨便刪的,例如在Ruby板上的討論串就有人提到要刪除某個分類名稱,但在刪除前要先將該分類底下的文章都指定為未分類。
總之,好奇心驅使之下,我猜想ActiveRecord裡面一定有針對關聯性特別設計一套機制來處理,果不其然其實在has_one, has_many底下就有:dependent來處理互相參照的資料。
:dependent有三個選項:(在此假設User has_many Posts, Post has_many Comments)
class User < ActiveRecord::Base has_many :posts, :dependent => :destroy end
至於要在物件刪除之前,若要做驗證動作,就如同ptt Ruby的板主godfat分享的一樣,使用"before_destroy"可以在呼叫destroy之前先做其他動作。例如在這個網頁裡面看到的sample code(before_destroy是寫在Model裡,destroy的動作則是由controller中的action來呼叫):
class Group < ActiveRecord::Base acts_as_treerder => "name" has_and_belongs_to_many => :users before_destroy :validates_no_dependents def validates_no_dependents if children.size > 0 || users.size > 0 errors.add :base, "Cannot delete this group, as it has sub-groups and/or users" end end end