2015-05-05 7 views
5

Ich habe zwei Tabelle, TabelleA und TabelleB.konnte Sammlung nicht löschen: [NHibernate.Exceptions.GenericADOException]

tableA Spalte: tabAId, col2, col3 (tabAId primaryKey und Identitätsspalte.)

tableB Spalte: tabAId, Name (tabAId ist nicht null)

Ich habe Bag erstellen in hbm-Datei von tableA, um die Beziehung zu erhalten.

<bag name="tableB" lazy="true" inverse="false" 
        batch-size="25" cascade="all-delete-orphan"> 
    <key column="tabAId" /> 
    <one-to-many class="tableB" /> 
</bag> 

Wenn ich versuche, Rekord es Exception werfen, wo, wie ich habe Liste der Kinder in tableA Instanz zu aktualisieren in tableA.

[NHibernate.Exceptions.GenericADOException] = { "konnte nicht Sammlung löschen: [MIHR.Entities.tableA.tableB # 21] [SQL: UPDATE dbo.tableB SET tabAId = null WHERE tabAId = @ p0]" }

Innerexception = { „Kann nicht den Wert NULL in Spalte einfügen‚tabAId‘Tabelle‚SA_MIHR_DEV.dbo.tableB‘;... Spalte nicht NULL-Werte erlaubt UPDATE nicht \ r \ nDie Anweisung wurde beendet“ }

Antwort

8

Es gibt nur zwei Möglichkeiten, wie Sie das lösen können.

1) nicht verwenden inverse="false"

<bag name="tableB" lazy="true" inverse="true" // instead of false 
        batch-size="25" cascade="all-delete-orphan"> 
    <key column="tabAId" /> 
    <one-to-many class="tableB" /> 
</bag> 

Diese Einstellung (inverse = "true") wird NHibernate anweisen, direkt einen Artikel aus DB zu löschen.

Während inverse="false" verwendet, wird in der Regel immer führen zu:

  • UPDATE (mit null) == Akt aus der Sammlung zu entfernen
  • DELETE Artikel == Akt der Kaskade

2) machen die Referenzspalte nullable

das bedeutet, dass wir NHibernate UPDATE tun lassen können und löschen. Weil die Spalte jetzt nullfähig ist.

Dies sind nur zwei Wege, wie Sie es hier lösen können.

Meine Präferenz wäre: inverse = "true"

arbeiten richtig mit inverse="true" wir beiden Seiten der Beziehung in C# immer zuordnen.Dies ist ein Muss für Add(), INSERT-Operation:

Parent parent = new Parent(); 
Child child = new Child 
{ 
    ... 
    Parent = parent, 
}; 
// unless initialized in the Parent type, we can do it here 
parent.Children = parent.Children ?? new List<Child>(); 
parent.Children.Add(child); 

// now just parent could be saved 
// and NHibernate will do all the cascade as expected 
// and because of inverse mapping - the most effective way 
session.Save(parent); 

Wie wir sehen können, wir zugewiesen haben - explizit - beide Seiten der Beziehung. Dies muss von der inversen Zuordnung von NHibernate profitieren. Und es ist auch eine gute Übung, denn später, wenn wir Daten von DB laden, erwarten wir, dass NHibernate das für uns einstellen wird

+1

Wenn ich Inverse = "true" setze, dann wird es neu erzeugte Identity Spalte Wert nicht einfügen in die untergeordnete Tabelle einfügen, während ein neuer Datensatz in die übergeordnete Tabelle eingefügt wird. –

+0

Kohler: Bitte sagen Sie mir wie ich vorgehen soll, wenn ich 'inversr =" true "' setze. –

+0

Jetzt sollten Sie das sehen ... Ich habe meine Antwort aktualisiert. Natürlich muss Ihre untergeordnete Entität einen Verweis auf Parent haben. Überprüfen Sie diese http://stackoverflow.com/a/30005490/1679310 für alle DETAILS –

Verwandte Themen