最近由于项目缘由,研究了Cassandra,Hbase等几个NoSQL数据库,最终决定采用HBase。在这里,我就向你们分享一下本身对HBase的理解。
在 说HBase以前,我想再唠叨几句。作互联网应用的哥们儿应该都清楚,互联网应用这东西,你没办法预测你的系统何时会被多少人访问,你面临的用户到底 有多少,说不定今天你的用户还少,明天系统用户就变多了,结果您的系统应付不过来了了,不干了,这岂不是咱哥几个的悲哀,说时髦点就叫“杯具啊”。
其 实说白了,这些就是事先没有认清楚互联网应用什么才是最重要的。从系统架构的角度来讲,互联网应用更加看重系统性能以及伸缩性,而传统企业级应用都是比较 看重数据完整性和数据安全性。那么咱们就来讲说互联网应用伸缩性这事儿.对于伸缩性这事儿,哥们儿我也写了几篇博文,想看的兄弟能够参考我之前的博文,对 于web server,app server的伸缩性,我在这里先不说了,由于这部分的伸缩性相对来讲比较容易一点,我主要来回顾一些一个慢慢变大的互联网应用如何应对数据库这一层的伸 缩。
首先刚开始,人很少,压力也不大,搞一台数据库服务器就搞定了,此时全部的东东都塞进一个 Server里,包括web server,app server,db server,可是随着人愈来愈多,系统压力愈来愈多,这个时候可能你把web server,app server和db server分离了,好歹这样能够应付一阵子,可是随着用户量的不断增长,你会发现,数据库这哥们不行了,速度老慢了,有时候还会宕掉,因此这个时候,你 得给数据库这哥们找几个伴,这个时候Master-Salve就出现了,这个时候有一个Master Server专门负责接收写操做,另外的几个Salve Server专门进行读取,这样Master这哥们终于不抱怨了,总算读写分离了,压力总算轻点了,这个时候其实主要是对读取操做进行了水平扩张,经过增 加多个Salve来克服查询时CPU瓶颈。通常这样下来,你的系统能够应付必定的压力,可是随着用户数量的增多,压力的不断增长,你会发现Master server这哥们的写压力仍是变的太大,没办法,这个时候怎么办呢?你就得切分啊,俗话说“只有切分了,才会有伸缩性嘛”,因此啊,这个时候只能分库 了,这也是咱们常说的数据库“垂直切分”,好比将一些不关联的数据存放到不一样的库中,分开部署,这样终于能够带走一部分的读取和写入压力了,Master 又能够轻松一点了,可是随着数据的不断增多,你的数据库表中的数据又变的很是的大,这样查询效率很是低,这个时候就须要进行“水平分区”了,好比经过将 User表中的数据按照10W来划分,这样每张表不会超过10W了。
综上所述,通常一个流行的 web站点都会经历一个从单台DB,到主从复制,到垂直分区再到水平分区的痛苦的过程。其实数据库切分这事儿,看起来原理貌似很简单,若是真正作起来,我 想凡是sharding过数据库的哥们儿都深受其苦啊。对于数据库伸缩的文章,哥们儿能够看看后面的参考资料介绍。
好 了,从上面的那一堆废话中,咱们也发现数据库存储水平扩张scale out是多么痛苦的一件事情,不过幸亏技术在进步,业界的其它弟兄也在努力,09年这一年出现了很是多的NoSQL数据库,更准确的应该说是No relation数据库,这些数据库多数都会对非结构化的数据提供透明的水平扩张能力,大大减轻了哥们儿设计时候的压力。下面我就拿Hbase这分布式列 存储系统来讲说。
一 Hbase是个啥东东?
在说Hase是个啥家伙之 前,首先咱们来看看两个概念,面向行存储和面向列存储。面向行存储,我相信大伙儿应该都清楚,咱们熟悉的RDBMS就是此种类型的,面向行存储的数据库主 要适合于事务性要求严格场合,或者说面向行存储的存储系统适合OLTP,可是根据CAP理论,传统的RDBMS,为了实现强一致性,经过严格的ACID事 务来进行同步,这就形成了系统的可用性和伸缩性方面大大折扣,而目前的不少NoSQL产品,包括Hbase,它们都是一种最终一致性的系统,它们为了高的 可用性牺牲了一部分的一致性。好像,我上面说了面向列存储,那么到底什么是面向列存储呢?Hbase,Casandra,Bigtable都属于面向列存 储的分布式存储系统。看到这里,若是您不明白Hbase是个啥东东,没关系,我再总结一下下:
Hbase是一个面向列存储的分布式存储系统,它的优势在于能够实现高性能的并发读写操做,同时Hbase还会对数据进行透明的切分,这样就使得存储自己具备了水平伸缩性。
二 Hbase数据模型
HBase,Cassandra 的数据模型很是相似,他们的思想都是来源于Google的Bigtable,所以这三者的数据模型很是相似,惟一不一样的就是Cassandra具备 Super cloumn family的概念,而Hbase目前我没发现。好了,废话少说,咱们来看看Hbase的数据模型究竟是个啥东东。
在 Hbase里面有如下两个主要的概念,Row key,Column Family,咱们首先来看看Column family,Column family中文又名“列族”,Column family是在系统启动以前预先定义好的,每个Column Family均可以根据“限定符”有多个column.下面咱们来举个例子就会很是的清晰了。
假如 系统中有一个User表,若是按照传统的RDBMS的话,User表中的列是固定的,好比schema 定义了name,age,sex等属性,User的属性是不能动态增长的。可是若是采用列存储系统,好比Hbase,那么咱们能够定义User表,而后定 义info 列族,User的数据能够分为:info:name = zhangsan,info:age=30,info:sex=male等,若是后来你又想增长另外的属性,这样很方便只须要 info:newProperty就能够了。
也许前面的这个例子还不够清晰,咱们再举个例子来解释 一下,熟悉SNS的朋友,应该都知道有好友Feed,通常设计Feed,咱们都是按照“某人在某时作了标题为某某的事情”,可是同时通常咱们也会预留一下 关键字,好比有时候feed也许须要url,feed须要image属性等,这样来讲,feed自己的属性是不肯定的,所以若是采用传统的关系数据库将非 常麻烦,何况关系数据库会形成一些为null的单元浪费,而列存储就不会出现这个问题,在Hbase里,若是每个column 单元没有值,那么是占用空间的。下面咱们经过两张图来形象的表示这种关系:
上 图是传统的RDBMS设计的Feed表,咱们能够看出feed有多少列是固定的,不能增长,而且为null的列浪费了空间。可是咱们再看看下图,下图为 Hbase,Cassandra,Bigtable的数据模型图,从下图能够看出,Feed表的列能够动态的增长,而且为空的列是不存储的,这就大大节约 了空间,关键是Feed这东西随着系统的运行,各类各样的Feed会出现,咱们事先没办法预测有多少种Feed,那么咱们也就没有办法肯定Feed表有多 少列,所以Hbase,Cassandra,Bigtable的基于列存储的数据模型就很是适合此场景。说到这里,采用Hbase的这种方式,还有一个非 常重要的好处就是Feed会自动切分,当Feed表中的数据超过某一个阀值之后,Hbase会自动为咱们切分数据,这样的话,查询就具备了伸缩性,而再加 上Hbase的弱事务性的特性,对Hbase的写入操做也将变得很是快。
上 面说了Column family,那么我以前说的Row key是啥东东,其实你能够理解row key为RDBMS中的某一个行的主键,可是由于Hbase不支持条件查询以及Order by等查询,所以Row key的设计就要根据你系统的查询需求来设计了额。我还拿刚才那个Feed的列子来讲,咱们通常是查询某我的最新的一些Feed,所以咱们Feed的 Row key能够有如下三个部分构成<userId><timestamp><feedId>,这样以来当咱们要查询某个 人的最进的Feed就能够指定Start Rowkey为<userId><0><0>,End Rowkey为<userId><Long.MAX_VALUE><Long.MAX_VALUE>来查询了,同时 由于Hbase中的记录是按照rowkey来排序的,这样就使得查询变得很是快。
三 Hbase的优缺点
1 列的能够动态增长,而且列为空就不存储数据,节省存储空间.
2 Hbase自动切分数据,使得数据存储自动具备水平scalability.
3 Hbase能够提供高并发读写操做的支持
Hbase的缺点:
1 不能支持条件查询,只支持按照Row key来查询.
2 暂时不能支持Master server的故障切换,当Master宕机后,整个存储系统就会挂掉.(0.90.x已解决)