1. 程式人生 > >Hbase架構與原理

Hbase架構與原理

HBase是Apache Hadoop中的一個子專案,Hbase依託於Hadoop的HDFS作為最基本儲存基礎單元,通過使用hadoop的DFS工具就可以看到這些這些資料儲存資料夾的結構,還可以通過Map/Reduce的框架(演算法)對HBase進行操作

一、   hbase架構

 1.概述。

HBase是Apache Hadoop的資料庫,能夠對大型資料提供隨機、實時的讀寫訪問。HBase的目標是儲存並處理大型的資料。HBase是一個開源的,分散式的,多版本的,面向列的儲存模型。它儲存的是鬆散型資料。

上圖是hadoop的生態系統描述,hadoop所有應用都是構建於hdfs(它提供高可靠的底層儲存支援,幾乎已經成為分散式檔案儲存系統事實上的工業標準)之上的分散式列儲存系統,主要用於海量結構化資料儲存。

HBase是一種NoSQL資料庫. NoSQL是一個通用詞表示資料庫不是RDBMS ,後者支援 SQL 作為主要訪問手段。有許多種 NoSQL 資料庫: BerkeleyDB 是本地 NoSQL 資料庫例子, 而 HBase 是大型分散式資料庫。 技術上來說, HBase 更像是"資料儲存(Data Store)" 多於 "資料庫(Data Base)"。因為缺少很多RDBMS特性, 如列型別,第二索引,觸發器,高階查詢語言等

然而, HBase 有許多特徵同時支援線性化和模組化擴充。 HBase 叢集通過增加RegionServers進行擴充。 它可以放在普通的伺服器中。例如,如果叢集從10個擴充到20個RegionServer,儲存空間和處理容量都同時翻倍。 RDBMS 也能很好擴充, 但僅對一個點 - 特別是對一個單獨資料庫伺服器的大小 - 同時,為了更好的效能,需要特殊的硬體和儲存裝置。Hbase特性:

強一致性讀寫: HBase 不是 "最終一致性(eventually consistent)" 資料儲存. 這讓它很適合高速計數聚合類任務。

自動分片(Automatic sharding):HBase 表通過region分佈在叢集中。資料增長時,region會自動分割並重新分佈。

RegionServer 自動故障轉移

Hadoop/HDFS 整合: HBase 支援本機外HDFS 作為它的分散式檔案系統。

MapReduce: HBase 通過MapReduce支援大併發處理, HBase 可以同時做源和目標.

Java 客戶端 API: HBase 支援易於使用的 Java API 進行程式設計訪問.

Thrift/REST API:HBase 也支援Thrift和 REST 作為非Java 前端.

Block Cache 和 Bloom Filters: 對於大容量查詢優化, HBase支援 Block Cache 和 Bloom Filters。

運維管理: HBase提供內建網頁用於運維視角和JMX 度量.

前文提到Hbase是一個列式儲存的資料庫,那麼什麼是列式儲存,它與傳統的RDBMS採用的行式儲存又有什麼區別?列儲存不同於傳統的關係型資料庫,其資料在表中是按行儲存的,列方式所帶來的重要好處之一就是,由於查詢中的選擇規則是通過列來定義的,因此整個資料庫是自動索引化的。按列儲存每個欄位的資料聚集儲存,在查詢只需要少數幾個欄位的時候,能大大減少讀取的資料量,一個欄位的資料聚集儲存,那就更容易為這種聚集儲存設計更好的壓縮/解壓演算法。這張圖講述了傳統的行儲存和列儲存的區別:

 2.hbase架構

注:準確的說位於上圖下半部分的組建應該是hdfs而非hadoop,hbase並不依賴於hadoop,但是它構建於hdfs之上。

ZookeeperZookeeper Quorum儲存-ROOT-表地址、HMaster地址
HRegionServer把自己以Ephedral方式註冊到Zookeeper中,HMaster隨時感知各個HRegionServer的健康狀況
Zookeeper避免HMaster單點問題
HMaster
HMaster沒有單點問題,HBase中可以啟動多個HMaster,通過Zookeeper的MasterElection機制保證總有一個Master在執行
主要負責Table和Region的管理工作:
1 管理使用者對錶的增刪改查操作
2 管理HRegionServer的負載均衡,調整Region分佈
3 Region Split後,負責新Region的分佈
4 在HRegionServer停機後,負責失效HRegionServer上Region遷移

HRegionServerHBase中最核心的模組,主要負責響應使用者I/O請求,向HDFS檔案系統中讀寫資料

HRegionServer管理一些列HRegion物件;
每個HRegion對應Table中一個Region,HRegion由多個HStore組成;
每個HStore對應Table中一個Column Family的儲存;
Column Family就是一個集中的儲存單元,故將具有相同IO特性的Column放在一個Column Family會更高效

HStoreHBase儲存的核心。由MemStore和StoreFile組成。
MemStore是Sorted Memory Buffer。使用者寫入資料的流程:

Client寫入 -> 存入MemStore,一直到MemStore滿 -> Flush成一個StoreFile,直至增長到一定閾值 -> 出發Compact合併操作 -> 多個StoreFile合併成一個StoreFile,同時進行版本合併和資料刪除 -> 當StoreFiles Compact後,逐步形成越來越大的StoreFile ->單個StoreFile大小超過一定閾值後,觸發Split操作,把當前Region Split成2個Region,Region會下線,新Split出的2個孩子Region會被HMaster分配到相應的HRegionServer 上,使得原先1個Region的壓力得以分流到2個Region上
由此過程可知,HBase只是增加資料,所有的更新和刪除操作,都是在Compact階段做的,所以,使用者寫操作只需要進入到記憶體即可立即返回,從而保證I/O高效能。

HLog引入HLog原因:
在分散式系統環境中,無法避免系統出錯或者宕機,一旦HRegionServer意外退出,MemStore中的記憶體資料就會丟失,引入HLog就是防止這種情況
工作機制:
每 個HRegionServer中都會有一個HLog物件,HLog是一個實現Write Ahead Log的類,每次使用者操作寫入Memstore的同時,也會寫一份資料到HLog檔案,HLog檔案定期會滾動出新,並刪除舊的檔案(已持久化到 StoreFile中的資料)。當HRegionServer意外終止後,HMaster會通過Zookeeper感知,HMaster首先處理遺留的 HLog檔案,將不同region的log資料拆分,分別放到相應region目錄下,然後再將失效的region重新分配,領取到這些region的 HRegionServer在Load Region的過程中,會發現有歷史HLog需要處理,因此會Replay HLog中的資料到MemStore中,然後flush到StoreFiles,完成資料恢復。

HBase儲存格式HBase中的所有資料檔案都儲存在Hadoop HDFS檔案系統上,格式主要有兩種:
1 HFile HBase中KeyValue資料的儲存格式,HFile是Hadoop的二進位制格式檔案,實際上StoreFile就是對HFile做了輕量級包裝,即StoreFile底層就是HFile
2 HLog File,HBase中WAL(Write Ahead Log) 的儲存格式,物理上是Hadoop的Sequence File

HFile

HFile檔案不定長,長度固定的塊只有兩個:Trailer和FileInfo
Trailer中指標指向其他資料塊的起始點
File Info中記錄了檔案的一些Meta資訊,例如:AVG_KEY_LEN,AVG_VALUE_LEN, LAST_KEY, COMPARATOR, MAX_SEQ_ID_KEY等
Data Index和Meta Index塊記錄了每個Data塊和Meta塊的起始點
Data Block是HBase I/O的基本單元,為了提高效率,HRegionServer中有基於LRU的Block Cache機制
每個Data塊的大小可以在建立一個Table的時候通過引數指定,大號的Block有利於順序Scan,小號Block利於隨機查詢
每個Data塊除了開頭的Magic以外就是一個個KeyValue對拼接而成, Magic內容就是一些隨機數字,目的是防止資料損壞

HFile裡面的每個KeyValue對就是一個簡單的byte陣列。這個byte數組裡麵包含了很多項,並且有固定的結構。

KeyLength和ValueLength:兩個固定的長度,分別代表Key和Value的長度
Key部分:Row Length是固定長度的數值,表示RowKey的長度,Row 就是RowKey
Column Family Length是固定長度的數值,表示Family的長度
接著就是Column Family,再接著是Qualifier,然後是兩個固定長度的數值,表示Time Stamp和Key Type(Put/Delete)
Value部分沒有這麼複雜的結構,就是純粹的二進位制資料

HLog檔案就是一個普通的Hadoop Sequence File,Sequence File 的Key是HLogKey物件,HLogKey中記錄了寫入資料的歸屬資訊,除了table和region名字外,同時還包括 sequence number和timestamp,timestamp是“寫入時間”,sequence number的起始值為0,或者是最近一次存入檔案系統中sequence number。
HLog Sequece File的Value是HBase的KeyValue物件,即對應HFile中的KeyValue

 3.什麼時候應該使用hbase

在學習一門新技術的時候首先需要明白,我們到底應該在什麼時候使用它,然後才是怎麼去使用它,Hbase並不適合所有問題。

首先,確信有足夠多資料,如果有上億或上千億行資料,HBase是很好的備選。如果只有上千或上百萬行,則用傳統的RDBMS可能是更好的選擇。因為所有資料可以在一兩個節點儲存,叢集其他節點可能閒置。

其次,確信可以不依賴所有RDBMS的額外特性 (e.g., 列資料型別, 第二索引,事物,高階查詢語言等.) 一個建立在RDBMS上應用,如不能僅通過改變一個JDBC驅動移植到HBase。相對於移植, 需考慮從RDBMS 到 HBase是一次完全的重新設計。

第三, 確信你有足夠硬體。甚至 HDFS 在小於5個數據節點時,幹不好什麼事情 (根據如HDFS 塊複製具有預設值 3), 還要加上一個NameNode.

HBase 能在單獨的筆記本上執行良好。但這應僅當成開發配置。

4.目錄表(.meta.和-root-)

-ROOT- 儲存 .META. 表存在哪裡的蹤跡. -ROOT- 表結構如下:

Key:

.META. region key (.META.,,1)

Values:

info:regioninfo (序列化.META.的 HRegionInfo 例項 )

info:server ( 儲存 .META.的RegionServer的server:port)

info:serverstartcode ( 儲存 .META.的RegionServer程序的啟動時間)

.META. 儲存系統中所有region列表。 .META.表結構如下:

Key:

Region key 格式 ([table],[region start key],[region id])

Values:

info:regioninfo (序列化.META.的 HRegionInfo 例項 )

info:server ( 儲存 .META.的RegionServer的server:port)

info:serverstartcode ( 儲存 .META.的RegionServer程序的啟動時間)

以上是官網文件對於.meta.和-root-的描述,簡而言之,-root-中儲存了.meta.的位置,而在.meta.中儲存了具體資料(region)的儲存位置。如圖:

Zookeeper中記錄了-ROOT-表的location
客戶端訪問資料的流程:
Client -> Zookeeper -> -ROOT- -> .META.-> 使用者資料表
多次網路操作,不過client端有cache快取

a.    啟動時序

1.啟動時主伺服器呼叫AssignmentManager.

2.AssignmentManager 在META中查詢已經存在的區域分配。

3.如果區域分配還有效(如 RegionServer 還線上),那麼分配繼續保持。

4.如果區域分配失效,LoadBalancerFactory 被呼叫來分配區域。 DefaultLoadBalancer 將隨機分配區域到RegionServer.

5.META 隨RegionServer 分配更新(如果需要) , RegionServer 啟動區域開啟程式碼(RegionServer 啟動時程序)

b.故障轉移

當regionServer故障退出時:

1.區域立即不可獲取,因為區域伺服器退出。

2.主伺服器會檢測到區域伺服器退出。

3.區域分配會失效並被重新分配,如同啟動時序。

5.預寫日誌(wal)

每個RegionServer會將更新(Puts, Deletes)先記錄到預寫日誌中(WAL),然後將其更新在StoreMemStore裡面。這樣就保證了HBase的寫的可靠性。如果沒有WAL,當RegionServer宕掉的時候,MemStore還沒有flush,StoreFile還沒有儲存,資料就會丟失。HLog 是HBase的一個WAL實現,一個RegionServer有一個HLog例項。

WAL 儲存在HDFS 的 /hbase/.logs/ 裡面,每個region一個檔案。

二、   資料模型

1.概念檢視

以bigTable論文中的例子來說明,有一個名為webtable的表,包含兩個列族:contents和anchor.在這個例子裡面,anchor有兩個列 (anchor:cssnsi.com,anchor:my.look.ca),contents僅有一列(contents:html)

Row Key

Time Stamp

ColumnFamily contents

ColumnFamily anchor

"com.cnn.www"

t9

anchor:cnnsi.com = "CNN"

"com.cnn.www"

t8

anchor:my.look.ca = "CNN.com"

"com.cnn.www"

t6

contents:html = "<html>..."

"com.cnn.www"

t5

contents:html = "<html>..."

"com.cnn.www"

t3

contents:html = "<html>..."

RowKey:行鍵,是表中每條記錄的“主鍵”,方便快速查詢,Rowkey的設計非常重要。
Column Family:列族,擁有一個名稱(string),包含一個或者多個相關列
Column:屬於某一個columnfamily,每條記錄可動態新增
Version Number:型別為Long,預設值是系統時間戳,可由使用者自定義
Value(Cell):一個cell由familyName:columnName唯一定義

2.物理檢視

儘管在概念視圖裡,表可以被看成是一個稀疏的行的集合。但在物理上,它的是區分列族 儲存的。新的columns可以不經過宣告直接加入一個列族.

Row Key

Time Stamp

Column Family anchor

"com.cnn.www"

t9

anchor:cnnsi.com = "CNN"

"com.cnn.www"

t8

anchor:my.look.ca = "CNN.com"

Row Key

Time Stamp

ColumnFamily "contents:"

"com.cnn.www"

t6

contents:html = "<html>..."

"com.cnn.www"

t5

contents:html = "<html>..."

"com.cnn.www"

t3

contents:html = "<html>..."

值得注意的是在上面的概念檢視中空白cell在物理上是不儲存的,因為根本沒有必要儲存。因此若一個請求為要獲取t8時間的contents:html,他的結果就是空。相似的,若請求為獲取t9時間的anchor:my.look.ca,結果也是空。但是,如果不指明時間,將會返回最新時間的行,每個最新的都會返回。例如,如果請求為獲取行鍵為"com.cnn.www",沒有指明時間戳的話,活動的結果是t6下的contents:html,t9下的anchor:cnnsi.com和t8下anchor:my.look.ca。

對於hbase我一直有一個疑問,在hbase提供了修改和刪除的介面,但是hdfs本身很難實現修改和刪除(可以將檔案塊從hdfs中下載,進行修改再上傳),那麼hbase是如何實現快速的刪除與修改呢?實際上在HBase中,修改和刪除資料都是增加1個新版本的資料(時間戳為最新),舊版本的資料並沒有發生變化,而實際上的修改和刪除是在Hfile的合併階段實現的。

三、   Hbase優化

1.    預先分割槽

預設情況下,在建立 HBase 表的時候會自動建立一個 Region 分割槽,當匯入資料的時候,所有的 HBase 客戶端都向這一個 Region 寫資料,直到這個 Region 足夠大了才進行切分。一種可以加快批量寫入速度的方法是通過預先建立一些空的 Regions,這樣當資料寫入 HBase 時,會按照 Region 分割槽情況,在叢集內做資料的負載均衡。

2.    Rowkey優化

HBase 中 Rowkey 是按照字典序儲存,因此,設計 Rowkey 時,要充分利用排序特點,將經常一起讀取的資料儲存到一塊,將最近可能會被訪問的資料放在一塊。

此外,Rowkey 若是遞增的生成,建議不要使用正序直接寫入 Rowkey,而是採用 reverse 的方式反轉Rowkey,使得 Rowkey 大致均衡分佈,這樣設計有個好處是能將 RegionServer 的負載均衡,否則容易產生所有新資料都在一個 RegionServer 上堆積的現象,這一點還可以結合 table 的預切分一起設計。

3.    減少列族數量

不要在一張表裡定義太多的 ColumnFamily。目前 Hbase 並不能很好的處理超過 2~3 個 ColumnFamily 的表。因為某個 ColumnFamily 在 flush 的時候,它鄰近的 ColumnFamily 也會因關聯效應被觸發 flush,最終導致系統產生更多的 I/O。

4.    快取策略

建立表的時候,可以通過 HColumnDescriptor.setInMemory(true) 將表放到 RegionServer 的快取中,保證在讀取的時候被 cache 命中。

5.    設定儲存生命期

建立表的時候,可以通過 HColumnDescriptor.setTimeToLive(int timeToLive) 設定表中資料的儲存生命期,過期資料將自動被刪除。

6.    硬碟配置

每臺 RegionServer 管理 10~1000 個 Regions,每個 Region 在 1~2G,則每臺 Server 最少要 10G,最大要1000*2G=2TB,考慮 3 備份,則要 6TB。方案一是用 3 塊 2TB 硬碟,二是用 12 塊 500G 硬碟,頻寬足夠時,後者能提供更大的吞吐率,更細粒度的冗餘備份,更快速的單盤故障恢復。

7.    分配合適的記憶體給RegionServer服務

在不影響其他服務的情況下,越大越好。例如在 HBase 的 conf 目錄下的 hbase-env.sh 的最後新增 export HBASE_REGIONSERVER_OPTS="-Xmx16000m$HBASE_REGIONSERVER_OPTS”

其中 16000m 為分配給 RegionServer 的記憶體大小。

8.    寫資料的備份數

備份數與讀效能成正比,與寫效能成反比,且備份數影響高可用性。有兩種配置方式,一種是將 hdfs-site.xml拷貝到 hbase 的 conf 目錄下,然後在其中新增或修改配置項 dfs.replication 的值為要設定的備份數,這種修改對所有的 HBase 使用者表都生效,另外一種方式,是改寫 HBase 程式碼,讓 HBase 支援針對列族設定備份數,在建立表時,設定列族備份數,預設為 3,此種備份數只對設定的列族生效。

9.    WAL(預寫日誌)

可設定開關,表示 HBase 在寫資料前用不用先寫日誌,預設是開啟,關掉會提高效能,但是如果系統出現故障(負責插入的 RegionServer 掛掉),資料可能會丟失。配置 WAL 在呼叫 JavaAPI 寫入時,設定 Put 例項的WAL,呼叫 Put.setWriteToWAL(boolean)。

10. 批量寫

HBase 的 Put 支援單條插入,也支援批量插入,一般來說批量寫更快,節省來回的網路開銷。在客戶端呼叫JavaAPI 時,先將批量的 Put 放入一個 Put 列表,然後呼叫 HTable 的 Put(Put 列表) 函式來批量寫。

11. 客戶端一次從伺服器拉取的數量

通過配置一次拉去的較大的資料量可以減少客戶端獲取資料的時間,但是它會佔用客戶端記憶體。有三個地方可進行配置:

1)在 HBase 的 conf 配置檔案中進行配置 hbase.client.scanner.caching;

2)通過呼叫 HTable.setScannerCaching(intscannerCaching) 進行配置;

3)通過呼叫 Scan.setCaching(intcaching) 進行配置。三者的優先順序越來越高。

12. RegionServer的請求處理I/O執行緒數

較少的 IO 執行緒適用於處理單次請求記憶體消耗較高的 Big Put 場景 (大容量單次 Put 或設定了較大 cache 的Scan,均屬於 Big Put) 或 ReigonServer 的記憶體比較緊張的場景。

較多的 IO 執行緒,適用於單次請求記憶體消耗低,TPS 要求 (每秒事務處理量 (TransactionPerSecond)) 非常高的場景。設定該值的時候,以監控記憶體為主要參考。

在 hbase-site.xml 配置檔案中配置項為 hbase.regionserver.handler.count。

13. Region的大小設定

配置項為 hbase.hregion.max.filesize,所屬配置檔案為 hbase-site.xml.,預設大小 256M。

在當前 ReigonServer 上單個 Reigon 的最大儲存空間,單個 Region 超過該值時,這個 Region 會被自動 split成更小的 Region。小 Region 對 split 和 compaction 友好,因為拆分 Region 或 compact 小 Region 裡的StoreFile 速度很快,記憶體佔用低。缺點是 split 和 compaction 會很頻繁,特別是數量較多的小 Region 不停地split, compaction,會導致叢集響應時間波動很大,Region 數量太多不僅給管理上帶來麻煩,甚至會引發一些Hbase 的 bug。一般 512M 以下的都算小 Region。大 Region 則不太適合經常 split 和 compaction,因為做一次 compact 和 split 會產生較長時間的停頓,對應用的讀寫效能衝擊非常大。

此外,大 Region 意味著較大的 StoreFile,compaction 時對記憶體也是一個挑戰。如果你的應用場景中,某個時間點的訪問量較低,那麼在此時做 compact 和 split,既能順利完成 split 和 compaction,又能保證絕大多數時間平穩的讀寫效能。compaction 是無法避免的,split 可以從自動調整為手動。只要通過將這個引數值調大到某個很難達到的值,比如 100G,就可以間接禁用自動 split(RegionServer 不會對未到達 100G 的 Region 做split)。再配合 RegionSplitter 這個工具,在需要 split 時,手動 split。手動 split 在靈活性和穩定性上比起自動split 要高很多,而且管理成本增加不多,比較推薦 online 實時系統使用。記憶體方面,小 Region 在設定memstore 的大小值上比較靈活,大 Region 則過大過小都不行,過大會導致 flush 時 app 的 IO wait 增高,過小則因 StoreFile 過多影響讀效能。

14. 作業系統引數

Linux系統最大可開啟檔案數一般預設的引數值是1024,如果你不進行修改併發量上來的時候會出現“Too Many Open Files”的錯誤,導致整個HBase不可執行,你可以用ulimit -n 命令進行修改,或者修改/etc/security/limits.conf和/proc/sys/fs/file-max 的引數,具體如何修改可以去Google 關鍵字 “linux limits.conf ”

15. Jvm配置

修改 hbase-env.sh 檔案中的配置引數,根據你的機器硬體和當前作業系統的JVM(32/64位)配置適當的引數

HBASE_HEAPSIZE 4000 HBase使用的 JVM 堆的大小

HBASE_OPTS "‐server ‐XX:+UseConcMarkSweepGC"JVM GC 選項

HBASE_MANAGES_ZKfalse 是否使用Zookeeper進行分散式管理

16. 持久化

重啟作業系統後HBase中資料全無,你可以不做任何修改的情況下,建立一張表,寫一條資料進行,然後將機器重啟,重啟後你再進入HBase的shell中使用 list 命令檢視當前所存在的表,一個都沒有了。是不是很杯具?沒有關係你可以在hbase/conf/hbase-default.xml中設定hbase.rootdir的值,來設定檔案的儲存位置指定一個資料夾,例如:<value>file:///you/hbase-data/path</value>,你建立的HBase中的表和資料就直接寫到了你的磁碟上,同樣你也可以指定你的分散式檔案系統HDFS的路徑例如:hdfs://NAMENODE_SERVER:PORT/HBASE_ROOTDIR,這樣就寫到了你的分散式檔案系統上了。

17. 緩衝區大小

hbase.client.write.buffer

這個引數可以設定寫入資料緩衝區的大小,當客戶端和伺服器端傳輸資料,伺服器為了提高系統執行效能開闢一個寫的緩衝區來處理它,這個引數設定如果設定的大了,將會對系統的記憶體有一定的要求,直接影響系統的效能。

18. 掃描目錄表

hbase.master.meta.thread.rescanfrequency

定義多長時間HMaster對系統表 root 和 meta 掃描一次,這個引數可以設定的長一些,降低系統的能耗。

19. split/compaction時間間隔

hbase.regionserver.thread.splitcompactcheckfrequency

這個引數是表示多久去RegionServer伺服器執行一次split/compaction的時間間隔,當然split之前會先進行一個compact操作.這個compact操作可能是minorcompact也可能是major compact.compact後,會從所有的Store下的所有StoreFile檔案最大的那個取midkey.這個midkey可能並不處於全部資料的mid中.一個row-key的下面的資料可能會跨不同的HRegion。

20. 快取在JVM堆中分配的百分比

hfile.block.cache.size

指定HFile/StoreFile 快取在JVM堆中分配的百分比,預設值是0.2,意思就是20%,而如果你設定成0,就表示對該選項遮蔽。

21. ZooKeeper客戶端同時訪問的併發連線數

hbase.zookeeper.property.maxClientCnxns

這項配置的選項就是從zookeeper中來的,表示ZooKeeper客戶端同時訪問的併發連線數,ZooKeeper對於HBase來說就是一個入口這個引數的值可以適當放大些。

22. memstores佔用堆的大小引數配置

hbase.regionserver.global.memstore.upperLimit

在RegionServer中所有memstores佔用堆的大小引數配置,預設值是0.4,表示40%,如果設定為0,就是對選項進行遮蔽。

23. Memstore中快取寫入大小

hbase.hregion.memstore.flush.size

Memstore中快取的內容超過配置的範圍後將會寫到磁碟上,例如:刪除操作是先寫入MemStore裡做個標記,指示那個value, column 或 family等下是要刪除的,HBase會定期對儲存檔案做一個major compaction,在那時HBase會把MemStore刷入一個新的HFile儲存檔案中。如果在一定時間範圍內沒有做major compaction,而Memstore中超出的範圍就寫入磁碟上了。