2014-02-17 94 views
1

我最近已經找到了如何使用NHibernate.Event名稱空間中的IPreDeleteEventListener,IPreInsertEventListenerIPreUpdateEventListener來審計實例。對於IPreInsertEventListeners,真假意味着什麼?

但是,它仍然讓我困惑,這些事件會以成功或失敗的結局返回。

例如,讓我們來看看Ayende的博客文章在這裏找到:

在他的例子,一個可以實現的接口如下:

public class AuditEventListener : IPreInsertEventListener { 
    public bool OnPreInsert(OnPreInsert @event) { 
     var audit = @event.Entity as IHaveAuditInformation; 
     if (audit == null) return false; 

     var time = DateTime.Now; 
     var name = WindowsIdentity.GetCurrent().Name; 

     Set(@event.Persister, @event.State, "CreatedAt", time); 
     Set(@event.Persister, @event.State, "CreatedBy", name); 

     audit.CreatedAt = time; 
     audit.CreatedBy = name; 

     return false; 
    } 
} 

它實際上意味着返回truefalse作爲返回值,sinc e我有另一個例子,其中true返回而不是false Ayende寫道。

這似乎回到true而不是false

public class SoftDeletableListener : IPreDeleteEventListener { 
    public void Register(Configuration cfg) { 
     cfg.EventListeners.PreDeleteEventListeners = 
      new IPreDeleteEventListener[] { this } 
       .Concat(cfg.EventListeners.PreDeleteEventListeners) 
       .ToArray(); 
    } 

    public Boolean OnPreDelete(PreDeleteEvent @event) { 
     ISoftDeletable softDeletable = @event.Entity as ISoftDeletable; 

     if (softDeletable == null) return true; 

     EntityEntry entry = @event.Session 
      .GetSessionImplementation() 
      .PersistenceContext 
      .GetEntry(@event.Entity); 
     entry.Status = Status.Loaded; 

     softDeletable.Deleted = true; 

     Object id = @event.Persister 
      .GetIdentifier(@event.Entity, @event.Session.EntityMode); 
     Object [] fields = @event.Persister 
      .GetPropertyValues(@event.Entity, @event.Session.EntityMode); 
     Object version = @event.Persister 
      .GetVersion(@event.Entity, @event.Session.EntityMode); 

     @event.Persister.Update(id 
      , fields 
      , new Int32[1] 
      , false 
      , fields 
      , version 
      , @event.Entity 
      , null 
      , @event.Session.GetSessionImplementation()); 

     return true; 
    } 
} 

所以我想知道什麼false/true實際上告訴NHibernate的取決於聽者處理。

+0

在'SoftDeletableListener'例如,當不可t是'if(softDeletable == nul l)返回false;'('false'而不是'true')?否則不會刪除任何實體,無論它是否是「ISoftDeletable」。 – lalibi

回答

3

在這種情況下,返回值應爲枚舉,讓我們用名字OnPreEventResult,而這些將是可能的值:

  • OnPreEventResult.Continue =>繼續目前返回false
  • OnPreEventResult.Break =>此刻,當true返回行動中止

所以,如上圖所示兩個例子中,我們可以使用返回值來管理執行流程:

  1. 以繼續
    如果我們在AuditEventListener回報,我們實際上返回類似OnPreEventResult.Continue。我們已經取得了一些custome邏輯,我們希望NHibernate的繼續......所以返回

  2. 玩轉/中止
    Ayende的例子向我們展示如何改變現實DELETE成UPDATE。更新顯式調用@event.Persister.Update(...和刪除是由於返回值執行,即OnPreEventResult.Break

在代碼中,返回的值存儲在一個名爲veto局部變量,這又是更自我描述。

參見:

EntityInsertAction甲片段中,Execute()方法:

... 
bool veto = PreInsert(); 

if (!veto) 
{  
    persister.Insert(id, state, instance, Session); 
... 
+0

+1感謝您的好解釋!我現在更好地瞭解發生了什麼。這些例子,恕我直言,如果他們實際上使用了這個'OnPreventResult'枚舉,它將會更簡潔。謝謝@Radim! –

+0

偉大的,如果這有幫助無論如何。享受NHibernate :) –

+0

很好的解釋。 實際上這個例子是錯誤的。如果這個類沒有實現「軟刪除」合約,那麼攔截器應該返回false而不是true。 – Raffaeu