【轉】Redis計數在新浪微博的應用

微博業務的迅速發展,對基礎架構層面的要求也愈來愈高。新浪做爲國內最先使用redis,而且是國內最大的redis使用者,在redis的使用上,也在逐步優化和提升。mysql

做爲微博中一項重要的數據,計數類業務在微博業務中佔的比重和重要性逐步提升。計數結果的準確度直接影響用戶體驗,而且很容易引發用戶的投訴。在計數業務上,在不斷的優化和改進中,咱們主要經歷瞭如下三個階段:redis

初級階段

從2010年開始,使用redis-2.0版本。在最初業務數據比較少的時候,表現至關不錯。但隨着數據量和請求量的不斷增長,一些問題逐漸暴露出來。sql

主從同步問題數組

  • 首先遇到的是主從的同步問題。它的原理是當master接收到slave的同步請求後,把內存的數據fork出一個子進程dump出來,造成rdb文件,而後傳到slave,slave再把這個文件加載到內存,以後的增量更新由master在執行完每條修改命令後當即同步給slave。 在網絡出現問題時,好比瞬斷,會致使slave裏的數據所有重傳。對單個端口來講,若是數據量小,那麼這個影響不大,而若是數據量比較大的話,就會致使網絡流量暴增,同時slave在加載rdb時沒法響應任何請求。網絡

  • 持久化問題架構

    計數業務中多數使用redis做爲存儲,所以都開啓了aof,並配置爲每秒作一次fsync操做將寫操做刷新到磁盤。隨着aof的增加,須要按期rewrite。Rewrite的機制和生成rdb的過程相似,都是fork出一個子進程來完成的,子進程對於磁盤的持續寫入會致使父進程的 fsync操做阻塞,形成大量請求超時。運維

  • 版本升級問題異步

    因爲redis在使用初期bug較多,版本迭代頻繁,而版本升級須要關閉redis進程並從新加載aof。對於大量使用redis的微博業務來說,這樣的升級成本也愈來愈難以承受。memcached

  • 內存使用問題函數

    2.0版本的redis,在內存使用上相對比較粗放,對於計數這樣一個簡單的key-value,佔用的內存達到100字節以上,存在比較多的優化空間。

進階階段

針對redis使用初期存在的問題,咱們逐個進行了改進。主從複製參考mysql的同步方式,使用rdb+aof結合的方式,解決了網絡瞬斷引發的重傳問題,同時限制子進程作後臺dump時對磁盤的寫入,期間暫停主進程的fsync操做,解決了慢請求的問題。

針對計數業務,咱們開發了專用的版本redisscounter,單個key-value佔用的內存key的長度加4個字節的value,將內存的使用量下降到原來的1/4如下。經過預先分配內存數組和double hash技術,消除了redis中hash表的大量指針開銷。

對於版本升級的問題,咱們將redis的核心處理邏輯封裝到動態庫,內存中的數據保存在全局變量裏,經過外部程序來調用動態庫裏的相應函數來讀寫數據。版本升級時只須要替換成新的動態庫文件便可,無須從新載入數據。經過這樣的方式,版本升級只需執行一條指令,便可在毫秒級別完成代碼的升級,同時對客戶端請求無任何影響。

有了上面的改進後,新版本開始大量應用,多數業務均可以做爲完整的存儲替代之前的mysql+memcached組合。對於微博的評論數和轉發數,因爲微博條目不斷增長,沒法保存全量數據,所以採用mysql+redisscounter組合的方式,mysql保存全量數據,使用兩組 redisscounter保存最近幾個月的熱數據,經過按期滾動兩組redisscounter裏的數據來清理冷數據。

高級階段

隨着微博的發展,針對單條微博的計數也不斷增長,從原來的評論數、轉發數,又增長了表態數,2013年還上線了閱讀數。Redisscounter 不能很好的解決這類擴展問題,同時上面的mysql+redisscounter的滾動方式也過於複雜,按期的滾動操做很容易出現問題。針對這類問題,咱們再度作出改進,將key由原先的字符串改爲微博id,同時對於每條微博的評論轉發等計數,咱們統計發現,絕大多數微博的計數均可以用10~15個bit 來保存,所以能夠將多個計數保存到一個4字節的value裏,過大的計數值在內存中另外開闢一塊空間來保存。這樣經過一條get命令便可獲取該微博的全部計數。同時針對微博業務的特色,越老的微博被訪問的次數就會越少,在內存使用多個數組保存不一樣範圍的微博,內存不足時將最老的一組微博dump到ssd 上,內部自動實現的滾動能夠保證熱微博所有在內存裏。對於落到ssd上的老數據的訪問,經過異步的io線程來讀寫,通過這樣的改進後,去掉了原先的 mysql存儲,下降了業務開發成本和運維成本。

從redis在計數業務上的發展經歷能夠看出,技術的進步是由業務的需求推進的。隨着業務的發展,還會遇到更多新的挑戰。但願咱們走過的這些改進之路對於讀者在使用redis的過程當中能有所幫助。

相關文章
相關標籤/搜索