2012-07-11 82 views
2

背景/意圖:一次增加數百個計數器,redis或mongodb?

所以我要從頭開始創建一個事件跟蹤器,並有幾個關於如何做到這一點的想法,但我不確定的最佳方式與數據庫方面着手東西的。我有興趣做的一件事是允許這些事件是完全動態的,但同時允許報告關係事件計數器。

例如,所有國家按操作系統細分。預期的效果將是:

  1. 美事件#
    • 的iOS - 事件#,在美國發生
    • 的Android - 事件#,在美國發生
  2. CA#的事件
    • iOS - 發生在CA的事件數#
    • Android - 發生在CA中的事件數#

我的意圖是要能夠接受這些事件的名字,像這樣:

/?country=US&os=iOS&device=iPhone&color=blue&carrier=Sprint&city=orlando&state=FL&randomParam=123&randomParam2=456&randomParam3=789 

爲了做關係計數器像上面我這意味着每個請求可能會增加100+個計數器。

假設每天會有上千萬的上述請求。

我想讓事情完全保持動態,而且我也希望以這種方式進行,以便數據查找保持超級快速。因此,我一直在研究如何使用redis或mongodb。

問題:

  1. 有沒有更好的辦法,同時保持動態的領域做到這一點,然後櫃檯?

  2. 如果這是全部在一個文件中(結構像一棵樹),將在mongodb中使用$ inc操作符在一次操作中同時增加100個以上的計數器是可行的而不是緩慢的?這裏的好處是,我可以在單個查詢中快速檢索一個「廣告系列」的所有統計信息。

  3. 這會更適合於redis併爲事件的所有適用計數器執行鋅比?

感謝

+0

如何「動態」你需要它?即什麼延遲?另一種方法是爲每個事件存儲文檔,然後定期使用map-reduce來彙總數據。這樣的方法也可以讓你改變事後報告的內容(例如添加'奧蘭多'的自定義報告)。 – 2012-07-11 22:38:43

+0

由於這是更多的市場營銷信息,它將是理想的儘快提供。爲什麼我認爲櫃檯可能很適合的另一個原因。 – Ataraxy 2012-07-12 00:51:02

回答

2

根據您的密鑰結構的佈局方式,我會建議流水線的zincr命令。你有一個簡單的「提交」觸發器 - 請求。如果你要迭代你的參數並且遍歷每個鍵,那麼在請求結束時通過execute命令將會非常快。我已經實現了一個系統,就像你在cgi和Django應用程序中描述的一樣。我設置了一鍵結構一起的臺詞:

YYYY-MM-DD:HH:MM - >排序集合

,並能夠處理事情是每秒150000-200000增量對Redis的側有一個單一的過程,這應該是足夠的你描述的情況。這個關鍵結構使我能夠根據時間窗口獲取數據。我還添加了一個過期的密鑰,以避免編寫一個數據庫清理過程。然後我有了一個cronjob,它可以使用上述關鍵模式的變體來設置操作,以「彙總」每小時,每天和每週的統計數據。我提出這些想法是因爲您可以利用Redis的內置功能來簡化報告方面。還有其他的方式,但這種模式似乎運作良好。

正如eyossi指出的那樣,全局鎖定對於並行寫入和讀取的系統來說可能是一個真正的問題。如果您將此作爲實時系統編寫,那麼併發性可能會成爲問題。如果它是「結束日期」日誌解析系統,那麼它不可能觸發爭用,除非在輸入時運行解析器或報告的多個實例。關於保持讀取速度快在Redis中,我會考慮設置一個只讀redis實例,從主引導文件中刪除。如果您將其放在運行報告的服務器上,並將其指向報告進程,則應該非常快速地生成報告。

根據您的可用內存,數據集大小以及是否將任何其他類型的數據存儲在redis實例中,您可能會考慮運行32位redis服務器以減少內存使用量。一個32b實例應該能夠將很多這種類型的數據保存在一小塊內存中,但是如果運行正常的64位Redis並沒有佔用過多的內存,可以隨意使用它。與往常一樣測試你自己的使用模式,以驗證

+0

謝謝你的觀點和建議。我實際上正在考慮以類似的方式進行。其目的是爲了實現這一目標,並擁有多個用戶和活動,因此可以將數據從Redis中滾出來,這可能會很棘手,因爲這些參數可能會產生如此多的未知變化。我將不得不進一步思考這一點,但這應該是一個開始的好地方! – Ataraxy 2012-07-12 23:09:18

0

在Redis的,你可以使用multi同時遞增多個鍵。

+0

非常感謝,玩了幾分鐘後,我想我可能會以這種方式結束。 – Ataraxy 2012-07-12 00:52:11

0

我對MongoDB有一些不好的經驗,我發現當它有很多寫入時它可能會非常棘手......

你可以看看this link瞭解更多信息,不要忘記閱讀「MongoDB使用1 BFGL(大型全局鎖定)」的部分(這可能已經在版本2.x中得到了改進 - 我沒有檢查它)

另一方面,我有一個很好的經驗Redis,我用它進行了大量的讀/寫操作,效果很好。 你可以找到關於如何我使用Redis的更多信息(以獲得有關併發量讀取/寫入感覺)位置:http://engineering.picscout.com/2011/11/redis-as-messaging-framework.html

+0

欣賞鏈接。我已經使用了redis,並且非常喜歡它,所以我可能只需要使用它。讓我想起mongodb的是在一份文件中爲「競選」做好每件事的潛在前景,但BFGL在這方面令人沮喪。雖然我不清楚這是否僅影響集合中的書寫,或者它也影響集合中的事物。我會進一步研究這一點! – Ataraxy 2012-07-12 00:54:36

0

我寧願用pipeline不是multi如果你不需要的原子功能..