分布式数据库实战【原创】

每年的双十一,系统都会遇到性能挑战。应用层面的扩展性,我们已经做了很多工作,基本上都能够水平扩展,目前最大的压力还是oracle数据库。这就是一个单点。因此,为了让数据库层面也能够水平扩展,我们准备采用分布式数据库引擎。3月底,我和另一名架构师组成了一个两个人小团队,开始立项。
开源的分布式数据库引擎有:cobar, mycat, Atlas, Kingshard, sharding-jdbc.考虑到架构组资源情况,我们觉得采用一个相对成熟,社区活跃的产品比较适合我们。最终我们选择了当当网开源的sharding-jdbc.
选型完之后,从做方案到改造上线,我们总共花了1个月左右时间,从改造之前的单次查询时间需要10s左右,降低到单次查询只需1s,我们觉得还是蛮有成就感的。接下来,我把改造的思路与大家分享一下。
1. 首先我们的业务系统都是运行在oracle上的,目前比较成熟的分库分表方案都是运行在mysql上。因此,我们需要将oracle的数据同步到mysql上,这样做带来的额外好处就是实现了读写分离。整个过程是这样的,用户写数据到oracle主库中,我们用cdc抽取并同步到mysql上。为了不影响主库性能,我们通过ogg将数据同步到备库,在备库上采用cdc抽取数据到rocketMq中,再从rocketMq抽取数据到mysql中。增加rocketMq是为了解耦,同时,也防止因为处理程序的故障,导致cdc数据未被执行就丢弃或重复执行。将数据从mq获取到mysql入库的过程,因为使用了多线程(PushConsumer),需要做幂等处理,保证所有数据可重执,同时严格保证数据处理的顺序。由于项目时间要求,目前上线的版本我们只做了一个进程的多线程,基本已经满足目前的性能要求,但是可靠性还存在问题。下一步我们将通过zookeeper做分布式的线程同步,保证分布式的幂等处理。
2. 在插入mysql和外网查询的功能中,我们使用了sharding-jdbc.不好处理的是,sharding-jdbc不支持小表广播。在插入的时候能够插入到指定库的指定表中,但是查询的时候又会从不同的库中查询。(不知是bug, 还是我们的配置不正确,还是为了不进行跨库join的有意优化),反正小表我们得自己同步。我们采用了阿里的otter.
3.到了正式上线,就涉及到数据迁移。当时打算自己做一个,后来发现阿里的yugong刚好满足我们需要,而且性能还挺好。
4.在整个过程中,为了更加方便的调试,我们还采用extjs做了一个针对mq的消息查询工具.另外,一开始为了性能,我们在获取cdc数据的时候,也采用了多线程调度,用的是当当的elastic-job.但是不知什么原因,采用这个分布式调度和cdc结合之后,老丢失据,我们估计是这个job我们配的不对,导致cdc的位移错乱,改成单线程就没问题了。幸亏性能瓶颈也不在这个地方,单线程也能满足我们的需求。
最后感谢阿里和当当,奉献了这么多好工具。我们的实施成功,完全是站在巨人的肩膀上。

猜你喜欢

转载自zhenggm.iteye.com/blog/2300203