如何评判基于中间件的mysql分布式中间件mysql与 云数据库

mysql分布式中间件数据库中间件(Distributed Database Middleware簡称DDM),是一款基于MySQL存储通过分库分表算法进行水平扩展,采用存储计算分离架构实现存储层、计算层的无限扩展。

DDM支持RDS for MySQL采用标准關系型数据库技术,结合云监控等运维管控手段保障DDM的高可用、持续运维以及良好的可扩展性。专注于解决数据库mysql分布式中间件扩展问題突破了传统数据库的容量和性能瓶颈,实现海量数据高并发访问其核心的优势是提供数据库水平扩展能力,同时提供单机MySQL的用户体驗

DDM在并发、计算、数据存储三个方面的可扩展性,打破业务发展中因数据库扩展性及运维压力所产生的困扰

  • 通过增加DDM实例节点和RDS for MySQL实例數量达到水平扩展效果。
  • 推荐从弹性云服务器(Elastic Cloud Server简称ECS)访问mysql分布式中间件数据库中间件,为保障安全性二者须在同一虚拟私有云(Virtual Private Cloud,簡称VPC)中

mysql分布式中间件数据库中间件具有简单易用、快速部署、低成本等优势。

  • 支持字符串、数字、日期等多种纬度
    • 兼容MySQL协议、语法、客户端。
    • 轻松数据导入数据库上云。
    • 业务零代码改动实现读写分离。
  • 可在线快速部署实例节省采购、部署、配置等自建数据库工莋,缩短项目周期帮助业务快速上线。

  • 稳定的产品完善的运维和技术支持,相比开源产品总体性价比更高;多种实例规格配置覆盖不哃业务规模场景按需购买。

Cobar是阿里巴巴研发的关系型数据的mysql汾布式中间件处理系统是提供关系型数据库(MySQL)mysql分布式中间件服务的中间件,该产品成功替代了原先基于Oracle的数据存储方案它可以让传統的数据库得到良好的线性扩展,并看上去还是一个数据库,对应用保持透明

  • 产品在阿里巴巴稳定运行3年以上。
  • 集群日处理在线SQL请求50亿次鉯上
  • 集群日处理在线数据流量TB级别以上。

Cobar的核心功能:

Cobar的mysql分布式中间件主要是通过将表放入不同的库来实现:

  • Cobar支持将一张表水平拆分成哆份分别放入不同的库来实现表的水平拆分
  • Cobar也支持将不同的表放入不同的库
  • 多数情况下用户会将以上两种方式混合使用

要强调的是,Cobar不支持将一张表例如test表拆分成test_1, test_2, test_3…..放在同一个库中,必须将拆分后的表分别放入不同的库来实现mysql分布式中间件

在用户配置了MySQL心跳的情况下,Cobar可以自动向后端连接的MySQL发送心跳判断MySQL运行状况,一旦运行出现异常Cobar可以自动切换到备机工作。需要强调的是:

  • Cobar的主备切换有两种触發方式一种是用户手动触发,一种是Cobar的心跳语句检测到异常后自动触发那么,当心跳检测到主机异常切换到备机,如果主机恢复了需要用户手动切回主机工作,Cobar不会在主机恢复时自动切换回主机除非备机的心跳也返回异常。
  • Cobar只检查MySQL主备异常不关心主备之间的数據同步,因此用户需要在使用Cobar之前在MySQL主备上配置双向同步详情可以参阅MySQL参考手册。
  • 不支持跨库情况下的join、分页、排序、子查询操作
  • SET语呴执行会被忽略,事务和字符集设置除外
  • 分库情况下,insert语句必须包含拆分字段列名
  • 分库情况下,update语句不能更新拆分字段的值
  • 暂时只支持MySQL数据节点。
  • dataSource:数据源表示一个具体的数据库连接,与物理存在的数据库schema一一对应
  • dataNode:数据节点,由主、备数据源数据源的HA以及连接池共同组成,可以将一个dataNode理解为一个分库
  • table:表,包括拆分表(如tb1tb2)和非拆分表。
  • tableRule:路由规则用于判断SQL语句被路由到具体哪些datanode执行。

Cobar支持的数据库结构(schema)的层次关系具有较强的灵活性用户可以将表自由放置不同的datanode,也可将不同的datasource放置在同一MySQL实例上在实际应用中,需要通过配置文件(/cobar.html

通 过MySQLReplication功能所实现的扩展总是会受箌数据库大小的限制一旦数据库过于庞大,尤其是当写入过于频繁很难由一台主机支撑的时 候,我们还是会面临到扩展瓶颈这时候,我们就必须许找其他技术手段来解决这个瓶颈那就是我们这一章所要介绍恶的数据切分技术。

可 能很多读者朋友在网上或者杂志上面嘟已经多次见到关于数据切分的相关文章了只不过在有些文章中称之为数据的Sharding。其实不管是称之为数据的 Sharding还是数据的切分其概念都是┅样的。简单来说就是指通过某种特定的条件,将我们存放在同一个数据库中的数据分散存放到多个数据库(主 机)上面以达到分散單台设备负载的效果。数据的切分同时还可以提高系统的总体可用性因为单台设备Crash之后,只有总体数据的某部分不可用而不是 所有的數据。

数 据的切分(Sharding)根据其切分规则的类型可以分为两种切分模式。一种是按照不同的表(或者Schema)来切分到不同的数据库(主机)之仩 这种切可以称之为数据的垂直(纵向)切分;另外一种则是根据表中的数据的逻辑关系,将同一个表中的数据按照某种条件拆分到多囼数据库(主机)上面这种切 分称之为数据的水平(横向)切分。

垂 直切分的最大特点就是规则简单实施也更为方便,尤其适合各业務之间的耦合度非常低相互影响很小,业务逻辑非常清晰的系统在这种系统中,可以很容易做 到将不同业务模块所使用的表分拆到不哃的数据库中根据不同的表来进行拆分,对应用程序的影响也更小拆分规则也会比较简单清晰。

水平切分于垂直切分相比相对来说稍微复杂一些。因为要将同一个表中的不同数据拆分到不同的数据库中对于应用程序来说,拆分规则本身就较根据表名来拆分更为复杂后期的数据维护也会更为复杂一些。

当我们某个(或者某些)表的数据量和访问量特别的大通过垂直切分将其放在独立的设备上后仍嘫无法满足性能要求,这时候我们就必须将垂直切分和水平切分相结合先垂直切分,然后再水平切分才能解决这种超大型表的性能问題。

下面我们就针对垂直、水平以及组合切分这三种数据切分方式的架构实现及切分后数据的整合进行相应的分析

我 们先来看一下,数據的垂直切分到底是如何一个切分法的数据的垂直切分,也可以称之为纵向切分将数据库想象成为由很多个一大块一大块的“数据块”(表) 组成,我们垂直的将这些“数据块”切开然后将他们分散到多台数据库主机上面。这样的切分方法就是一个垂直(纵向)的数據切分

一 个架构设计较好的应用系统,其总体功能肯定是由很多个功能模块所组成的而每一个功能模块所需要的数据对应到数据库中僦是一个或者多个表。而在架构设计 中各个功能模块相互之间的交互点越统一越少,系统的耦合度就越低系统各个模块的维护性以及擴展性也就越好。这样的系统实现数据的垂直切分也就越容 易。

当我们的功能模块越清晰耦合度越低,数据垂直切分的规则定义也就樾容易完全可以根据功能模块来进行数据的切分,不同功能模块的数据存放于不同的数据库主机中可以很容易就避免掉跨数据库的Join存茬,同时系统架构也非常的清晰

当 然,很难有系统能够做到所有功能模块所使用的表完全独立完全不需要访问对方的表或者需要两个模块的表进行Join操作。这种情况下我们就必须根据实际 的应用场景进行评估权衡。决定是迁就应用程序将需要Join的表的相关某快都存放在同┅个数据库中还是让应用程序做更多的事情,也就是程序完全通过模块 接口取得不同数据库中的数据然后在程序中完成Join操作。

一般来說如果是一个负载相对不是很大的系统,而且表关联又非常的频繁那可能数据库让步,将几个相关模块合并在一起减少应用程序的工莋的方案可以减少较多的工作量是一个可行的方案。

当 然通过数据库的让步,让多个模块集中共用数据源实际上也是简介的默许了各模块架构耦合度增大的发展,可能会让以后的架构越来越恶化尤其是当发展到一 定阶段之后,发现数据库实在无法承担这些表所带来嘚压力不得不面临再次切分的时候,所带来的架构改造成本可能会远远大于最初的时候

所以,在数据库进行垂直切分的时候如何切汾,切分到什么样的程度是一个比较考验人的难题。只能在实际的应用场景中通过平衡各方面的成本和收益才能分析出一个真正适合洎己的拆分方案。

比如在本书所使用示例系统的example数据库我们简单的分析一下,然后再设计一个简单的切分规则进行一次垂直垂直拆分。

系统功能可以基本分为四个功能模块:用户群组消息,相册以及事件分别对应为如下这些表:

)上面提供的使用手册获取,这里就鈈再细述了

★利用HiveDB实现数据切分及整合

和 前面的MySQLProxy以及Amoeba一样,HiveDB同样是一个基于Java针对MySQL数据库的提供数据切分及整合的开源框架只是目前的 HiveDB僅仅支持数据的水平切分。主要解决大数据量下数据库的扩展性及数据的高性能访问问题同时支持数据的冗余及基本的HA机制。

HiveDB的实现机淛与MySQLProxy和Amoeba有一定的差异他并不是借助MySQL的Replication功能来实现数据的冗余,而是自行实现了数据冗余机制而其底层主要是基于HibernateShards来实现的数据切分工莋。

在 HiveDB中通过用户自定义的各种Partitionkeys(其实就是制定数据切分规则),将数据分散到多个MySQLServer中在访问的时 候,在运行Query请求的时候会自动分析过滤条件,并行从多个MySQLServer中读取数据并合并结果集返回给客户端应用程序。

单纯从功能方面来讲HiveDB可能并不如MySQLProxy和Amoeba那样强大,但是其数据切分的思路与前面二者并无本质差异此外,HiveDB并不仅仅只是一个开源爱好者所共享的内容而是存在商业公司支持的开源项目。

下面是HiveDB官方网站上面一章图片描述了HiveDB如何来组织数据的基本信息,虽然不能详细的表现出太多架构方面的信息但是也基本可以展示出其在数据切分方面独特的一面了。

★ 其他实现数据切分及整合的解决方案

除了上面介绍的几个数据切分及整合的整体解决方案之外还存在很多其怹同样提供了数据切分与整合的解决方案。如基于MySQLProxy的基础上做了进一步扩展的HSCALE通过Rails构建的SpockProxy,以及基于Pathon的Pyshards等等

不管大家选择使用哪一种解决方案,总体设计思路基本上都不应该会有任何变化那就是通过数据的垂直和水平切分,增强数据库的整体服务能力让应用系统的整体扩展能力尽可能的提升,扩展方式尽可能的便捷

只 要我们通过中间层Proxy应用程序较好的解决了数据切分和数据源整合问题,那么数据庫的线性扩展能力将很容易做到像我们的应用程序一样方便只需要通过 添加廉价的PCServer服务器,即可线性增加数据库集群的整体服务能力讓数据库不再轻易成为应用系统的性能瓶颈。

数据切分与整合可能存在的问题

这里大家应该对数据切分与整合的实施有了一定的认识了,或许很多读者朋友都已经根据各种解决方案各自特性的优劣基本选定了适合于自己应用场景的方案后面的工作主要就是实施准备了。

茬实施数据切分方案之前有些可能存在的问题我们还是需要做一些分析的。一般来说我们可能遇到的问题主要会有以下几点:

◆ 引入mysql汾布式中间件事务的问题;

◆跨节点Join的问题;

◆ 跨节点合并排序分页问题;

1. 引入mysql分布式中间件事务的问题

一旦数据进行切分被分别存放在哆个MySQLServer中之后,不管我们的切分规则设计的多么的完美(实际上并不存在完美的切分规则)都可能造成之前的某些事务所涉及到的数据已經不在同一个MySQLServer中了。

在 这样的场景下如果我们的应用程序仍然按照老的解决方案,那么势必需要引入mysql分布式中间件事务来解决而在MySQL各個版本中,只有从MySQL5.0开始以后 的各个版本才开始对mysql分布式中间件事务提供支持而且目前仅有Innodb提供mysql分布式中间件事务支持。不仅如此即使峩们刚好使用了支持mysql分布式中间件事务的MySQL版本,同 时也是使用的Innodb存储引擎mysql分布式中间件事务本身对于系统资源的消耗就是很大的,性能夲身也并不是太高而且引入mysql分布式中间件事务本身在异常处理方面就会带来 较多比较难控制的因素。

怎 么办其实我们可以可以通过一個变通的方法来解决这种问题,首先需要考虑的一件事情就是:是否数据库是唯一一个能够解决事务的地方呢其实并不是这样的, 我们唍全可以结合数据库以及应用程序两者来共同解决各个数据库解决自己身上的事务,然后通过应用程序来控制多个数据库上面的事务

吔就是说,只要我们愿意完全可以将一个跨多个数据库的mysql分布式中间件事务分拆成多个仅处于单个数据库上面的小事务,并通过应用程序来总控各个小事务当然,这样作的要求就是我们的俄应用程序必须要有足够的健壮性当然也会给应用程序带来一些技术难度。

上面介绍了可能引入mysql分布式中间件事务的问题现在我们再看看需要跨节点Join的问题。数据切分之后可能会造成有些老的Join语句无法继续使用,洇为Join使用的数据源可能被切分到多个MySQLServer中了

怎 么办?这个问题从MySQL数据库角度来看如果非得在数据库端来直接解决的话,恐怕只能通过MySQL一種特殊的存储引擎Federated来解决了 Federated存储引擎是MySQL解决类似于Oracle的DBLink之类问题的解决方案。和OracleDBLink的主要区别在于 Federated会保存一份远端表结构的定义信息在本地咋一看,Federated确实是解决跨节点Join非常好的解决方案但是我们还应该清楚一 点,那就似乎如果远端的表结构发生了变更本地的表定义信息昰不会跟着发生相应变化的。如果在更新远端表结构的时候并没有更新本地的Federated表 定义信息就很可能造成Query运行出错,无法得到正确的结果

对 待这类问题,我还是推荐通过应用程序来进行处理先在驱动表所在的MySQLServer中取出相应的驱动结果集,然后根据驱动结果集再到被驱动表所在的 MySQLServer中取出相应的数据可能很多读者朋友会认为这样做对性能会产生一定的影响,是的确实是会对性能有一定的负面影响,但是除叻此法 基本上没有太多其他更好的解决办法了。而且由于数据库通过较好的扩展之后,每台MySQLServer的负载就可以得到较好的控制单纯针对單条 Query来说,其响应时间可能比不切分之前要提高一些所以性能方面所带来的负面影响也并不是太大。更何况类似于这种需要跨节点Join的需求也并不 是太多,相对于总体性能而言可能也只是很小一部分而已。所以为了整体性能的考虑偶尔牺牲那么一点点,其实是值得的毕竟系统优化本身就是存在很多取舍 和平衡的过程。

3. 跨节点合并排序分页问题

一 旦进行了数据的水平切分之后可能就并不仅仅只有跨節点Join无法正常运行,有些排序分页的Query语句的数据源可能也会被切分到多个节点这样造成 的直接后果就是这些排序分页Query无法继续正常运行。其实这和跨节点Join是一个道理数据源存在于多个节点上,要通过一个Query来解决就和 跨节点Join是一样的操作。同样Federated也可以部分解决当然存茬的风险也一样。

还是同样的问题怎么办?我同样仍然继续建议通过应用程序来解决

如 何解决?解决的思路大体上和跨节点Join的解决类姒但是有一点和跨节点Join不太一样,Join很多时候都有一个驱动与被驱动的关系所以Join 本身涉及到的多个表之间的数据读取一般都会存在一个順序关系。但是排序分页就不太一样了排序分页的数据源基本上可以说是一个表(或者一个结果集),本身 并不存在一个顺序关系所鉯在从多个数据源取数据的过程是完全可以并行的。这样排序分页数据的取数效率我们可以做的比跨库Join更高,所以带来的性能 损失相对嘚要更小在有些情况下可能比在原来未进行数据切分的数据库中效率更高了。当然不论是跨节点Join还是跨节点排序分页,都会使我们的應用服务 器消耗更多的资源尤其是内存资源,因为我们在读取访问以及合并结果集的这个过程需要比原来处理更多的数据

分析到这里,可能很多读者朋友会发现上面所有的这些问题,我给出的建议基本上都是通过应用程序来解决大家可能心里开始犯嘀咕了,是不是洇为我是DBA所以就很多事情都扔给应用架构师和开发人员了?

其 实完全不是这样首先应用程序由于其特殊性,可以非常容易做到很好的擴展性但是数据库就不一样,必须借助很多其他的方式才能做到扩展而且在这个扩展过 程中,很难避免带来有些原来在集中式数据库Φ可以解决但被切分开成一个数据库集群之后就成为一个难题的情况要想让系统整体得到最大限度的扩展,我们只能 让应用程序做更多嘚事情来解决数据库集群无法较好解决的问题。

通 过数据切分技术将一个大的MySQLServer切分成多个小的MySQLServer既解决了写入性能瓶颈问题,同时也再┅次提升了整个数据库集群的 扩展性不论是通过垂直切分,还是水平切分都能够让系统遇到瓶颈的可能性更小。尤其是当我们使用垂矗和水平相结合的切分方法之后理论上将不会再遇到扩 展瓶颈了。

我要回帖

更多关于 mysql分布式数据库 的文章

 

随机推荐