0

書き込み可能なすべてのActiveRecordアソシエーションメソッドの動作をオーバーライドする方法はありますか?たとえば、次のような「リクエスト」というモデルがあります。

class Request < ActiveRecord::Base
   has_many :line_items
end

リクエストモデルには、「ステータス」と呼ばれるフィールドがあります。ステータスが「DRAFT」でない場合、line_itemsリレーションの書き込み可能なすべてのActiveRecordアソシエーションメソッドで例外をスローする必要があります。次のように、個別にオーバーライドできることを知っています。

class Request < ActiveRecord::Base
   has_many :line_items

   def line_items=(args)
      if status != 'DRAFT'
         raise Exception.new "cannot edit a non-draft request"
      else
         write_attribute :line_items, args
      end
   end
end

ただし、ActiveRecordがこれらの関連付けのために作成するメソッドはたくさんあります(http://api.rubyonrails.org/classes/ActiveRecord/Associations/ClassMethods.htmlの「自動生成されたメソッド」を参照)。

助けてくれてありがとう。

4

1 に答える 1

1

一部のオブジェクトが Rails コードで受け入れられない場合、最初にそのオブジェクト クラス自体を確認し、他の関連するクラスは確認しません。実際に追跡しない限り、line_items のこれらのルールは実際にはリクエスト モデルでコード化されています。LineItem は、オブジェクトが拒否された理由を知ることよりも、Request を知ることをお勧めします。

次に、すべてのリクエストの関連付けが同じルールに従うことを絶対に望んでいない場合があります。

そこで、私はこれを提案します。

class LineItem < ActiveRecord::Base
  belongs_to :request
  before_save :raise_if_draft_request
  def raise_if_draft_request
    raise Exception.new "cannot edit a non-draft request" if self.request.status=='DRAFT'
  end
end
于 2012-06-03T05:39:45.463 に答える