"deleted object would be re-saved by cascade (remove deleted object from associations)[DelftTools.Hydro.HydroNode#2]"

Recently a lot of NHibernate errors have come up. A very common cause is the cascade rules in the mapping as they require close attention. An example of a 'wrong' mapping was the mapping of composite branch structures (CS) (the mapping is shown below). The CS has a list of child structures and these were persisted using a cascade='all'. The same structures were also in the list of branchfeatures on the branch and these were mapped using cascade=all-delete-orphan. So the same weir was saved via branch and via the composite structure. This is fine as long as the cascade don't conflict.

Sometimes a conflict occurs when one cascade results in a delete and another in a save. For example a compositie structure is deleted and the cascade deletes all child-structures. But one of these structures is still in the branchfeatures collection of a branch. The branch cascade insists on the object being saved (or at least not deleted) and the CS cascade wants to delete. Hence a conflict. This can be fixed by removing the structure from both lists or downgrading/removing one of the cascades. In this case the branch should be responsible for saving the features and the CS should have a list of child structures without cascades.

A quick recap of the different cascades :

  • none - do not do any cascades, let the users handles them by themselves.
  • save-update - when the object is saved/updated, check the associations and save/update any object that require it (including save/update the associations in many-to-many scenario).
  • delete - when the object is deleted, delete all the objects in the association.
  • delete-orphan - when the object is deleted, delete all the objects in the association. In addition to that, when an object is removed from the association and not associated with another object (orphaned), also delete it. Orphan only checks one relation
  • all - when an object is save/update/delete, check the associations and save/update/delete all the objects found.
  • all-delete-orphan - when an object is save/update/delete, check the associations and save/update/delete all the objects found. In additional to that, when an object is removed from the association. (orphaned) delete it. So 're-parenting' (changing parent) is a problem.

A note about orphan cascade:
Orphan only looks at one instance at a time. So a composite structure might have a list of child structures. When a child structure is removed from the CS it is considered an orphan. NHibernate does not care about other relation the structure might have (for example with branch or a new CS)

About reparenting : http://fabiomaulo.blogspot.com/2009/09/nhibernate-tree-re-parenting.html