在 NHibernate 中克隆实体

本文关键字:实体 NHibernate | 更新日期: 2023-09-27 18:36:56

我想将单个对象保存到数据库中两次。我有这个代码:

using (var ss = NHibHelp.OpenSession())
using (var tt = ss.BeginTransaction())
{
    var entity = new Entity();
    ss.Save(entity);
    ss.Save(entity);
    tt.Commit();
}

但这会导致只向数据库添加一行。如何将单个对象插入数据库两次(使用两个不同的 ID)?

在 NHibernate 中克隆实体

你不应该这样做 - NHibernate在其会话中维护"对象标识",因此它不会区分.。井。。同一对象。 我真的建议不要这样做,更好的解决方案是查看克隆对象的方法(通过反射或克隆方法),然后保存克隆的对象。

如果您想忽略我上面的建议,您可以通过从会话中逐出实体,将其 id 设置回未保存的值(取决于您的映射,但可能是 0),然后再次保存它来让它工作。

如果您刚刚调用会话,它也可能有效。合并(实体)两次(您可能需要在第一次调用后将 id 重置为其未保存的值)。

或者,您可以将无状态会话与会话一起使用。Merge(),然后你不必在 Save 之间逐出实体。

您可以通过两种方式执行此操作:

  1. 克隆实体,应该是深层副本。

    using (var ss = NHibHelp.OpenSession())
    using (var tt = ss.BeginTransaction())
    {
      var entity = new Entity();
      var clonedEntity = entity.Clone();
      ss.Save(entity);
      ss.Save(clonedEntity);
      tt.Commit();
    }
    

如果分配了您的 ID,请记住创建一个新 ID。 深拷贝在复杂实体方面存在一些问题,如果您有反转集合,则需要重新引用它们。

2.在新会话中打开第二个事务并提交它。

var entity = new Entity();
using (var ss = NHibHelp.OpenSession())
using (var tt = ss.BeginTransaction())
{      
     ss.Save(entity);
     tt.Commit();
}
using (var ss = NHibHelp.OpenSession())
using (var tt = ss.BeginTransaction())
{      
     ss.Save(entity);
     tt.Commit();
}