使用多个NHibernate监听器来更新数据库

本文关键字:更新 数据库 监听器 NHibernate | 更新日期: 2023-09-27 18:17:00

我使用NHibernate 2.1 in,并有一些实现IPreInsertEventListener, IPreUpdateEventListener, IPreDeleteEventListener的监听器。

两个侦听器执行最后一分钟的数据库操作。两者都是审计相关的,但执行非常不同的审计操作,因此是单独的侦听器——一个侦听器审计所有内容并写入审计表,另一个侦听器只对少数实体类型感兴趣并更新不同表中的数据。

我遇到的问题是,在创建或更新我的审计实体并将它们保存到会话后,侦听器反过来尝试刷新会话,这会触发另一个更新,不久之后我得到StackOverflowException。

下面是两个不同的侦听器正在做的事情的示例:

// Generic audit listener (audits everything)
public bool OnPreUpdate(PreUpdateEvent evnt)
{
    // Ignore audit entries, otherwise we go round and round
    if (!(evnt.Entity == AuditEntry))
    {
        ISession session = evnt.Session.GetSession(EntityMode.Poco);
        // create AuditEntry for the updated Entity
        // ...
        session.Save(auditEntity);
        session.Flush();
    }
}
// Restricted audit listener (only interested in a handful of entities)
public bool OnPreUpdate(PreUpdateEvent evnt)
{
    if (evnt.Entity is RelevantToThisListener) // etc
    {
        ISession session = evnt.Session.GetSession(EntityMode.Poco);
        // create or modify some other audit entity
        // ...
        session.Save(auditEntity);
        session.Flush();
    }
}

一个想法是只有一个审计侦听器,适当地委托任务,并负责一次刷新。

但在走这条路之前,还有其他选择吗?是否可以启动此事件会话的另一个隔离会话,以便我仅刷新新更改?

谢谢

使用多个NHibernate监听器来更新数据库

选项1:var isolatedSession = evnt.Session.Factory.OpenSession();

选项2:从监听器中删除session.Flush();

我支持选项2,因为

  • 将启用审计行的批处理,而立即刷新将中断
  • 审计行也会在被审计实体回滚时被回滚