`
san_yun
  • 浏览: 2594542 次
  • 来自: 杭州
文章分类
社区版块
存档分类
最新评论

HBase Memstore理解笔记

阅读更多

HBase BlockCache理解笔记

 

HBase read path. Data is reconciled from the BlockCache, the MemStore, and the HFiles to give the client an up-to-date view of the row(s) it asked for.

 

 

HBase Memstore理解笔记

 

当RegionServer收到了写请求,它会把请求指到相应的Region。每个Region都存储一定数目的行。每行数据可被分成多个列族(column family)。每个column family的数据被存储在HStore中,而HStore由Memstore和若干个HFile组成。Memstore是在RegionServer的内存中,而HFile被写入HDFS。当写请求被处理时,数据首先被写入Memstore,然后,当某个门限满足了之后,Memstore的数据被flush到HFile里。

 

使用Memstore方案的主要原因就是HBase存储数据必须要以row排序,这样才能高效的查询。而DFS的设计是针对连续读写的,不允许修改文件,所以HBase就不能高效的把收到的数据写入磁盘,因为收到的写请求一般都是无序的,直接写入磁盘会导致磁盘的数据也无序,就无法高效查询了。为了解决这个问题,HBase把收到的写请求换存在内存中(也就是Memstore),在flush之前将缓存的数据排序,然后将数据快速的批量顺序写入HDFS中。注意,实际中的HFile可并不只是简单的若干行有序数据。

 

除了解决了无序问题,Memstore还有以下好处:

 

1.它可以作为内存中的cache,保存了最近新添加/修改的数据。当新写入数据的访问频率比旧数据多很多的情况下,这是一个很有用的特性。

2.把写请求缓存起来批处理是一个很经典的优化手段,例如,假如对于每个cell,只需要保存一个版本,那么当memstore中存在同个cell的多个更新的话,就只需要把最新的修改写入HFile即可。

 

需要注意的一点是:每个column family的memstore的每次flush都会创建一个HFile。

读请求就简单多了:HBase首先检查memstore里是否有要读的数据,然后去HFile中查找,最后把merge后的结果返回给client。

 

Frequent Memstore Flushes

如果写请求的量非常大,大到HBase都来不及做flush,那么HBase可能就会block写操作了,为了避免这种情况,提高flush的频率是一种显而易见的方法。但是,这会影响读操作的性能,还会给集群带来额外的压力。

每当Memstore flush的时候,每个CF就会创建一个HFile。频繁的flush就会创建过多的HFile。这样HBase在处理读操作的时候就会查找很多HFile,导致读性能无法容忍。为了避免打开过多的HFile以至于影响读请求的性能,HBase采取了合并HFile的解决方案。HBase会周期性的将多个小HFile合并为一个大的HFile。很明显,Memstore flush创建的小文件越多,给系统带来的负载也就越大。更严重的是,合并HFile的操作和其他服务是同步进行的,当HBase觉得合并HFile的速度不够快,它也会block写操作,这是谁都不希望看到的。

Hint:监控Compaction Queue的size。一旦它持续增长,就需要采取措施以防出现问题。

 

Multiple Column Families & Memstore Flush

所有CF的memstore都是同时flush的。这意味着,每次flush都会创建N个HFile,一个CF一个。因此,如果各个CF的数据量不平衡,就会导致创建过多的HFile,因为只要有一个CF的memstore达到了门限,所有的CF都要做flush动作。这样也会导致过多的HFile,影响集群的性能。

Hint: 很多情况下,只有一个CF是最佳设计。

 

HLog (WAL) Size & Memstore Flush

HLog(WAL)包含了RegionServer上所有已经写入Memstore但是还没有flush到HFile的写操作。因为Memstore中的数据并没有持久化,我们需要WAL,当RegionServer挂了的时候,可以根据WAL恢复数据。

当HLog,也就是HBase的WAL,逐渐的变得很大了,复现操作就会消耗很多的时间。因此HBase会设置一个WAL大小的门限,当达到这个门限的时候,就会命令Memstore做flush,这样可以减小WAL。所以当HLog过大了,也会触发Memstore的flush。那么就要注意了,到底是Memstore的门限优先级高还是HLog的优先级高呢?答案是前者,正确的配置应该是让Memstore先达到容量门限,否则的话,每次因为WAL大小超限而进行flush,不就无法充分使用Memstore的资源了么。况且,WAL超标有可能会导致很多个Region进行memstore flush,这并不是触发memstore flush的最佳方式。

 

Hint: 保证hbase.regionserver.hlog.blocksize * hbase.regionserver.maxlogs略大于hbase.regionserver.global.memstore.lowerLimit * HBASE_HEAPSIZE.

 

Compression & Memstore Flush

压缩存储在HFile里的数据是一个好习惯。不仅可以节约空间,也可以显著的减少磁盘和网络的IO。当Memstore flush的时候,数据会被压缩。压缩不能拖慢flush太多,否则会遇到很多本文提到的问题,比如由于Memstore过大而block写操作。

Hint: 在选择压缩类型的时候,应该更看重压缩速度而不是压缩比率,SNAPPY是一个好选择。

 

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics