NHibernate尝试刷新已经失败的操作 - 如何避免它

时间:2012-07-17 09:46:03

标签: asp.net nhibernate nhibernate-3

在我的Web应用程序中,在请求周期的某个地方,我在存储库上调用以下方法:

     repository.Delete(objectToDelete);   

这是NHibernate实现:

    public void Delete(T entity)
    {
        if (!session.Transaction.IsActive)
        {
            using (ITransaction transaction = session.BeginTransaction())
            {
                session.Delete(entity);
                transaction.Commit();
            }
        }
        else
        {
            session.Delete(entity);
        }
    }

session.Delete(entity)(在using语句中)失败 - 这很好我有一些数据库约束,这就是我的预期。但是,在 Global.asax.cs 中的请求结束时,我使用以下代码关闭会话:

    protected void Application_EndRequest(object sender, EventArgs e)
    {
        ISession session = ManagedWebSessionContext.Unbind(HttpContext.Current, sessionFactory);

        if (session != null)
        {
            if (session.Transaction != null && session.Transaction.IsActive)
            {
                session.Transaction.Rollback();
            }
            else
            {
                session.Flush();
            }
            session.Close();
        }
    }

这是用于删除对象的同一会话。现在,时间:

session.Flush();
调用

,NHibernate尝试执行相同的DELETE操作 - 抛出异常和应用程序崩溃。不完全是我想要的,因为我之前已经处理过异常(在存储库级别)并且我显示了preety UI消息框。

当调用session.Flush时,如何防止NHibernate再次尝试执行DELETE(我猜其他方案中的UPDATE操作)操作。 Basicall我没有设计 Application_EndRequest 所以我不确定这是否是一个很好的方法来刷新一切。

由于

1 个答案:

答案 0 :(得分:1)

NHibernate的刷新模式默认设置为“auto”,这意味着(除其他事项外)提交事务将导致NHibernate刷新并且删除失败。

在请求结束时,您再次手动刷新会话,告诉NHibernate再次执行删除(因为没有活动事务)。

这不符合预期的原因是因为您的期望是错误的。 NHibernate会话是一个工作单元,即您的应用程序在一个请求中执行的所有操作。 交易完全不相关。第一次刷新会话失败的事实也是第二次失败的原因。

如果你想阻止NHibernate第二次执行删除,你不应该只刷一次,只刷一次。通过提交事务或手动完成。

在某种程度上不相关的说明:你使用NHibernate并且交易错误。它会在以后给你带来大量的问题。关于如何在Web应用程序中使用NHibernate,有一些很好的在线资源。