2011-03-22 81 views
2

我的問題是,我有很多事件發生在一個大型Web應用程序中,現在我想查看發生了什麼(用於審計目的),或者我想彙總數據以進行統計報告。收集審計和統計數據

一種解決方案是在DB中爲每種類型的事件創建一個表並將其記錄在那裏。例如更改密碼,記錄日期,用戶,IP等。這將爲我提供我需要的審計信息,並且還能夠根據表運行報告以瞭解此功能的使用頻率。缺點是我需要爲每個要捕獲的事件類型創建一個新表。

我的理想解決方案是使用一個更靈活的結構,也許是一個XML字段的單個表,但我並不是瘋狂的表中的xml字段。

所以我的問題:是否有一個很好的(流行)模式來解決我的問題?

回答

1

每個事件一個表和一個表之間的中間方式(假定事件之間的差與該事件中攜帶的參數/數據):

Event Type 
    Event Type Id (PK) 
    Name 
    Number of parameters (useful - not essential) 

Event 
    Event Id (PK) 
    Event Type Id (FK) 
    Timestamp 

Event Attribute 
    Event Attribute Id (PK) 
    Event Id (FK) 
    Name 
    Value (as string in all cases) 
    Sequence Number (within Event. this may well not be needed, but can be a convenience) 

我不認爲這是一個命名模式,但它是數據庫設計中反覆出現的模式。

我認爲這會給你所需要的所有信息,而不需要存儲XML。

+0

感謝克里斯 - 欣賞模式和解釋。 – Guy 2011-03-24 18:32:12

2

您的大型網絡應用程序有多大?

將事件記錄爲XML blob應該可以工作,並且某些數據庫(例如SQL Server)可以讓您直接查詢該XML。但是,這些查詢的性能很糟糕。

在數據庫中進行事件日誌記錄之前,您應該計算出每秒要創建多少條記錄。 如果數量很大,它會給數據庫帶來嚴重的負擔,並可能影響您的整體應用程序性能。另外,一旦你累積了大量的記錄,查詢數據將永遠持續(並且在這個過程中殺掉數據庫性能)。聚合數據更糟糕 - 關係數據庫在聚合方面效率不高。

克里斯的上述建議對於小型數據庫很適用,但不會擴展,因爲您的查詢必須使用連接。解除數據標準化可能會更好。

即使您的應用程序沒有獲得足夠的流量,您現在仍然擔心此問題,請記住,由於上述原因,記錄到數據庫的事件無法很好地擴展。

Concreate建議:

如果你沒有那麼多的流量,並決定登錄到數據庫,這樣做是爲了一個獨立的模式,這樣它會更容易讓你將它移到一個單獨的數據庫服務器,以便從生產數據庫中卸載它。

如果您決定將事件記錄爲xml,請考慮使用關係數據庫是否有用處 - 如果無法高效查詢,那麼簡單的日誌文件將更簡單。當然,當然你必須弄清楚如何處理這些日誌數據,但是對於不經常/簡單的查詢,使用grep,awk等編寫一些腳本會讓你有一個非常長的路要走。

通常通過(非常)大規模應用現今所用的方法記錄到的文件,然後在運行使用分析(聚集)地圖降低,例如在hadoop上。

+0

謝謝Elad - 感謝您的詳細回覆。 – Guy 2011-03-24 18:31:48

+0

就像感興趣的事情一樣,你認爲聯接不能縮放?我一直都明白,聯接實際上是零成本,因此對數據庫或其模式的可伸縮性沒有影響。 – 2011-03-24 20:04:01

+1

@ chris-walton google「數據庫連接不會擴展」,您將獲得大量示例,主要來自NoSQL陣營。我還可以從個人經驗中證明,一旦你傳遞了一定的表大小(在MySQL中少至1M記錄,儘管它在很大程度上取決於配置,特別是RAM分配),加入查詢的性能開始快速下降。 – Elad 2011-03-27 15:23:29