初识 HBase

初识 HBase


HBase简介

对大数据领域有必定了解的小伙伴对HBase应该不会陌生,HBase是Apache基金会开源的一个分布式非关系型数据库,属于Hadoop的组件。它使用Java编写,需运行于HDFS文件系统之上。HBase与Hadoop中的其余组件同样,能够运行在廉价硬件上,并可提供数10亿行 X 数百万列的大数据存储、管理能力,以及随机访问和实时读/写能力。HBase的设计模型参考了Google的Bigtable,能够说是Bigtable的开源实现版本。html

HBase特性

  • 数据容量大,单表能够有百亿行、百万列,数据矩阵横向和纵向两个维度所支持的数据量级都很是具备弹性
  • 多版本,每一列存储的数据能够有多个version
  • 稀疏性,为空的列并不占用存储空间,表能够设计的很是稀疏
  • 读写强一致,非 “最终一致性” 的数据存储,使得它很是适合高速的计算聚合
  • 自动分片,经过Region分散在集群中,当行数增加的时候,Region也会自动的切分和再分配
  • Hadoop/HDFS集成,和HDFS开箱即用,不用太麻烦的衔接。扩展性强,只须要增长DataNode就能够增长存储空间
  • 丰富的“简洁,高效”API,提供了Thrift/REST API,Java API等方式对HBase进行访问
  • 块缓存布隆过滤器,能够高效的列查询优化
  • 操做管理,Hbase提供了内置的web界面来操做,还能够监控JMX指标
  • 高可靠,保证了系统的容错能力,WAL机制使得数据写入时不会由于集群异常而致使写入数据丢失。故HBase选择了CAP中的CP
  • 面向列的存储和权限控制,并支持独立检索,能够动态的增长列
    • 列式存储:其数据在表中是按照某列存储的,这样在查询只须要少数几个字段的时候,能大大减小读取的数据量
  • 高性能,具有海量数据的随机访问和实时读写能力
    • 写方面:底层的 LSM 数据结构和 Rowkey 有序排列等架构上的独特设计,使得HBase具备很是高的写入性能。
    • 读方面:region 切分、主键索引和缓存机制使得HBase在海量数据下具有必定的随机读取性能,针对 Rowkey 的查询可以达到毫秒级别

综上,HBase是一个高可靠、高性能、面向列、可伸缩的分布式数据库,是谷歌Bigtable的开源实现。主要用来存储非结构化和半结构化的松散数据。HBase的目标是处理很是庞大的表,能够经过水平扩展的方式,利用廉价计算机集群处理由超过10亿行数据和数百万列元素组成的数据表。更多内容详见官方文档web

HBase提供的访问接口

类型 特色 场合
Native Java API 最常规和高效的访问方式 适合Hadoop MapReduce做业并行批处理HBase表数据
HBase Shell HBase的命令行工具,最简单的接口 适合管理HBase时使用
Thrift Gateway 利用Thrift序列化技术进行访问,支持C++、PHP、Python等多种语言 适合其余异构系统在线访问HBase表数据
REST Gateway 解除了语言限制,任何语言均可以经过该方式访问HBase 支持REST风格的HTTP API访问HBase
Pig 使用 Pig Latin 流式编程语言来处理HBase中的数据 适合作数据统计
Hive 简单 当须要以相似SQL语言方式来访问HBase的时候

HBase 与 HDFS 的区别

  • HDFS是面向批量的访问模式,其类型为文件系统,存储的是文件类型的数据
  • HBase是面向随机访问和实时读写模式,其类型为数据库服务,存储的是非结构化和半结构化的松散数据
  • HBase 使用 HDFS 做为底层的文件系统,HBase 的数据最终会写到 HDFS 中。就像其余的数据库同样,真正的数据是存储在操做系统里的文件系统中的
  • 打个不恰当的比方:它们的区别就像是Linux文件系统与MongoDB的区别

HBase 与关系数据库的区别

数据类型:数据库

  • 关系数据库采用关系模型,具备丰富的数据类型和存储方式,HBase则采用了更加简单的数据模型,它把数据存储为未经解释的字符串。

数据操做:apache

  • 关系数据库中包含了丰富的操做,其中会涉及复杂的多表链接。HBase操做则不存在复杂的表与表之间的关系,只有简单的插入、查询、删除、清空等,由于HBase在设计上就避免了复杂的表和表之间的关系。因此HBase也就不支持复杂的条件查询,只能是经过行键查询。

存储模式:编程

  • 关系数据库是基于行模式存储的。HBase是基于列存储的,每一个列簇都由几个文件保存,不一样列簇的文件是分离的。而且列簇中的列是能够动态增长的,而关系数据库须要一开始就设计好。除此以外,HBase能够自动切分数据,关系型数据库则须要咱们人工切分数据。

数据索引:json

  • 关系数据库一般能够针对不一样列构建复杂的多个索引,以提升数据访问性能。HBase只有一个索引——行键,经过巧妙的设计,HBase中的全部访问方法,或者经过行键访问,或者经过行键扫描,从而使得整个系统不会慢下来。

数据维护:数组

  • 在关系数据库中,更新操做会用最新的当前值去替换记录中原来的旧值,旧值被覆盖后就不会存在。而在HBase中执行更新操做时,并不会删除数据旧的版本,而是生成一个新的版本,旧有的版本仍然保留。

可伸缩性:浏览器

  • 关系数据库很难实现横向扩展,纵向扩展的空间也比较有限。相反,HBase和BigTable这些分布式数据库就是为了实现灵活的水平扩展而开发的,可以轻易地经过在集群中增长或者减小硬件数量来实现性能的伸缩。

HBase 常见应用场景

  • 存储业务数据:交通工具GPS信息,司机点位信息,订单信息,物流信息,设备访问信息,用户行为信息等
  • 存储日志数据:架构监控数据(登陆日志,中间件访问日志,推送日志,短信邮件发送记录等),业务操做日志信息等
  • 存储业务附件:UDFS系统存储图像,视频,文档等附件信息,智慧城市系统的监控图像、流量数据等

HBase 的版本选择与定位

如何选择合适的 HBase 版本

HBase属于Hadoop生态体系,因此HBase的版本选择实际就是Hadoop的版本选择。而Hadoop就像Linux同样,也有多个发行版,经常使用发行版有如下几种:缓存

  • 原生的Apache Hadoop
  • CDH:Cloudera Distributed Hadoop
  • HDP:Hortonworks Data Platform

原生的Apache Hadoop在生产环境中不建议使用,由于Apache社区里的Hadoop生态系统的框架只是解决了单个框架的问题,若是想要将不一样的框架,例如Hive、Hbase等框架综合起来使用的话,老是会产生jar包的冲突问题,并且这些冲突问题一般都是没法解决的。因此在学习的时候可使用Apache Hadoop,可是生产环境中就不太建议使用了。服务器

CDH以及HDP都是基于Apache Hadoop社区版衍生出来的,这两个发行版虽然都是商业版的,但不属于收费版本,除非须要提供技术服务,才须要收取必定的服务费用,而且它们也都是开源的。在国内绝大多数公司都会选择使用CDH版本,因此在这里也主要介绍CDH,选择CDH的主要理由以下:

  • CDH对Hadoop版本的划分很是清晰,目前只有三个系列的版本(如今已经更新到CDH6.32了,基于hadoop3.x),分别是cdh四、cdh5和cdh6,分别对应第一代Hadoop(Hadoop 1.0)、第二代Hadoop(Hadoop 2.0)和第三代Hadoop(Hadoop 3.0),相比而言,Apache版本则混乱得多;
  • CDH文档清晰且丰富,不少采用Apache版本的用户都会阅读cdh提供的文档,包括安装文档、升级文档等。

并且CDH提供了一个CM组件,让咱们在安装它的时候只须要在浏览器上的页面中,点击各类下一步就能够完成安装,比起Apache Hadoop的安装要方便不少,并且不少操做均可以在图形界面上完成,例如集群的搭建以及节点切换等。CDH与Spark的合做是很是好的,因此在CDH中对Spark的支持比较好。最主要的是通常状况下使用同一版本的CDH,就不会发生jar冲突的状况。

CDH6的下载地址以下:

注:选择版本的时候尽可能保持一致,例如hive选择了cdh5.7.0的话,那么其余框架也要选择cdh5.7.0,否则有可能会发生jar包的冲突。

HBase 在 Hadoop 生态系统中的定位

初识 HBase


HBase 系统架构与数据模型

系统架构

大体的架构体系

在HBase中,表被分割成多个更小的块而后分散的存储在不一样的服务器上,这些小块叫作Region,存放Region的地方叫作RegionServer。Master进程负责处理不一样的RegionServer之间的Region的分发。HBase里的HRegionServer和HRegion类表明RegionServer和Region。HRegionServer除了包含一些HRegion以外,还处理两种类型的文件用于数据存储。

初识 HBase

  • HBase 依赖 Zookeeper 做为分布式的协调、治理工具,RegionServer、Master也会把本身的信息写到ZooKeeper中
  • HBase 还依赖 HDFS 做为底层的文件系统,HBase 的数据最终是存储到 HDFS 服务中的
  • HBase 存在两个主要进程,分别是RegionServer和Master
    • HBase 中的 RegionServer,能够类比为 HDFS 的 DataNode 即数据节点。客户端经过RegionServer对数据进行读写操做,而RegionServer会负责与 HDFS 进行数据交互
    • RegionServer会实时向Master报告自身状态及region等信息。Master知道全局的RegionServer运行状况,能够控制RegionServer的故障转移和region的切分。Master至关因而RegionServer集群的管理者,而且任什么时候刻只有一个Master在运行

细化的架构体系

初识 HBase

Client

  • 客户端包含访问HBase的接口,同时在缓存中维护着已经访问过的Region位置信息,用来加快后续数据访问过程

Zookeeper

  • Zookeeper做为协调工具能够帮助选举出一个Master做为集群的总管,并保证在任什么时候刻总有惟一一个Master在运行,这就避免了Master的“单点故障”的问题
    初识 HBase

Master

  • 主要负责表和Region的管理工做
  • 管理客户端对表的增长、删除、修改、查询等操做
  • 实现不一样RegionServer之间的负载均衡
  • 在Region分裂或合并后,负责从新调整Region的分布
  • 对发生故障失效的RegionServer上的Region进行迁移

RegionServer

  • RegionServer是HBase中最核心的模块,负责维护分配给本身的Region,并响应用户的读写请求。
  • 用户读写数据过程:
    • 用户写入数据时,被分配到相应Region服务器去执行
    • 用户数据首先被写入到MEMStore和Hlog中
    • 只有当操做写入Hlog以后,commit()调用才会将其返回给客户端
    • 当用户读取数据时,Region服务器首先访问MEMStore缓存,若是找不到,再去磁盘上面的StoreFile中寻找
  • 缓存的刷新:
    • 系统会周期性地把MemStore缓存里的内容刷写到磁盘的StoreFile文件中,清空缓存,并在Hlog里面写入一个标记
    • 每次刷写都生成一个新的StoreFile文件,所以,每一个Store包含多个StoreFile文件
    • 每一个Region服务器都有一个本身的HLog 文件,每次启动都检查该文件,确认最近一次执行缓存刷新操做以后是否发生新的写入操做;若是发现更新,则先写入MemStore,再刷写到StoreFile,最后删除旧的Hlog文件,开始为用户提供服务。
  • StoreFile的合并:
    • 每次刷写都生成一个新的StoreFile,数量太多,影响查找速度、
    • 调用Store.compact()把多个合并成一个
    • 合并操做比较耗费资源,只有数量达到一个阈值才启动合并

读写流程示意图:
初识 HBase

HLog

  • 预写日志文件,也叫作WAL(write-ahead log),WAL位于/hbase/WALs/目录下
  • 一般状况,每一个RegionServer只有一个WAL实例。在2.0以前,WAL的实现叫作HLog

MasterProcWALHMaster记录管理操做,好比解决冲突的服务器,表建立和其它DDL等操做到它的WAL文件中,这个WALs存储在MasterProcWALs目录下,它不像RegionServer的WALs,HMaster的WAL也支持弹性操做,就是若是Master服务器挂了,其它的Master接管的时候继续操做这个文件。

WAL记录全部的HBase数据改变,若是一个RegionServer在MemStore进行FLush的时候挂掉了,WAL能够保证数据的改变被应用到。若是写WAL失败了,那么修改数据的完整操做就是失败的。

MultiWAL:若是每一个RegionServer只有一个WAL,因为HDFS必须是连续的,致使必须写WAL连续的,而后出现性能问题。MultiWAL可让RegionServer同时写多个WAL并行的,经过HDFS底层的多管道,最终提高总的吞吐量,可是不会提高单个Region的吞吐量。

HFile

  • 真实存储数据的文件,HFile是Hbase在HDFS中存储数据的格式,它包含多层的索引,这样在Hbase检索数据的时候就不用彻底的加载整个文件。索引的大小(keys的大小,数据量的大小)影响block的大小,在大数据集的状况下,block的大小设置为每一个RegionServer 1GB也是常见的。

HFile的生成方式:

  • 一、起初,HFile中并无任何Block,数据还存在于MemStore中
  • 二、Flush发生时,建立HFile Writer,第一个空的Data Block出现,初始化后的Data Block中为Header部分预留了空间,Header部分用来存放一个Data Block的元数据信息
  • 三、然后,位于MemStore中的KeyValues被一个个append到位于内存中的第一个Data Block中
  • 四、若是配置了Data Block Encoding,则会在Append KeyValue的时候进行同步编码,编码后的数据再也不是单纯的KeyValue模式。Data Block Encoding是HBase为了下降KeyValue结构性膨胀而提供的内部编码机制

初识 HBase


表结构及数据模型

HBase 是一个稀疏、多维度、排序的映射表,这张表的索引是行键、列簇、列限定符和时间戳。在 HBase 中每一个值都是一个未经解释的字符串,没有数据类型。用户在表中存储数据,每一行都有一个可排序的行键和任意多的列。

表在水平方向由一个或多个列簇组成,一个列簇中能够包含任意多个列,同一个列簇里面的数据存储在一块儿。列簇支持动态扩展,能够很轻松地添加一个列簇或列,无需预先定义列的数量以及类型,全部列均以字符串形式存储,用户须要自行进行数据类型转换。

在 HBase 中执行更新操做时,并不会删除数据旧的版本,而是生成一个新的版本,旧的版本仍然保留(这是和HDFS只容许追加不容许修改的特性相关的),因此 HBase 的数据是版本化的。

初识 HBase

  • 表:HBase采用表来组织数据,表由行和列组成,列划分为若干列簇。
  • 行:每一个HBase表都由若干行组成,每一行由行键(row key)来标识。
  • 行键:每一行都会存在一个行键,能够类比为关系型数据库中的主键
  • 列簇:一个HBase表被分组成许多“列簇”(Column Family)的集合,列簇中的列是有序的,它是基本的访问控制单元。在设计表时,列簇尽可能不超过5个,不然会影响性能。
  • 列限定符:列簇里的数据经过限定符(列名)来定位。每一个列簇中的列数是没有限制的,列只有在插入数据后才存在
  • 单元格:在HBase表中,经过行、列簇和列限定符肯定一个“单元格”(cell),单元格中存储的数据没有数据类型,总被视为字节数组byte[]
  • 时间戳:每一个单元格都保存着同一份数据的多个版本,这些版本采用时间戳进行索引。

这是官方文档中给出的一个示例表:
初识 HBase

说明:

  • 该表中包含两行:com.cnn.wwwcom.example.www
  • 有三个列簇:contentsanchorpeople
  • 第一行(com.cnn.www)拥有5个版本,第二行(com.example.www)拥有1个版本
  • 对于第一行(com.cnn.www):
    • contents列簇中包含一列:contents:html
      • 该列的值为某个网站的html内容
    • anchor列簇中包含两列:anchor:cnnsi.comanchor:my.look.ca
      • cnnsi.com列的值为CNN
      • my.look.ca列的值为CNN.com
    • people列簇中没有任何列
  • 对于第二行(com.example.www):
    • contents列簇中包含一列:contents:html
      • 该列的值为一段html
    • anchor列簇中没有任何列
    • people列簇中包含一列:people:author
      • 该列的值为John Doe

使用json格式表示该表内容以下:

{
  "com.cnn.www": {
    contents: {
      t6: contents:html: "<html>..."
      t5: contents:html: "<html>..."
      t3: contents:html: "<html>..."
    }
    anchor: {
      t9: anchor:cnnsi.com = "CNN"
      t8: anchor:my.look.ca = "CNN.com"
    }
    people: {}
  }
  "com.example.www": {
    contents: {
      t5: contents:html: "<html>..."
    }
    anchor: {}
    people: {
      t5: people:author: "John Doe"
    }
  }
}