高效能kv儲存之Redis、Redis Cluster、Pika:如何應對4000億的日訪問量?
一、背景介紹
隨著360公司業務發展,業務使用kv儲存的需求越來越大。為了應對kv儲存需求爆發式的增長和多使用場景的需求,360web平臺部致力於打造一個全方位,適用於多場景需求的kv解決方案。目前,我們線上大規模使用的kv儲存有Redis,Redis cluster以及Pika。
為什麼說是爆發式的需求增長呢?早在2015年9月份,公司Redis的日訪問量還處於800億,到了2016年第三季度日訪問量已經突破2500億,2017年第一季度日訪問量已經接近4000億。短短的一年半時間,日訪問量增長了5倍。下面給大家分別簡單介紹一下Redis,Redis Cluster以及Pika的特點和使用場景。
二、kv儲存之Redis
1、Redis介紹
Redis做為大家熟知的開源記憶體資料庫,在很多專案中被廣泛的使用。它支援String、Hash、List、Set、Zset、Geo、Hyperloglogs等多資料結構。同時也支援主從複製、Lua指令碼、事務、資料持久化、高可用和叢集化等等
2、Redis特性
1)高效能:Redis雖然是單執行緒的,但是它同樣擁有著超高的效能。我們線上的普通PC Server上,經過測試,每秒請求數OPS能夠達到10w左右。
2)多樣化資料結構:Redis支援String、Hash、List、Set、Zset、Geo等多資料結構。
3)持久化:RDB持久化:快照式持久化方式,將記憶體中的全量資料dump到磁碟。它的優勢是載入速度比AOF快,劣勢是快照式的全量備份,沒有增量資料,造成資料丟失。
AOF持久化:AOF記錄Redis執行的所有寫操作命令。恢復資料的過程相當於回放這些寫操作。使用AOF的持久化方式,優勢是有靈活的刷盤策略,保證資料的安全性。劣勢是AOF檔案體積比RDB大,佔用磁碟多,資料載入到記憶體的資料慢。
4)多重資料刪除策略:
①惰性刪除:當讀/寫一個已經過期的key時,會觸發惰性刪除策略,刪除掉這個過期key。
②定期刪除:由於惰性刪除策略無法保證冷資料被及時刪掉,所以Redis會定期主動淘汰一批已過期的key。
③主動刪除:當前已用記憶體超過maxmemory限定時,觸發主動清理策略,該策略由啟動引數的配置決定,可配置引數及說明如下:
- volatile-lru:從已設定過期時間的樣本中根據LRU演算法刪除資料 (redis3.0之前的預設策略)
- volatile-ttl:從已設定過期時間的樣本中挑選過期時間最小的資料刪除
- volatile-random:從已設定過期時間的樣本中隨機選擇資料刪除
- allkeys-lru:從樣本中根據LRU演算法刪除資料
- allkeys-random:從樣本中任意選擇刪除資料
- noenviction:禁止從記憶體中刪除資料 (從redis3.0 開始預設策略)
maxmemory-samples 刪除資料的抽樣樣本數,redis3.0之前預設樣本數為3,redis3.0開始預設樣本數為5,該引數設定過小會導致主動刪除策略不準確,過大會消耗多餘的cpu。
5)高可用:Redis自身帶有哨兵的元件,可以監控Redis主從的執行狀態和自動的故障切換,實現Redis的高可用。
3、Redis使用場景
一般場景:OPS < 10W,資料量較小
進階場景:單點寫入可以支撐,但讀取量巨大,可以採用讀寫分離,1主多從的方案;
寫入讀取量都很大,單點寫入無法支撐,可以採用Hash分片方式。
但是,無論數讀寫分離的方式還是Hash分片的方式,在的Redis的架構中沒有引入中介軟體或者更加智慧的驅動的情況下,都需要從程式碼上去保證,這一定程度上增加了開發人員的程式碼複雜度。同時隨著業務的增長,擴充套件性也較差。那麼如何更加理想的去解決這個問題,使用Redis Cluster會是一個更加簡潔有效的方案。
三、kv儲存之Redis Cluster
1、Redis Cluster介紹
Redis Cluster 是一個分散式、無中心節點的、高可用、可線性擴充套件的記憶體資料庫,Redis Cluster的功能是普通單機 Redis 的功能的一個子集。Redis Cluster為了保證一致性而犧牲了一部分容錯性: 系統會在保證對網路斷線和節點失效具有有限抵抗力的前提下, 儘可能地保持資料的一致性。
2、Redis Cluster重要概念:
①hash slots——雜湊槽
Redis 叢集沒有使用一致性hash,而是引入了雜湊槽(hash slot)的概念。Redis 叢集一共有16384個hash slot,叢集使用CRC16校驗後對16384取模來計算鍵key屬於哪個槽。
②cluster node——叢集節點
叢集中的每個主節點負責處理16384個hash slot中的一部分。每個node的hash slot數量可以靈活手工調整。
③cluster map——叢集資訊表
叢集中的每個節點都記錄整個叢集的Cluster map資訊,叢集資訊包括每個節點的唯一id號,ip地址,port埠號,role 在叢集中的角色,主節點負責的hash slot的範圍,節點狀態等。節點之間通過Gossip協議進行通訊,傳播叢集資訊,並發現新節點向其他節點發送ping包,檢查目標節點是否正常執行。
3、Redis Cluster架構
4、Redis Cluster資料路由
①client執行命令,計算key對應的hash slots
②根據本地快取的cluster map資訊,連線負責該hash slots的資料節點獲取資料
如果slot不在當前連線的節點,返回moved錯誤,重定向客戶端到新的目的伺服器上獲取資料,並更新client本地快取的cluster map
如果slot在當前節點且key存在,則執行操作結果給客戶端
如果slot遷出中,返回ask錯誤,重定向客戶端到遷移的目的伺服器上獲取資料
5、使用場景
大容量、高併發、可線性擴充套件
剛才僅僅是對Redis Cluster做了簡單的介紹,關於叢集的建立、資料的遷移、叢集的擴容和縮容、hash slots重分佈、叢集的reblance等日常操作,使用Redis Cluster中遇到的問題以及在改進smart driver道路上解決的問題等等,如果有同學感興趣的話,歡迎私下共同交流學習。
四、kv儲存之Pika
1、Pika是什麼
Pika 是DBA需求,基礎架構組開發的大容量、高效能、持久化、支援多資料結構的類Redis儲存系統,目前已經開源,最新版本為Pika 2.2版本。它所使用的nemo引擎本質上是對Rocksdb的改造和封裝,使其支援多資料結構的儲存,並在nemo引擎之上封裝redis介面,使其完全支援Redis協議。Pika相容string、hash、list、zset、set等多資料結構,使用磁碟而非記憶體儲存資料解決了Redis由於儲存資料量巨大而導致記憶體不夠用的容量瓶頸。
2、Pika PK Redis
Pika PK Redis之優勢:
①大容量儲存:Pika資料容量受制於磁碟,最大使用空間等於磁碟空間的大小,而Redis資料容量受限於主機記憶體
②秒級啟動:Pika 在寫入的時候, 資料是落盤的,Pika 重啟不用載入所有資料到記憶體,不需要進行回放資料操作。而Redis啟動需要將所有資料從磁碟載入到記憶體,隨著容量增加,啟動時間遞增到分鐘級甚至更長時間。
③秒級備份:Pika的備份方式,是將所有資料檔案做快照。Redis無論是用RDB還是AOF的方式來實現資料備份的目的,都需要將全量的資料寫入到磁碟,備份速度慢。
④秒刪資料:Pika的資料刪除是標記刪除,Pika Key的元資訊上有版本資訊,表示當前key的有效版本,已刪除的資料在Compact合併資料的過程中刪除。而單執行緒的Redis在大量刪除資料時候會影響線上業務,刪除大物件會阻塞住Redis的主執行緒,刪除速度慢。
⑤同步續傳:Pika寫入資料會有write2file日誌檔案,只要該檔案未刪除,無需全量同步資料,均可斷點續傳資料。而Redis一旦主從同步緩衝區被迴圈重寫,容易導致全量資料重傳。
⑥高壓縮比:Pika儲存的資料預設會被壓縮,相對於Redis,Pika有5~10倍的壓縮比。所以Redis的資料儲存到Pika,資料體積會小很多。
⑦高性價比:相對於Redis使用昂貴的記憶體成本,Pika使用磁碟儲存資料,價效比極高
Pika PK Redis之劣勢:
①讀寫效能較弱:Pika是持久化的,基於磁碟的kv儲存。而Redis是記憶體資料庫。雖然pika是多執行緒的,但是在大多場景下,效能還是略遜色於Redis
②多資料結構效能損耗:Pika底層使用Rocksdb儲存引擎,它並不支援多資料結構,Pika在Rocksdb的上層進行了改造和封裝,實現了對多資料結構的支援。同時在效能上,會有一些損耗。
③相容大部分Reids介面:Pika相容了90% Redis介面,使其易用性得到大大提升。但是目前還沒有做到完全相容。
3、Pika整體架構
4、Pika使用場景
①業務量並沒有那麼大,使用Redis記憶體成本太高
②資料量很大,使用Redis單個伺服器記憶體無法承載
③經常出現時間複雜度很高的請求讓Redis間歇性阻塞
④讀寫分離且不希望故障切主後影到從庫,能夠快速切換
5、Pika使用現狀
①內部:目前Pika已經在360內部的各個業務線廣泛使用,共計覆蓋43個主業務線和76個子業務線,近千億的日訪問量和數十T的資料規模,節約了大量昂貴的伺服器記憶體,降低了使用成本。
②社群:在業內,據不完全統計,很多著名網際網路公司也使用了Pika,例如新浪微博、美團、58同城、迅雷、萬達電商、環信…………
6、Redis如何遷移到Pika
那麼,在適用於 Pika的業務場景下,我們如何將Redis資料遷移到Pika呢?
Pika自帶的工具集,其中aof_to_pika這個工具可以幫助我們完成很平滑的這個任務。由於該工具依賴於AOF來發送資料,所以原Redis必須要開啟AOF,並關閉AOF重寫的策略。aof_to_pika通過reader執行緒讀取aof檔案中的內容,根據設定的單次傳送長度拼裝成資料塊,將要傳送的資料庫加入佇列。同時sender執行緒不斷的從佇列中讀取資料傳送到目的Pika完成資料的重放。
除了Redis的遷移工具之外。考慮有同學可能也使用到了ssdb,那麼Pika也很貼心的提供了從ssdb遷移資料到Pika的工具ssdb_to_pika。
五、多場景的業務需求
最後,針對於業務多變的kv儲存需求,常常有兩個重點是我們最為關注的,一個是資料量,另一個是訪問量。圍繞著資料量和訪問量的大小,往往決定了我們是使用Redis、Redis Cluseter or Pika。
六、QA
Q1:Pika支援叢集嗎?
A1:Pika目前主持主從結構,也支援codis。自身目前還不支援分散式的叢集化,我們還在做多資料結構叢集化的調研。
Q2:Pika 與Redis什麼關係?替代嗎還是補充?看著像是補充。 Pika 如果是替代Redis,那使用磁碟如何保證高效能。
A2: Pika與Redis是使用場景上互相補充的關係。目前線上的Pika機器都使用的ssd,一般場景下ops在5w以內場景都能輕鬆應對。
Q3:Redis持久化方式如何選取?還是不做持久化?
A3:持久化多數場景下選擇AOF方式,做不做持久化取決於業務對資料安全性的要求,畢竟純快取的資料一旦伺服器宕機或者資料庫崩潰,資料都會全部丟失。
Q4 : 張老師你好,Pika掛固態硬碟讀寫效能是否可以pk Redis?360 業務有這樣應用嗎?
A4:目前360內部使用Pika的應用,全部使用的都是SSD硬碟。
Q5 : Pika 裡邊 zset 是落地的麼,zset是怎麼實現的呢? 對scan 類的命令支援怎樣?Pika 效能如何?
A5: 是落地的,大致原理是將一條key-score-members轉換成3條rocksdb的kv來儲存。scan是都支援的,和Redis一樣。Pika的效能我們認為還不錯,能夠滿足多數場景,但是建議大家要部署在SSD上,和記憶體比SSD還是便宜太多的,另外非常歡迎大家用測試比較Pika與相似專案的效能!
Q6 : 老師,像類似於fastdfs也是儲存在硬碟的,請問Pika與他們在使用場景上有什麼不同呢?
A6: 就我個人知識瞭解,fastdfs是一個分散式檔案系統,儲存小檔案、圖片等,與Pika面向的場景不一樣,Pika是為了解決Redis單機記憶體不足而設計的一個線上資料庫,當然,只要單機磁碟容量夠,也是可以儲存二進位制檔案到pika的。
Q7: Pika和Aerospike相比有哪些優勢呢?Aerospike開源版本記憶體加持久化後,執行刪除操作,重啟後刪除的資料會重新從磁碟載入,Pika有沒有這個弊病?
A7: Pika的設計初衷其實就是為滿足業務在Redis儲存中,因為記憶體不足而造成業務損失,所以,我們的Pika的命令基本與Redis保持一致,並且client也是複用Redis的,這樣,業務從Redis切換到Pika,無任何複雜度,這一點,我個人看Aerospike是比不了的。另外,Pika是不會載入刪除資料。
Q8:redis 中熱鍵大鍵如何處理?發現大部分故障都源於此
A8: 熱點資料需要進行業務邏輯上的拆分或者多級快取分擔壓力。我們線上也因為大鍵造成了一些困擾,例如:網絡卡頻寬被打死、del大鍵造成Redis堵塞等,從Redis本身,確實沒有太好的辦法來解決,只能從業務層面分析出現大鍵的原因,做出響應的對策,例如:對大鍵進行壓縮儲存、或者儲存大鍵到有多執行緒處理的pika中等等。
作者介紹
張恆,360web平臺部DBA ,主要負責公司kv儲存、資料倉庫gp運維以及私有云資料庫平臺建設。
文章來自微信公眾號:高效運維開發