3

Ruby ORM、ActiveRecordで長年働いていたEF Code Firstにまだ慣れてきました。 ActiveRecordは以前はbefore_validationやbefore_saveのような種類のcallbacksを持っていましたが、オブジェクトをデータレイヤーに送る前にオブジェクトを変更することができました。私はEFコードの最初のオブジェクトモデリングに相当するテクニックがあるのだろうかと思います。EFコードファーストモデルによる保存または検証前のロジックの実行

インスタンス化時に(もちろんデフォルト値などを設定するために)オブジェクトメンバーを設定する方法はわかっていますが、オブジェクトライフサイクルのさまざまな瞬間に介入する必要があることもあります。

が若干不自然な例を使用するために、私は著者とを連結する結合テーブルを持っていると言う演劇、対応するオーサリングオブジェクトで表される:位置に関連する著者のゼロインデックス付きの順序を表す

public class Authoring 
{ 
    public int ID { get; set; } 

    [Required] 
    public int Position { get; set; } 

    [Required] 
    public virtual Play Play { get; set; } 

    [Required] 
    public virtual Author Author { get; set; } 
} 

Playを指定します。 (位置が0の "Rodgers"作者と位置1の "Hammerstein"作者の2人の作者による単一の "南太平洋"プレイがあるかもしれません)。

私は、オーサリングレコードを保存する前に、関連するプレイの既存の作者が存在するかどうかを確認しました。いいえの場合、Positionを0に設定します。はいの場合、Playに関連付けられた最高値の位置を設定し、1だけインクリメントします。

私はこのようなロジックをEFコードの最初のモデルレイヤー内に実装しますか?また、検証エラーがチェックされる前にコード内のデータをマッサージしたい場合、どうすればよいでしょうか?

基本的に、私は上記のRailsライフサイクルフックと同等のものを探していますが、少なくともそれを偽造する方法もあります。 :)

答えて

3

(ボックスのうちは何もありません) base.SaveChanges()を呼び出します。そうした場合、修正を行う前にDetectChangesを呼び出すことができます。 Btw。同様の問題については、「Programming Entity Framework DbContext」(ISBN 978-1-449-31296-1)の192-194ページを参照してください。そして、はい、これはバリデーションの文脈の中にあります...

3

IValidatableObjectを実装できます。これにより、単一のフックが得られます。

IEnumerable<ValidationResult> Validate(ValidationContext validationContext) 

そして、そこで検証ロジックを適用することができます。

ObjectContextSavingChangesイベントがあります(DbContextから入手できます)。

あなただけのカスタムIDoStuffOnSaveインターフェイスを作成して保存に関するいくつかのロジックを実行する必要があり、あなたの事業体に適用できますが、DbContext.SaveChangesを上書きアップが修正を行うことができます

+3

私はいくつかの理由でバリデーションからエンティティを変更するのをやめます:1)保存されない前に変更された状態にない関連するエンティティを変更した場合検証後にDetectChangesが再度呼び出されないため、2)無効にするようにすでに検証されている関連エンティティを変更した場合、データベースに保存する際に例外が発生することがあります3)これは単一責任の原則。 SavingChangesイベントの場合、これは検証が行われた後で、足で自分を撃つことができます。 – Pawel

関連する問題