Memstore數據刷寫與阻塞機制深入剖析及參數優化


本文來自轉載,轉載地址:https://juejin.im/post/5bfe7892e51d4531b1515164  在此要着重感謝華為的架構師秦凱新大佬!

1 Memstore的角色地位

  • 一個Store中總會有一個Memstore和多個HFile,每一次刷寫就會生成一個HFile。
  • 如果你開啟了BlcokCache,那么讀取數據時會首先查詢BlockCache,當BlockCache查不到數據時,就會去查詢MemStore+HFile的數據。
  • 這里要明確一下,完整的數據集合包含了MemStore中的數據和落盤的HFile文件。
  • MemStore的實現目的不是加速數據的寫入,主要是維持HBase中的數據按照rowkey順序來存儲,所以先使用MemStore先對數據進行整理排序后再持久化到HDFS。

2 Memstore的各種阻塞

  • 經常會遇到性能問題,寫操作被Block住了,其實大部分情況只要了解MemStore的刷寫機制和HFile的合並機制后,就可以着手解決寫操作被Block住的問題。

2.1 數據刷寫時機一(hbase.hregion.memstore.flush.size)

  • 當Memstore占用的內存大小達到hbase.hregion.memstore.flush.size的配置值的時候就會觸發一次刷寫,生產一個HFile。

    悖論 :但是問題來了,因為MemStore的刷寫存在一個定期檢查時間,有時候可能數據增長速度太快,在還未達到檢查時間之前,數據就達到了hbase.hregion.memstore.flush.size的好幾倍,從而被阻塞住了。

2.2 memstore阻塞情況一

  • hbase.hregion.memstore.flush.size 默認閾值是128MB

  • hbase.hregion.memstore.block.multiplier:是一個倍數,默認是4。

  • 上面兩個數的乘積默認為512M,因為MemStore的刷寫存在一個定期檢查時間,在下一次刷寫檢查到來之前若達到了這個閾值,就會立即觸發刷寫,同時阻塞住所有的寫入該Store的寫請求。

2.3 數據刷寫時機二 (globalMemStoreSize)

  • globalMemStoreLimitLowMarkPercent:

    全局的memstore刷寫下限,過去通過配置hbase.regionserver.global.memstore.lowerLimit來定義,現在統一改成: hbase.regionserver.global.memstore.size.lower.limit。該配置項是一個百分比,所以取值在0.0-1.0,默認是0.95。

  • globalMemStoreSize表示全局memstore容量,這個值計算方法如下:

       hbase_heapsize(Regionserver 占用堆內存大小)*hbase.regionserver.global.memstore.size
    復制代碼

    hbase.regionserver.global.memstore.size的默認值是0.4。

    一旦達到這個閾值:

      regionserverHeapSize*
      hbase.regionserver.global.memstore.size*
      hbase.regionserver.global.memstore.size.lower.limit
    復制代碼

    就會觸發一次強制的刷寫。

2.4 memstore阻塞情況二(global.memstore.size):

當hbase_heapsize(Regionserver 占用堆內存大小)*hbase.regionserver.global.memstore.size 大小達到閾值時,就會阻塞整個HBase集群的寫入。

舉例:hBase堆內存的大小為16GB,hbase.regionserver.global.memstore.size是0.4
  ,hbase.regionserver.global.memstore.lowerLimit為0.95
  ,那么觸發刷寫的閾值為:
         16*0.4*0.95=6.08
         
舉例:hBase堆內存的大小為16GB,hbase.regionserver.global.memstore.size是
    0.4,hbase.regionserver.global.memstore.lowerLimit為0.95
    那么觸發阻塞的閾值為:
         16*0.4=6.4
真實案例:hbase_heapsize(Regionserver
占用堆內存大小)配置太小,數據沒怎么寫入就出現寫不進去了。
復制代碼

2.5 數據刷寫時機三 (WAL的數量大於maxLogs)

WAL的數量大於maxLogs時,也會觸發一次刷寫,不過不會發生阻塞事件,倒是會警告一下。該參數其實新版本已經不需要進行設置了,最大就是32,也可以更小,根據hbase.regionserver.global.memstore.size來決定:

   Math.max(32,(regionserverHeapSize*memstoreSizeRatio*2/logRollSize))
復制代碼

2.6 數據刷寫時機四(自動刷寫間隔)

hbase.regionserver.optionalcacheflushinterval:表示memstore的刷寫間隔,默認值是3600000,即1個小時。如果設定為0,則意味着關閉自動刷寫。

2.7 數據刷寫時機五(手動刷寫)

API:

  • flush(TableName tableName):對單表進行刷寫。
  • flushRegion(byte[] regionName):對單個Region進行刷寫。

HBase Shell:

  • flush ‘tablename’

  • flush 'regionname'


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM