要搞懂大数据存储选型,首先必须得了解数据库的发展历史,了解关系数据库的优势和缺点,才能进一步考虑如何处理这些问题。
数据库发展
简单来说,数据库的发展是跟随数据量的发展来发展的,最开始的时候LAMP已经足够使用,当海量大数据出现后,如何存储和查询这些数据就成了人们考虑的问题,这时候人们自然想到从两方面入手:
- 硬件
1. 增加单机性能,加CPU加内存,也就是垂直扩展,但是提升有限
2. 改用主备,增加读性能,写性能存在同步锁问题
3. 分库分表,也就是水平扩展
- 软件
1. 优化索引,减少查询
2. 缓存查询结果
3. 反范式,快速查询
这些手段在一段时间内满足了要求,但是扩展性、易用性、性能等诸多方面都存在较大问题,这时候人们开始思考关系数据库的本质和提升的可能。
关系数据库(RDBMS)需要如下四点要求(ACID):
- 原子性(Atomicity A)
事务操作的成功失败标准,比如汇钱,一个账号取钱另一个账号收钱,整个过程是最小化单元,不能中断
- 一致性(Consistency C)
不同用户同一时刻看到的数据一致,也就是事务操作前后的逻辑不能变,比如两个人的总余额固定,转账过程中的中间结果别人是看不到的,能看到的只有一致性的数据
- 独立性(Isolation I)
事务操作过程中,不同事务的操作中间和结果如何相关影响,这涉及到不同的隔离级别,比如常见的读已提交和重复读
- 持久性(Durability D)
事务修改保存在磁盘上,宕机也不会丢失
ACID主要依赖事务,这就带来了诸多限制,比如多行事务原子性保证涉及到整个分布式集群锁住的问题,这完全丧失了分布式的优点,因此分布式可扩展数据库可从如下两个方面入手:
NoSQL
NoSQL,指的是非关系型的数据库。NoSQL有时也称作Not Only SQL的缩写,是对不同于传统的关系型数据库的数据库管理系统的统称。
NoSQL其实就是弱化了了ACID的一些特性,来获得其他方面的提升,需要满足CAP理论:
- 一致性(Consistency) (不同机器访问一致,即所有节点在同一时间具有相同的数据)
- 可用性(Availability) (客户端总是可以读写,即保证每个请求不管成功或者失败都有响应)
- 分隔容忍(Partition tolerance) (分到多个机器形成多个分区,即使网络故障依然可以工作,即系统中任意信息的丢失或失败不会影响系统的继续运作)
对应关系数据库的事务级别,这里的一致性也分为几个等级:
- 严格一致性 必须更新主节点时锁定副本
- 因果一致性 因果相关操作必须串行化
- 弱一致性(最终一致性) 更新最终会传播到所有节点,中间会出现不同步
CAP指出一个分布式系统不可能同时很好的满足一致性,可用性和分区容错性这三个需求,最多只能同时较好的满足两个。因此,根据CAP原理将NoSQL数据库分成了满足 CA 原则、满足 CP 原则和满足 AP 原则三 大类:
- CA - 单点集群,满足一致性,可用性的系统,通常在可扩展性上不太强大。
- CP - 满足一致性,分区容忍性的系统,通常性能不是特别高。
- AP - 满足可用性,分区容忍性的系统,通常可能对一致性要求低一些。
简单来说,实际使用中我们可以通过适当降低一个特性来增加强其他特性,如下:
这里CA也就是对应传统关系数据库,网络发生分裂时,主节点被剥离,无法正常工作。NoSQL常用的是实际P固定,可选C或A。
可以看到这里,Cassandar强调AP,因此一致性没那么好,满足最终一致性,但是写入性能非常高,常用和Spark等配合实施写入,目前国外NoSQL排名第一;MongoDB/HBase/Redis等强调CP,因此相对来说写入性能没那么好(相对来说,比关系数据库还是高很多),但是一致性非常好,对于消息系统、订单系统等场合是必须的。
Sharding-nothing
原则就是按照一定的规则将数据分片互不相干的部分,这样减少资源访问的冲突,加快速度,基本上分布式的数据库都要使用这种原则,比如Hbase/Cassandra的Rowkey,MongoDB的分片等等,常用的分片原则如下:
- 1.功能或特性,比如博客的文章、评论、点赞分别管理
- 2.键值拆分,比如hash值或时间
- 3.一个统一的管理节点或目录,通过查表快速定位数据
基于这个原则,人们还对传统的关系数据库进行改造,最有名的就是基于PostgreSQL改造的GreenPlum,依赖MPP架构(即大规模并行处理-Massively Parallel Processor),通过多个Segmen并行工作,达到极高的查询速度。
存储选型
有了前面的历史背景描述,再来看大数据存储选型会简单很多,主要从如下几个方面展开:
- 数据存储空间和存储记录数
- 并发访问量
- 写入、查询速度
- 分析的复杂程度(对二级索引、事务、join的支持)
- 成本
首先数据规模限制了如何存储的问题,海量数据关系数据库肯定存不下,常见的数据库和对应的数据量级简单列如下:
- Mysql 百GB
- PostgreSQL TB
- MongoDB TB
- GreenPlum 百TB
- Hbase、Cassandra 千TB~PB
再就是考虑并发量和速度,这其实也和查询复杂度相关,总之记住大数据组件肯定都是牺牲某一方面的特性来满足其他特性的提升,整个是一个取舍的问题,常见的几个大数据存储特征如下:
- MongoDB 并发量和速度和传统mysql没区别,也支持ACID(支持复杂查询),但是存储量限制在那,得益于无模式和自动扩容的设计,常用做项目前期替代mysql做快速迭代
- Hbase/Cassandra,并发访问都可达千万QPS,速度也非常快,适合OLTP,但是基于行键的设计没法支持复杂查询,当然有各种各样的针对此的解决方法,但是那只是为了处理需求来设计的,并不是他们擅长的
- GreenPlum 对于海量数据分析非常快,非常适合做OLAP,但是MPP的架构压力都在Master上,并发访问无法提升,可以和HBase/Cassandra配合使用
原创,转载请注明来自