2012-03-12 11 views
3

私はこの問題を多く見ましたが、解決策のどれも私のために働いていません。流暢NHibernate 1対多カスケード削除

私は流暢なNHibernateでMS SQLにマップされたC#で1対多の関係を持っています。私が子要素を削除しようとすると、NHibernateは外部キーをNULLに設定することによってそうすることを試みますが、これはもちろんエラーをスローします。

同様の質問に対する解決策は、Inverseを親のマッピングHasManyに追加することでした。しかし、今この問題があります:

var parent = //something 
parent.Children.Clear(); 
session.Update(parent); 

これは、親全体が削除されます!どうして?

答えて

11

マッピングで「逆」を使用すると、親と子の関係を「所有する」という概念が逆転します。 「逆」を指定することによって、NHは基本的に、関係の子側が親を所有するかどうかを決定する親の代わりに親に属するかどうかを決定するかのように動作します。実際の良い例は、学生が大学に入学することです。学生は、もはや大学に所属しないことを選択することができ、依然として存在し、実体として意味があります。これは、大学とのこの関係を結成するかどうかを決定する主要な決定者である学生でもなく、学生でもあります(実生活では、学生がもはや歓迎されないと言う状況があります。大学は単に良い立場の学生に「あなたが脱落している」と言うだけではなく、大学にそれを伝える学生です)。

ParentとChildrenの関係をInverseとして指定すると、NHはリレーションシップのコンテキスト外に存在できない側としてリレーションシップの「一方」側(Parent)を扱うことになります。だから、あなたがすべての子どもたちをクリアすると、子どもがいない親は「孤児」になり、NHはそれを削除します。

これはあなたの望むようには聞こえません。だから、この関係からInverseマッピングを削除して、親が子とのこの関係を「所有」できるようにします。すべての子を削除すると、それらは孤立し削除されますが、親はまだ周囲にあります。今では、外部キーがNULL可能でないため、子が「孤立している」ことができないという問題があります。彼らは何かに属していなければなりません。 NHは、「オーファン削除」カスケーディングルールを使用する場合は、子レコードのFKをNULLにする必要があります。これは、孤立ファイルの削除は、FKフィールドをnullに設定することによって、レコードが最初に孤立している必要がある2パス操作であるためです。 NHは、テーブルからNULL FKのレコードを削除するために2番目のステートメントを実行します。したがって、NULL可能なFKフィールドでも、NHを目的のカスケード規則で使用すると、一時的な期間以上の間、NULL FKのレコードは作成されません。

これが受け入れがたい場合は、カスケードルールからオーファンの削除を削除し、手動で各レコードを削除し、セッションから削除する必要があります。

foreach(var child in parent.Children) 
     session.Delete(child); 

    parent.Children.Clear(); 
    session.Update(parent); 
+1

これをありがとう - あなたのフィードバックでは、この情報は私の問題を解決 - 孤児削除「は、使用するつもりならNHがNULL可能であることを子レコードのFKが必要です 『』カスケーディング規則を。」 –

+0

(さらに上)...私の子供のテーブルの私のFKがNOT NULLに設定されていて、あなたがNHが2子を削除する-pass:子をNULLに設定し、次にFK = nullを削除します。 –