2010-10-04 14 views
11

Sto cercando di capire perché NHibernate gestisce uno a molti cascata (usando cascade = all-delete-orphan) come fa. Ho incontrato lo stesso problema come questo ragazzo:Perché NHibernate non elimina prima gli orfani?

Forcing NHibernate to cascade delete before inserts

Per quanto posso dire NHibernate esegue sempre inserti prima, poi gli aggiornamenti, poi cancella. Ci può essere una buona ragione per questo, ma non posso per la vita di me capire quale sia questa ragione. Spero che una migliore comprensione di questo mi aiuterà a trovare una soluzione che non odio :)

Ci sono buone teorie su questo comportamento? In quale scenario la cancellazione degli orfani non funzionerebbe? Tutti gli ORM funzionano in questo modo?

+1

Voglio solo aggiungere la mia frustrazione a questa domanda. NHibernate è un fallimento assoluto in questo caso. Ho combattuto tutto il giorno con questo stupido problema. Anche gli ORM più elementari gestiscono molto più elegantemente l'NHibernate. Ho finito per dover codificare completamente questo.Entrambi dovremmo aver perso qualcosa. – JasonCoder

risposta

2

MODIFICA: Dopo aver detto che non c'è motivo, ecco un motivo. Diciamo che avere il seguente scenario:

public class Dog { 
    public DogLeg StrongestLeg {get;set;} 
    public IList<DogLeg> Legs {get;set; 
} 

Se si dovesse eliminare prima, e permette di dire si eliminano tutti Dog.Legs, allora si può eliminare lo StrongestLeg che causerebbe una violazione di riferimento. Quindi non puoi CANCELLARE prima di AGGIORNARE.

Diciamo che aggiungi una nuova gamba e che la nuova gamba è anche la StrongestLeg. Quindi devi INSERIRE prima di AGGIORNARE in modo che la Leg abbia un ID che può essere inserito in Dog.StrongestLegId.

Quindi è necessario INSERIRE, AGGIORNARE, quindi ELIMINARE.

Anche come ibernato è basato su Hibernate, ho dato un'occhiata a Hibernate e ho trovato diverse persone che parlano dello stesso problema.

E qui è la migliore risposta da loro:

Gail Badner ha aggiunto un commento - 21/feb/08 14.30: Il problema sorge quando una nuova entità di associazione con un ID generato viene aggiunta alla raccolta. Il primo passaggio , quando si unisce un'entità contenente questa raccolta, è cascade salvare la nuova associazione entità. La cascata deve verificarsi prima delle altre modifiche alla raccolta. Poiché la chiave univoca per questa nuova entità di associazione è la stessa di un'entità che è già persistente, a ConstraintViolationException è generata. Questo è un comportamento previsto.

+0

Non è solo questo. Fondamentalmente qualsiasi entità a cui si fa riferimento non può essere cancellata fino a quando non viene deferenziata. Qualsiasi entità che faccia riferimento a un'altra non può essere aggiornata fino a quando l'altra non viene inserita. – Iain

+0

Alcuni RDBMS consentono di rinviare il controllo dei vincoli fino alla fine della transazione, quindi non è una domanda non ragionevole e uno scenario molto valido e comune. Ulteriori informazioni http://stackoverflow.com/questions/1330020/is-it-possibile-per-defer-referenziale-integrity-checks-until-the-end-of-a-transact – ironstone13

Problemi correlati