本文主要介绍 Phoenix 对接低延迟业务遇到的问题和解决过程,并在最后列举了几个 Phoenix 应用比较成功的场景,帮助读者更好地将 Phoenix 应用到企业应用中。
背景
HBase 作为一个优秀的分布式数据库,满足了大量 KV 及 Scan 查询的场景,但其 API 语义定义得偏底层,更专注于 Bytes,需要应用层自己维护类型和编码关系,使用门槛偏高。随着公司业务发展,用户对支持海量存储、并且支持 SQL 的 DB 需求越发强烈,所以引入了 Phoenix。
Phoenix 作为将 HBase从NoSQL 向 SQL 的封装,不仅为 HBase 带来了门槛更低的 SQL 语义,也让其支持了聚合查询、salting、二级索引、join 等扩充 HBase 使用范围的功能。随着 Phoenix 版本的更替,以及各种已知 Bug 的 fixed,在稳定性和高可用性上有了很大的提升和进步,越来越多的企业将 Phoenix 实际应用到实际线上业务中,通过从社区获取到反馈社区的迭代,使 Phoenix 成为了一个可靠的开源产品,在简化架构和业务逻辑方面起着重要的积极作用。
Phoenix 原理
了一张 SYSTEM.CATALOG 表维护 SQL 二维表的各列到 HBase ColumnFamily 和 Column 的映射。并且为了减轻 Client 端的任务,利用了 HBase的Observer 和
Endpoint 两个接口,实现了 Scan、UnGroupedAggregate、ServerCaching 等coprossor。
![图1 Phoenix 实现架构 图1 Phoenix 实现架构](https://ipad-cms.csdn.net/cms/attachment/201712/5a26055c11056.png)
图1 Phoenix 实现架构
这样的实现让 HBase 与 Phoenix 结合得更紧密,但是有个致命的缺点,Phoenix 可利用的内存太小。
![图2 HBase RegionServer内存分布图 图2 HBase RegionServer内存分布图](https://ipad-cms.csdn.net/cms/attachment/201712/5a26054e93663.png)
图2 HBase RegionServer 内存分布图
如图2,RegionServer 的 Heap 大致上可以分为三个部分,BlockCache、Memstore 和 Rest。BlockCache 主要负责缓存近期读命令中的 HFile Block,以供下次访问时缩减磁盘 I/O 带来的延迟。Memstore 则负责将近期写入的数据缓存在内存,等到每个 Region 缓存一定量的大小后(默认 128M)再向 HDFS Flush一个HFile,有助于减少 StoreFile 的数量、减小读延迟。最后 Rest 部分负责 RegionServer 的处理逻辑、Compaction 和 Coprossor 等其他事情。 Phoenix 的 Server 部分逻辑就是工作在 Rest 这个部分。
但是要注意的是,生产环境为了更好地提高吞吐性能,BlockCache 和 Memstore 通常会占用整个 RegionServer Heap 的70%到80%,所以留给 Phoenix 的可用内存并不多。