我不知道為什么你會選擇對特定數(shù)量的“錯誤”(或警告)如此具體。聽起來您正在尋找將要發(fā)布到 Yahoo! 的某些文章的內(nèi)容。 Insider (N Foos to Blah for the BlahBlah)。
那說:
當(dāng)您考慮使用 redis 時,我建議您考慮以下幾點:
選擇一致的方式來命名您的密鑰并為其添加前綴。管理您的命名空間。
創(chuàng)建一個關(guān)鍵前綴或模式的“注冊表”,將每個前綴或模式映射到“擁有”它們的內(nèi)部應(yīng)用程序(并在維基中記錄這些,perhaos)
對于您放入 Redis 基礎(chǔ)設(shè)施的每一類數(shù)據(jù):設(shè)計、實施和測試?yán)占?或數(shù)據(jù)遷移到存檔存儲的機制。
在對應(yīng)用程序部署進(jìn)行大量投資之前,設(shè)計、實施和測試分片(一致散列)庫,并確保在每個服務(wù)器上保留復(fù)制的“分片”注冊表。
將您所有的 K/V 存儲和相關(guān)操作隔離到您自己的庫/API 或服務(wù)中,并以無情和無情的鐵手絕對強制使用該 API/服務(wù)
讓我依次解釋這些要點:
您應(yīng)該從一開始就假設(shè)您的 Redis 基礎(chǔ)設(shè)施將是許多應(yīng)用程序或單獨模塊使用的公共資源。每個服務(wù)器上可以有多個數(shù)據(jù)庫(默認(rèn)編號為 0 到 31,但您可以增加這些數(shù)據(jù)庫的數(shù)量)。但是,最好假設(shè)您需要使用鍵前綴來避免各種不同應(yīng)用程序/模塊之間的沖突。
一致的鍵前綴:管理您的命名空間:
您的應(yīng)用程序/模塊應(yīng)該提供動態(tài)更改這些鍵前綴的靈活性。確保所有鍵都是從應(yīng)用程序/模塊前綴與您正在操作的鍵連接起來合成的;禁止對關(guān)鍵字符串進(jìn)行硬編碼。
注冊表:記錄和跟蹤您的命名空間:
我建議您在 Redis 服務(wù)器上“保留”某些關(guān)鍵模式(前綴或全局模式)。例如,您可以將 __key_registry__(類似于 Python 保留方法/屬性名稱)作為 URL 的關(guān)鍵前綴的哈希,進(jìn)入您的 wiki 或 Trac 或您使用的任何內(nèi)部文檔站點。因此,您可以對數(shù)據(jù)庫內(nèi)容進(jìn)行管理,并追蹤誰/什么對您在任何數(shù)據(jù)庫中找到的每個鍵負(fù)責(zé)。 (制定一項政策,即任何與您的注冊表中的任何模式不匹配的密鑰都可以/將被您的自動內(nèi)務(wù)管理立即刪除)。
垃圾收集:
在持久的、共享的、鍵/值存儲中,特別是在 Redis 的情況下(其中完整的鍵/值存儲必須始終適合 RAM ---不推薦使用 VM/交換存儲)垃圾收集是可能是單一的主要維護(hù)問題。
因此,您需要考慮如何選擇需要從 Redis 遷移出的數(shù)據(jù)(可能會遷移到 SQL/RDBMS 或其他形式的存檔存儲中),以及您將如何跟蹤和清除數(shù)據(jù)這是過時的或無用的。
顯而易見的方法涉及使用 EXPIRE 或 EXPIREAT 功能/命令。這允許 Redis 為您管理垃圾收集,無論是相對于您對任何給定鍵的操作(創(chuàng)建或更新),還是根據(jù)絕對(自紀(jì)元以來的秒數(shù))時間規(guī)范。關(guān)于 Redis 過期的唯一技巧是每次更新密鑰時都必須重新設(shè)置它。
這種方法適用于它自然適用的情況。但是,如果您想無限期地緩存數(shù)據(jù)/鍵并且只清理條目,則它沒有用。為此,我建議您使用“ZSET”——一個帶有值和“分?jǐn)?shù)”的集合,可以通過這些分?jǐn)?shù)的范圍來查詢……通常用于有序/排序的集合。在我的模型中,您將向集合、鍵及其關(guān)聯(lián)的時間戳添加項目(當(dāng)您將相應(yīng)的鍵/值添加或更新到數(shù)據(jù)庫本身時。然后您可以使用以下內(nèi)容查詢該 ZSET:ZRANGEBYSCORE __EXPIRY__ 0 $SOME_EPOCH_TIME 獲取在特定時間之前添加/更新的這些子集。您可以迭代此結(jié)果,刪除相應(yīng)的鍵/值對,直到您在服務(wù)器上釋放了足夠的空間來滿足您的需求(或完成了您為自己設(shè)置的其他垃圾收集要求)。
另一種有用的方法是維護(hù)一個或多個隊列(Redis 列表,由 RPUSH/LPUSH 和 RPOP/LPOP 命令、它們的 B* 阻塞表兄弟或相當(dāng)棘手的 BRPOPLPUSH/RPOPLPUSH 命令操作),用于將事物持久化以使其更持久大容量存儲(例如您的 SQL RDBMS)?;旧?,這用作一個工作隊列,列出在 Redis 中已更改的鍵(可能還有某種形式的關(guān)于規(guī)范數(shù)據(jù)存儲的標(biāo)識符),因此需要將其復(fù)制到您的大容量存儲中。您可以監(jiān)控此類隊列的長度為 e確保您沒有遇到不斷增長的積壓。
分片:
Redis 不提供分片。您可能應(yīng)該假設(shè)您將增長超出單個人 Redis 服務(wù)器的容量(從屬服務(wù)器用于冗余,而不是用于擴展,但如果您有某種方法來管理數(shù)據(jù)一致性,您可以將一些只讀操作卸載到從屬服務(wù)器—— - 例如,未到期描述的密鑰/時間戳值的 ZSET 也可用于一些離線批量處理操作;發(fā)布/訂閱功能也可用于主機提供有關(guān)所選密鑰/數(shù)據(jù)靜止的提示。
所以你應(yīng)該考慮編寫自己的抽象層來提供分片。基本上想象一下,你已經(jīng)實現(xiàn)了一個一致的散列方法……在使用它之前,你通過它運行每個合成的密鑰。雖然您只有一個 Redis 服務(wù)器,但哈希到服務(wù)器的映射最終總是指向您唯一的服務(wù)器。稍后,如果您需要添加更多服務(wù)器,則可以調(diào)整映射,以便將一半或三分之一的密鑰解析到其他服務(wù)器。當(dāng)然,您會希望實現(xiàn)這一點,以便主服務(wù)器上的故障導(dǎo)致您的庫/服務(wù)模塊在輔助服務(wù)器和可能的任何第三級服務(wù)器上自動重試。根據(jù)您的應(yīng)用程序,您甚至可能會嘗試從另一個數(shù)據(jù)源(例如您的 SQL RDBMS)完全獲取某些類型的數(shù)據(jù)。
這是一個領(lǐng)域,特別是,我希望看到一個強大的第三方(或 antirez 創(chuàng)建)庫編寫來處理所有繁瑣地位置。一致的散列并不難……但它確實需要相當(dāng)多的精心編寫的代碼來實現(xiàn)——而且它應(yīng)該遠(yuǎn)離大多數(shù)應(yīng)用程序編碼人員。您想要一些可以正常工作并繼續(xù)工作的東西,即使您添加了額外的服務(wù)器容量(需要為所有受影響的密鑰遷移實用程序)和故障(要求您已經(jīng)處理了將數(shù)據(jù)復(fù)制到二級和/或三級服務(wù)器) .
將您的 Redis 操作與您的應(yīng)用程序分離:
我希望你已經(jīng)看到了這個建議對我提出的所有其他建議的重要性的預(yù)示。如果有人只是將 Redis 基礎(chǔ)設(shè)施用作臨時的、無底的資源,那么這些都將不起作用。
不要將您的應(yīng)用程序視為使用 Redis!
您正在編寫一個使用一組服務(wù)的應(yīng)用程序。碰巧的是,(部分)這些服務(wù)是由 Redis 服務(wù)器提供的。但是,您應(yīng)該將其視為實現(xiàn)細(xì)節(jié),并專注于您需要哪些服務(wù)以及您向應(yīng)用程序開發(fā)人員提供哪些 API 來提供這些服務(wù)。
Redis 提供的任何東西都不是您通過眾多替代方案無法完成的。如果您編寫正確類型的代碼(可能包括存儲過程、觸發(fā)器等和/或單獨的守護(hù)程序)并實現(xiàn)正確的模式,則可以在某種程度上使用 SQL/RDBMS 后端來近似或提供 Redis 的每個功能它。
如果您專注于需要提供給應(yīng)用程序開發(fā)人員的 API,那么您就有希望更換那些不可避免地需要在以后更換(無論出于何種原因)的部分。您還可以在開發(fā)需要與現(xiàn)有數(shù)據(jù)庫交互的其他應(yīng)用程序和模塊時提供更大的靈活性。






