ari
ari

Reputation: 331

NHibernate cascade collection delete when insert new item to not empty collection

I have the following Fluent Mappings:

    public ScanDeliverySessionMap()
    {
        Id(x => x.Id);
        ...
        ...
        HasManyToMany(x => x.ToScanForms) <--- IList<Form> ToScanForms --->
            .Table("ToScanForm")
            .ParentKeyColumn("SessionId")
            .ChildKeyColumn("FormId").Cascade.SaveUpdate();
    }

    public FormMap()
    {

        Id(x => x.Id).Column("FormID").GeneratedBy.Foreign("Log");

        ....
        ....

        HasManyToMany(x => x.ScanDeliverySessions)
            .Table("ToScanForm")
            .ParentKeyColumn("FormId")
            .ChildKeyColumn("SessionId").Inverse();
    }

When I try to insert new Form to the ToScanForms collection Everything seemingly works properly but watching on NHProf I see that NH casacde DELETE over all ToScanForms items and then NH INSERT the ToScanForms items including the new item.

Some screenshots: alt text alt text

Upvotes: 3

Views: 554

Answers (1)

Pedro
Pedro

Reputation: 11904

That behaviour occurs because nhibernate doesn't know which entities in the collection are new and which are old, so he must delete everything and then re-insert them.

To prevent this is behaviour is quite simple: change your property to an ICollection and map your HasManyToMany as a set. You mapping would be changed to the following:

public ScanDeliverySessionMap()
{
    Id(x => x.Id);
    ...
    ...
    HasManyToMany(x => x.ToScanForms) //<--- ICollection<Form> ToScanForms --->
        .AsSet()
        .Table("ToScanForm")
        .ParentKeyColumn("SessionId")
        .ChildKeyColumn("FormId").Cascade.SaveUpdate();
}

public FormMap()
{

    Id(x => x.Id).Column("FormID").GeneratedBy.Foreign("Log");

    ....
    ....

    HasManyToMany(x => x.ScanDeliverySessions)
        .AsSet()
        .Table("ToScanForm")
        .ParentKeyColumn("FormId")
        .ChildKeyColumn("SessionId").Inverse();
}

Under the hood nhibernate will use Iesi Collections' HashSet, so now he knows which entities are new and which are old.

Upvotes: 4

Related Questions