Entfernen Sie ein Objekt aus der Sammlung mit Entity Framework

7

Ich benutze DDD. Ich habe eine Klasse Product, die eine aggregierte Wurzel ist.

%Vor%

Die Ebene, die die Modelle enthält, kennt EF überhaupt nicht. Das Problem ist, dass wenn ich DeleteComment(comment) aufruft, EF die Ausnahme

auslöst

Eine Beziehung aus dem AssociationSet 'Product_Comments' befindet sich im Status 'Gelöscht'. Bei Multiplizität-Constraints muss ein entsprechendes "Product_Comments_Target" ebenfalls im Status "Gelöscht" sein.

Auch wenn das Element aus der Sammlung entfernt wird, löscht EF es nicht. Was sollte ich tun, um dies zu beheben, ohne DDD zu brechen? (Ich denke darüber nach, ein Repository für Kommentare zu erstellen, hat aber nicht Recht)

Codebeispiel:

Da ich versuche, DDD zu verwenden, ist Product ein aggregierter Root und hat ein Repository IProductRepository . Ein Kommentar kann ohne ein Produkt nicht existieren, ist also ein Kind von Product Aggregate und Product ist verantwortlich für das Erstellen und Löschen von Kommentaren. Comment hat kein Repository.

%Vor%     
Catalin 20.11.2012, 12:45
quelle

5 Antworten

11

Ich habe viele Leute gesehen, die dieses Problem gemeldet haben. Es ist eigentlich ziemlich einfach zu beheben, aber ich denke, es gibt nicht genug Dokumentation darüber, wie EF in dieser Situation sich verhalten soll.

Trick: Wenn Sie die Beziehung zwischen Eltern und Kind einrichten, müssen Sie eine "zusammengesetzte" Taste auf dem Kind erstellen. Auf diese Weise werden die zugehörigen Datensätze tatsächlich aus der Datenbank gelöscht, wenn Sie dem übergeordneten Objekt mitteilen, dass es einen oder alle untergeordneten Elemente löschen soll.

So konfigurieren Sie den zusammengesetzten Schlüssel mithilfe der Fluent-API:

%Vor%

Dann, um die verwandten Kinder zu löschen:

%Vor%

Fertig!

    
Mosh 09.07.2014 04:19
quelle
6

Hier ist ein Paar verwandter Lösungen:

Löschen von abhängigen Entitäten beim Entfernen aus der EF-Sammlung

    
Euphoric 21.11.2012 09:07
quelle
2

Ich habe 3 Ansätze zur Umgehung dieses Mangels in EF gesehen:

  1. Konfigurieren Sie einen zusammengesetzten Schlüssel (gemäß Moshs Antwort)
  2. Heben Sie ein Domain-Event an und weisen Sie EF an, die Child-Deletionen in seinem Handler auszuführen (gemäß dieser Antwort)
  3. Überschreibe DbContext 's SaveChanges() und handle mit der Löschung dort (laut Euphoric's Antwort)

Ich mag Option 3 am besten, da sie keine Änderung an Ihrer Datenbankstruktur (1) oder an Ihrem Domänenmodell (2) erfordert, sondern die Problemumgehung in der Komponente (EF), die den Mangel an erster Stelle hatte.

Dies ist also eine aktualisierte Lösung aus Euphoric's Antwort / Blogpost:

%Vor%

Hinweis: Dies setzt voraus, dass ParentProduct die Navigationseigenschaft in Comment zurück zu ihrer besitzenden Product ist.

    
BCA 30.11.2016 14:35
quelle
1

Das Löschen des Kommentars vom Produkt mit Ihrem Ansatz löscht nur die Verknüpfung zwischen Produkt und Kommentar. Damit der Kommentar noch existiert.

Sie müssen dem ObjectContext mitteilen, dass der Kommentar auch mit der Methode DeleteObject() gelöscht wird.

Wie ich es tue, verwende ich die Update-Methode meines Repositorys (weiß Entity Framework), um nach gelöschten Assoziationen zu suchen und auch die veralteten Entitäten zu löschen. Sie können dies tun, indem Sie den ObjectStateManager des ObjectContext verwenden.

%Vor%

Beispiel:

%Vor%     
Jehof 21.11.2012 07:20
quelle
0

Ich habe dasselbe Problem gelöst, indem ich ein Elternattribut für meine Modelle erstellt und das Attribut in der SaveChanges-Funktion überprüft habe. Ich habe dazu einen Blog geschrieben: Ссылка

    
Wim 21.11.2012 10:01
quelle