Codis學習(一)——初識

Codis是一個用Go編寫的分佈式、高性能Redis集羣解決方案。並且已投入生產,廣泛應用於許多公司。

對於上層的應用來說, 連接到 Codis Proxy 和連接原生的 Redis Server 沒有顯著區別 (除了部分codis不支持的命令外), 上層應用可以像使用單機的 Redis 一樣使用, Codis 底層會處理請求的轉發, 不停機的數據遷移等工作, 所有後邊的一切事情, 對於前面的客戶端來說是透明的, 可以簡單的認爲後邊連接的是一個內存無限大的 Redis 服務。


今日內容預覽

與Twemproxy和Redis-Cluster對比


- Codis Twemproxy Redis-Cluster
不重啓集羣的情況下resharding 支持 不支持 支持
pipeline 支持 支持 不支持
hash的多域操作 支持 支持 支持
resharding時的多鍵操作 支持 - 不支持
Redis客戶端支持 任意客戶端 任意客戶端 客戶端必須支持cluster協議

“resharding”意味着將數據從一個redis服務器遷移到另一個redis服務器,通常在增加/減少redis服務器數量時發生。

相對於twemproxy的優劣?

codis和twemproxy最大的區別有兩個:一個是codis支持動態水平擴展,對client完全透明不影響服務的情況下可以完成增減redis實例的操作;一個是codis是用go語言寫的並支持多線程而twemproxy用C並只用單線程。 後者又意味着:codis在多核機器上的性能會好於twemproxy;codis的最壞響應時間可能會因爲GC的STW而變大,不過go1.5發佈後會顯著降低STW的時間;如果只用一個CPU的話go語言的性能不如C,因此在一些短連接而非長連接的場景中,整個系統的瓶頸可能變成accept新tcp連接的速度,這時codis的性能可能會差於twemproxy。

相對於redis cluster的優劣?

redis cluster基於smart client和無中心的設計,client必須按key的哈希將請求直接發送到對應的節點。這意味着:使用官方cluster必須要等對應語言的redis driver對cluster支持的開發和不斷成熟;client不能直接像單機一樣使用pipeline來提高效率,想同時執行多個請求來提速必須在client端自行實現異步邏輯。 而codis因其有中心節點、基於proxy的設計,對client來說可以像對單機redis一樣去操作proxy(除了一些命令不支持),還可以繼續使用pipeline並且如果後臺redis有多個的話速度會顯著快於單redis的pipeline。同時codis使用zookeeper來作爲輔助,這意味着單純對於redis集羣來說需要額外的機器搭zk,不過對於很多已經在其他服務上用了zk的公司來說這不是問題:)

Codis特性


可視化管理界面以及admin命令行管理工具
支持大多數Redis命令,與Twemproxy完全兼容
動態擴縮容

Codis組成


Codis 3.x 由以下組件組成:

Codis Server:基於 redis-3.2.8 分支開發。增加了額外的數據結構,以支持 slot 有關的操作以及數據遷移指令。具體的修改可以參考文檔 redis 的修改。

Codis Proxy:客戶端連接的 Redis 代理服務, 實現了 Redis 協議。 除部分命令不支持以外(不支持的命令列表),表現的和原生的 Redis 沒有區別(就像 Twemproxy)。

對於同一個業務集羣而言,可以同時部署多個 codis-proxy 實例;
不同 codis-proxy 之間由 codis-dashboard 保證狀態同步。

Codis Dashboard:集羣管理工具,支持 codis-proxy、codis-server 的添加、刪除,以及據遷移等操作。在集羣狀態發生改變時,codis-dashboard 維護集羣下所有 codis-proxy 的狀態的一致性。

對於同一個業務集羣而言,同一個時刻 codis-dashboard 只能有 0個或者1個;
所有對集羣的修改都必須通過 codis-dashboard 完成。

Codis Admin:集羣管理的命令行工具。

可用於控制 codis-proxy、codis-dashboard 狀態以及訪問外部存儲。

Codis FE:集羣管理界面。

多個集羣實例共享可以共享同一個前端展示頁面;
通過配置文件管理後端 codis-dashboard 列表,配置文件可自動更新。

Storage:爲集羣狀態提供外部存儲。

提供 Namespace 概念,不同集羣的會按照不同 product name 進行組織;
目前僅提供了 Zookeeper、Etcd、Fs 三種實現,但是提供了抽象的 interface 可自行擴展。

codis的分片


Codis 採用 Pre-sharding 的技術來實現數據的分片, 默認分成 1024 個 slots (0-1023), 對於每個key來說, 通過以下公式確定所屬的 Slot Id : SlotId = crc32(key) % 1024。

每一個 slot 都會有一個且必須有一個特定的 server group id 來表示這個 slot 的數據由哪個 server group 來提供。數據的遷移也是以slot爲單位的。

關於遷入codis


分兩種情況:

1、原來使用 twemproxy 的用戶: 可以, 使用codis項目內的redis-port工具, 可以實時的同步 twemproxy 底下的 redis 數據到你的 codis 集羣上. 搞定了以後, 只需要你修改一下你的配置, 將 twemproxy 的地址改成 codis 的地址就好了. 除此之外, 你什麼事情都不用做.

2、原來使用 Redis 的用戶: 如果你使用了下面提到的codis不支持的命令,是無法直接遷移到 Codis 上的. 你需要修改你的代碼, 用其他的方式實現.

codis不支持的命令列表


以下命令codis不允許使用,如果使用,proxy會關閉連接進行警告。

類型 命令
keys keys,migrate,move,object,randomkey,rename,renamenx,scan
string bitop,msetnx
list blpop,brpop,brpoplpush
pub/sub psubscribe,publish,punsbscribe,subscribe,unsubscribe
transaction discard,exec,multi,unwatch,watch
scripting script
server bgrewriteaof,bgsave,client,config,dbsize,debug,flushall,flushdb,lastsave,latency,monitor,psync,replconf,restore,save,shutdown,slaveof,slowlog,sync,time
codis slot SLOTSCHECK,SLOTSDEL,SLOTSINFO,SLOTSMGRTONE,SLOTSMGRTSLOT,SLOTSMGRTTAGONE,SLOTSMGRTTAGSLOT

以下命令是“半支持”的。Codis不支持跨節點操作,因此您必須使用哈希標籤將一個請求中顯示的所有密鑰放入同一個插槽中,然後您就可以使用這些命令。 Codis不檢查密鑰是否具有相同的標籤,因此如果您不使用標籤,您的程序將得到錯誤的響應。

類型 命令
list rpoplpush
set sdiff,sinter,sinterstore,smove,sunion,sunionstore
sorted set zinterstore,zunionstore
hyperloglog pfmerge
scripting eval,evalsha
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章