Hbasecompact和split跟踪举例分析

本篇内容主要讲解“Hbase compact和split跟踪举例分析”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“Hbase compact和split跟踪举例分析”吧!

成都创新互联是一家专注网站建设、网络营销策划、微信小程序开发、电子商务建设、网络推广、移动互联开发、研究、服务为一体的技术型公司。公司成立十载以来,已经为近千家轻质隔墙板各业的企业公司提供互联网服务。现在,服务的近千家客户与我们一路同行,见证我们的成长;未来,我们一起分享成功的喜悦。

为了准确了解HBASE内部工作原理,我们需要做一些测试,在大量数据插入的情况下,HBASE内部到底有什么表现?  比如插入速度,  hstore compact,split等相关活动,了解了这些才能更好的维护HBASE系统本身。

此次测试会有几轮,所以测试到哪里就写到哪里,我随便找了一张大概120W来的表,我会写一个mapreduce任务,来读取这张表,再写入另外一个测试表: test2, 没有选择更大的表是因为毕竟整个拷贝是需要时间,通常20分钟-30分钟,太大的表,不太利于跟踪。 拷贝过程,HBASE会针对此表有相关的活动日志,依据日志,我们来看看HBASE到底在干什么。

测试开始, 下面是我的mapreduce任务进度,reduce开始的时间,实际就是写入HBASE的时间,那么从11:36开始,应该HBASE在插入

17/06/29 11:31:41 INFO mapreduce.Job:  map 71% reduce 0%
17/06/29 11:32:07 INFO mapreduce.Job:  map 81% reduce 0%
17/06/29 11:32:08 INFO mapreduce.Job:  map 86% reduce 0%
17/06/29 11:32:19 INFO mapreduce.Job:  map 86% reduce 29%
17/06/29 11:36:07 INFO mapreduce.Job:  map 95% reduce 29%
17/06/29 11:36:11 INFO mapreduce.Job:  map 96% reduce 29%

跟踪日志过程

1.  11:36分日志显示flush一个memstore,大小为129M, 这个和设置的参数值是一样的,hbase.hregion.memstore.flush.size=128M, flush之后,会生产一个hfile,实际文件大小为48.9M, 另外注意最后的compaction requested=false

2017-06-29 11:36:34,505 INFO org.apache.hadoop.hbase.regionserver.HRegion: Flushing 1/1 column families, memstore=129.14 MB
2017-06-29 11:36:36,157 INFO org.apache.hadoop.hbase.regionserver.DefaultStoreFlusher: Flushed, sequenceid=54, memsize=129.1 M, hasBloomFilter=true, into tmp file hdfs://nameservice1/hbase/data/default/test2/786ef51a9c89f0e31073ba8aafc7ef94/.tmp/047e3c0dad4940788b97b203495c1536
2017-06-29 11:36:36,182 INFO org.apache.hadoop.hbase.regionserver.HStore: Added hdfs://nameservice1/hbase/data/default/test2/786ef51a9c89f0e31073ba8aafc7ef94/cf/047e3c0dad4940788b97b203495c1536, entries=644303, sequenceid=54, filesize=48.9 M
2017-06-29 11:36:36,185 INFO org.apache.hadoop.hbase.regionserver.HRegion: Finished memstore flush of ~129.14 MB/135411576, currentsize=36.78 MB/38569776 for region test2,,1498706810880.786ef51a9c89f0e31073ba8aafc7ef94. in 1681ms, sequenceid=54, compaction requested=false

2. 第二次刷新, 注意最后的compaction requested=false,

2017-06-29 11:36:41,766 INFO org.apache.hadoop.hbase.regionserver.DefaultStoreFlusher: Flushed, sequenceid=107, memsize=128.7 M, hasBloomFilter=true, into tmp file hdfs://nameservice1/hbase/data/default/test2/786ef51a9c89f0e31073ba8aafc7ef94/.tmp/57d95a2f46454109b336161e9ae9bc14
2017-06-29 11:36:41,786 INFO org.apache.hadoop.hbase.regionserver.HStore: Added hdfs://nameservice1/hbase/data/default/test2/786ef51a9c89f0e31073ba8aafc7ef94/cf/57d95a2f46454109b336161e9ae9bc14, entries=636412, sequenceid=107, filesize=49.5 M
2017-06-29 11:36:41,788 INFO org.apache.hadoop.hbase.regionserver.HRegion: Finished memstore flush of ~128.74 MB/134994216, currentsize=26.27 MB/27549840 for region test2,,1498706810880.786ef51a9c89f0e31073ba8aafc7ef94. in 1318ms, sequenceid=107, compaction requested=false


3. 第三次刷新, 此时日志明确的表示,要进行合并, 当有3个HFILE的时候,HBASE会合并,这是因为默认我们的参数hbase.hstore.compactionThreshold=3  ,此时发生的是minor合并

2017-06-29 11:36:48,023 INFO org.apache.hadoop.hbase.regionserver.DefaultStoreFlusher: Flushed, sequenceid=160, memsize=128.7 M, hasBloomFilter=true, into tmp file hdfs://nameservice1/hbase/data/default/test2/786ef51a9c89f0e31073ba8aafc7ef94/.tmp/1fa335caa3144c8da5e0ca7697f551cf
2017-06-29 11:36:48,041 INFO org.apache.hadoop.hbase.regionserver.HStore: Added hdfs://nameservice1/hbase/data/default/test2/786ef51a9c89f0e31073ba8aafc7ef94/cf/1fa335caa3144c8da5e0ca7697f551cf, entries=636412, sequenceid=160, filesize=49.9 M
2017-06-29 11:36:48,054 INFO org.apache.hadoop.hbase.regionserver.HRegion: Finished memstore flush of ~128.74 MB/134994216, currentsize=31.53 MB/33059808 for region test2,,1498706810880.786ef51a9c89f0e31073ba8aafc7ef94. in 1343ms, sequenceid=160, compaction requested=true

跟踪HFILE合并, 日志显示,3个文件合并在一起,一共148M,花费的时间为3秒,很显然minor合并的速度还是很快的。

2017-06-29 11:36:48,058 INFO org.apache.hadoop.hbase.regionserver.HStore: Starting compaction of 3 file(s) in cf of test2,,1498706810880.786ef51a9c89f0e31073ba8aafc7ef94. into tmpdir=hdfs://nameservice1/hbase/data/default/test2/786ef51a9c89f0e31073ba8aafc7ef94/.tmp, totalSize=148.3 M

2017-06-29 11:36:51,792 INFO org.apache.hadoop.hbase.regionserver.CompactSplitThread: Completed compaction: Request = regionName=test2,,1498706810880.786ef51a9c89f0e31073ba8aafc7ef94., storeName=cf, fileCount=3, fileSize=148.3 M, priority=7, time=17006286308699473; duration=3sec

4. flush  

5. flush 

6. 要求合并(此时第一个合并之后只有一个文件,加上flush的2个文件,一共3个,达到了合并条件)

7. 要求split (split之后为2个文件)

8. flush

9. 要求合并(之前split为2个文件,加上flush的一个为3个文件,达到合并条件)

10. 要求split

以上是根据日志显示得到的一个跟踪过程。 我们可以看到minor compact速度很快,根据参数设置,每3个文件就会合并一次。 至于major compact由hbase.hregion.majorcompaction来控制,
默认是7天时间,0表示关闭major compact.  所以从理论来讲,minor compact对于一个数据量大的系统,可能时时刻刻在合并, 因为memstore 默认128M可能1分钟就满了,刷出之后产生HFILE,然后达到合并条件就合并。

而split有3个策略,默认是IncreasingToUpperBoundRegionSplitPolicy , 还有KeyPrefixRegionSplitPolicy, ConstantSizeRegionSplitPolicy, 根据规则在128M的时候就应该split,但是实际从日志来看,并没有,后续再做观察。

通常我们会提到手动拆分,也就是关闭自动拆分,从拆分策略来看,只有ConstantSizeRegionSplitPolicy能完全禁止自动拆分,设置这个策略之后,然后修改region的max filesize,比如100G,那么基本就可以关闭自动拆分。


根据以上合并以及拆分理论知识,我们假设有一个系统负载极大,不停的大量数据写入,那么我们可以知道,HBASE内部在不停的合并,达到拆分规则又拆分,又合并,又拆分,周而复始。
在拆分的时候,1个大region拆分成2个小region, 然后修改meta,再online2个小region,  删除大的region. 但是在这过程,我们知道数据还在不停的写入,hbase.hstore.blockingStoreFiles默认为10,这个参数是用来控制当一个region下超过多少个文件就BLOCK更新插入,等待合并结束,问题是这个参数不会一直BLOCK,hbase.hstore.blockingWaitTime 默认90秒,超过这个时间又会放行插入和更新。很显然,出现这种情况之后,小region如果出现了需要split的情况怎么办? 开始的合并还没有结束,大region还没有offline, 小region又要拆分。 

如果出现了上面的情况,我不知道具体HBASE是什么规则,但是我想这是一个极度复杂的处理,简单处理的话只有BLOCK插入和更新,等待合并或者拆分结束。目前我还没找到有完全BLOCK HBASE插入和更新的参数, 所以为了更好管理HBASE, 建议关闭自动拆分,为什么? 不仅仅是为了说SPLIT可能会影响性能,如果说SPLIT会影响,那么合并也会影响,更多的是,拆分和合并我们要有取舍,关闭了自动拆分,人为来控制,那么在HBASE内部仅仅存在合并,至少不会出现上述极度复杂的情况。

最后,如果系统负载极大的时候,rowkey分配不规则,大量线程往一个region写数据,默认单个memstore是128M,最大大小为128*2=256M, 这个时候按照规则会BLOCK写入,甚至出现org.apache.hadoop.hbase.RegionTooBusyException: org.apache.hadoop.hbase.RegionTooBusyException: Above memstore limit  memstoreSize=269744800, blockingMemStoreSize=268435456 之类的错误。  

这里简单说一下memstore block写入规则,默认memstore size=128M,  结合hbase.hregion.memstore.block.multiplier=2 ,也就是说memstore最大大小为256M, 将BLOCK写入,阻止大量写入避免出现outofmemory错误. 上面你看到的above memstore size > 256M.

所以预先分区以及估算写入量就显的非常重要,如果你的系统负载并没有那么大,那么就显的不是那么重要了。

到此,相信大家对“Hbase compact和split跟踪举例分析”有了更深的了解,不妨来实际操作一番吧!这里是创新互联网站,更多相关内容可以进入相关频道进行查询,关注我们,继续学习!


文章题目:Hbasecompact和split跟踪举例分析
文章路径:http://pwwzsj.com/article/jospsj.html