/// <summary> /// Given a collection type, determine the Type representing elements /// within instances of that collection. /// </summary> /// <param name="collectionType">The collection type to be checked.</param> /// <returns>The Type of the elements of the collection.</returns> private IType GetElementType(CollectionType collectionType) { return collectionType.GetElementType(_sfi); }
/// <summary> Cascade to the collection elements</summary> private void CascadeCollectionElements(object child, CollectionType collectionType, CascadeStyle style, IType elemType, object anything, bool isCascadeDeleteEnabled) { // we can't cascade to non-embedded elements bool embeddedElements = eventSource.EntityMode != EntityMode.Xml || ((EntityType) collectionType.GetElementType(eventSource.Factory)).IsEmbeddedInXML; bool reallyDoCascade = style.ReallyDoCascade(action) && embeddedElements && child != CollectionType.UnfetchedCollection; if (reallyDoCascade) { log.Info("cascade " + action + " for collection: " + collectionType.Role); foreach (object o in action.GetCascadableChildrenIterator(eventSource, collectionType, child)) CascadeProperty(o, elemType, style, anything, isCascadeDeleteEnabled); log.Info("done cascade " + action + " for collection: " + collectionType.Role); } var childAsPersColl = child as IPersistentCollection; bool deleteOrphans = style.HasOrphanDelete && action.DeleteOrphans && elemType.IsEntityType && childAsPersColl != null; //a newly instantiated collection can't have orphans if (deleteOrphans) { // handle orphaned entities!! log.Info("deleting orphans for collection: " + collectionType.Role); // we can do the cast since orphan-delete does not apply to: // 1. newly instantiated collections // 2. arrays (we can't track orphans for detached arrays) string entityName = collectionType.GetAssociatedEntityName(eventSource.Factory); DeleteOrphans(entityName, childAsPersColl); log.Info("done deleting orphans for collection: " + collectionType.Role); } }