HBase豆知识

时间:2022-07-23
本文章向大家介绍HBase豆知识,主要内容包括其使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。

关于Phoenix的使用

Phoenix带来的SQL on HBase易用性相比,它带来的负面影响也是巨大的, 大表Join大表,或者全表OrderBy等消耗的资源随数据量呈至少线性增长, 并发直线下降,甚至低到只有百级别,扩容带来的收益下降很快。 另外,Phoenix表查询通过多个独立协调器(Query Server),互相不管对方, 玩命占用HBase资源,在高并发的大查询下就会容易造成HBase整个集群过载。 而像Presto系统所有的请求都是走同一个协调器,可以总控资源使用,优雅的处理过载。 让现有HBase集群聚焦在线KV Store,聚焦作为在线业务的温存储层。

Phoenix针对KV系统提供的 SaltBucket、SkipScan、Aggregation、列合并等特性可以看做是对HBase的最佳实践。 云厂商今后可能从两个方面来改善Phoenix,一个是SQL的分离执行,Scale 无关的本地编译执行,Scale 相关的自动走DLA编译执行;另一个是像Presto那样资源调度的统一处理。

写入数据

HBase写入是先写WAL,然后写内存,如果宕机了,内存里的数据会丢失,需要回放log恢复数据之后,region才能上线,这个是需要时间的一般是3到5分钟。 而升级是不要这个过程的,region会先移走这个时间是百ms级别的。

phoniex 有自己的一套 编码格式, 列族、列名转化方式。 直接读phoenix原生的表, 需要自己去解析字段类型

连接数

hbase zk针对某个ip机器上连接有个上限:200,整体上HBase的连接数没有上限,据官方说是几十万级别的。

范围读

范围读说是的是 scan[startkey, endkey],在开始RK与结束RK顺之间按照字典顺序扫描数据。 一般一次扫描,不超过200为好,超过的话,可以设计为多次迭代的形式继续扫描。

删除表

执行删除表(disable->drop操作),表并不是立即删除,而是先进archive目录保留一小段时间, 所以,空间水位线不会立即下来。

Region Replica(HBASE-10070)特性

在HBase最初的架构中,一个Region只能被部署在一个RegionServer中,它的数据多副本交由HDFS来保障。从1.0版本开始,HBase有了Region Replica(HBASE-10070)特性,该特性允许将一个Region部署在多个RegionServer中来提升读取的可用性,但多Region副本之间的数据却不是实时同步的,因此不具备生产能力。

现存系统针对结构化数据存储与查询的一些痛点问题

结构化数据的存储,通常包含如下两种方式:

静态数据通常以Parquet/Carbon/Avro形式直接存放在HDFS中,对于分析场景,这种存储通常是更加适合的。但无论以哪种方式存在于HDFS中,都难以支持单条记录级别的更新,随机读取也并不高效。 可变数据的存储通常选择HBase或者Cassandra,因为它们能够支持记录级别的高效随机读写。但这种存储却并不适合离线分析场景,因为它们在大批量数据获取时的性能较差。 针对HBase而言,有两方面的主要原因:

  • 一、HFile本身的结构定义,它是按行组织数据的,这种格式针对大多数的分析场景,都会带来较大的IO消耗,因为可能会读取很多不必要的数据,相对而言Parquet格式针对分析场景就做了很多优化。
  • 二、由于HBase本身的LSM-Tree架构决定的,HBase的读取路径中,不仅要考虑内存中的数据,同时要考虑HDFS中的一个或多个HFile,较之于直接从HDFS中读取文件而言,这种读取路径是过长的

如上两种存储方式,都存在明显的优缺点: 直接存放于HDFS中,适合离线分析,却不利于记录级别的随机读写。 直接将数据存放于HBase/Cassandra中,适合记录级别的随机读写,对离线分析却不友好。

ROWKEY设计

md5(car_Id).substring(0,4)_carid_timestamp md5的目的是打散,不是唯一

预分区

MD5Hash.getMD5AsHex hexString的假设数据范文是0000-fffff

建表时,指定分区算法,并且做了预分区

create 'prod:iov_passenger_location_history_5m','cf1',{NUMREGIONS => 30, SPLITALGO => 'HexStringSplit'}

NUMREGIONS 为 region的个数,一般按每个region 8~10GB左右来计算region数量,集群规模大,region数量可以适当取大一些。

预分区

HBase可以支持100TB+的表,上万个分区, 建表时先估下数据量,然后指定好合适的分区数,分区数太多也不行,太少就会频繁的split,

SPLITALGO 为 rowkey分割的算法,HBase自带了三种pre-split的算法: HexStringSplit、DecimalStringSplit 和 UniformSplit

各种Split算法适用场景:

  • HexStringSplit: rowkey是十六进制的字符串作为前缀的,这个配合md5前缀用的最多
  • DecimalStringSplit: rowkey是10进制数字字符串作为前缀的
  • UniformSplit: rowkey前缀完全随机

客户端的报错问题

Caused by: java.io.IOException: Call to press-001/10.30.93.78:16020 failed on local exception: org.apache.hadoop.hbase.ipc.FailedServerException: This server is in the failed servers list:  press-001/10.30.93.78/10.30.93.78:16020
    at org.apache.hadoop.hbase.ipc.IPCUtil.wrapException(IPCUtil.java:180)
    at org.apache.hadoop.hbase.ipc.AbstractRpcClient.onCallFinished(AbstractRpcClient.java:390)
    at org.apache.hadoop.hbase.ipc.AbstractRpcClient.access$100(AbstractRpcClient.java:95)
    at org.apache.hadoop.hbase.ipc.AbstractRpcClient$3.run(AbstractRpcClient.java:410)
    at org.apache.hadoop.hbase.ipc.AbstractRpcClient$3.run(AbstractRpcClient.java:406)
    at org.apache.hadoop.hbase.ipc.Call.callComplete(Call.java:103)
    at org.apache.hadoop.hbase.ipc.Call.setException(Call.java:118)
    at org.apache.hadoop.hbase.ipc.AbstractRpcClient.callMethod(AbstractRpcClient.java:423)

hbase.regionserver.port:HBase RegionServer绑定的端口,默认16020