回滚后的NHibernate 3会话状态()

时间:2010-12-06 16:11:36

标签: nhibernate session transactions rollback

我有一个问题。

using (var tran = repository.Session.BeginTransaction())
{
    try
    {
        repository.Save(entity);
        tran.Comit();
    }
    catch(Exception)
    {
        tran.Rollback();
        throw;
    }    
}

using (var tran = repository.Session.BeginTransaction())
{
    try
    {
        repository.GetById(id);
        tran.Comit();
    }
    catch(Exception)
    {
        tran.Rollback();
        throw;
    }    
}

当我尝试在第一个tran.rollback()块中的异常和using之后通过ID获取实体时,我得到更新异常。所以NHibernate试图从第二个using块中的第一个using块更新实体。

为什么呢?我做了tran.Rollback()。我也必须Session.Clear()吗?

1 个答案:

答案 0 :(得分:15)

根据Hibernate的API,当Hibernate Session抛出异常时,你必须关闭Session并创建一个新的Session。此外,当您回滚Hibernate事务时,您不能在以后提交它或刷新会话 - 您必须在新会话中重新开始。

特别是(这是一个实现细节,所以不要依赖它),在回滚之后,Hibernate Session仍然有自事务开始以来创建/修改的实体 - Hibernate不通过你的实体并且还原所有你做出的改变因此,如果您回滚事务然后刷新会话, Hibernate将提交您认为已回滚的实体更改。如果你想通过试图破解这种行为(例如清除会话)来玩火,请注意。最好重新开始一个新的会议。