使用子集合更新NHibernate对象

时间:2018-10-17 15:44:04

标签: c# nhibernate fluent-nhibernate nhibernate-mapping

我正在尝试使用在休眠会话中找到的.Update()方法使用子集合更新nHibernate对象。在当前设置下,我唯一能做的就是添加子代,我无法对其进行修改或删除。

为清楚起见,对象及其映射如下:

public class Parent {
   public virtual int Id { get; set; }
   public virtual string Name { get; set; }
   public virtual ISet<Child> Children { get; set; } = new HashSet<Child>();
}

public class ParentMap: ClassMap<Parent>
{
   public ParentMap()
   {
     Id(x => x.Id);
     Map(x => x.Name);
     HasMany(x => x.Children)
       .AsSet()
       .Inverse()
       .Cascade.AllDeleteOrphan();
   }
}

public class Child {
   public virtual int Id { get; set; }
   public virtual string Name { get; set; }
   public virtual Parent Parent { get; set; }
}

public class ChildMap: ClassMap<Child>
{
   public ChildMap()
   {
       Id(x => x.Id);
       Map(x => x.Name);
       References(x => x.Parent);        
   }
}

当我从UI层获得更改并尝试使用以下方法更新已经存在的对象时:

using (var tx = _session.BeginTransaction())
     _session.Update(newParent);
     tx.Commit();
}

在这里,newParent是一个临时对象(从较早的会话中从数据库中获取并显示在UI中),包含与我要更新的对象相同的标识符,但对子集合进行了更改。以某种方式使用这种方法,我只能添加子代,而不能修改或删除它们。

我的错误在哪里?

1 个答案:

答案 0 :(得分:2)

您最有可能发生的事情是,您无需修改​​NHibernate在您的父实体中实例化的集合,而是将它们全部替换为HashSet的新实例。

当您从NHibernate保存或获取实体时,您的孩子ISet会加载PersistentGenericSet(实现ISet)的实例,该实例负责帮助完成此更改跟踪您的收藏。

简而言之,不要分配给Children属性。实际上,将设置器设为protected。 只需Add()Remove()Clear()即可。