1.
1.1.时效性问题
mysql 主从复制存在延迟,不适合对数据同步实时性要求高的场景
注:复制有延迟这个问题mysql自身都解决不了,更不要指望第三方工具解决,这也是为什么很多生产mysql不开启读写分离的原因
1.2.canal 高可用问题
canal 挂载主库:mysql 一旦发生了故障转移,业务就会在其他mysql节点进行binlog的写入,很可能mysql 从节点的binlog和主节点binlog名称都不一样,而且canal 没有办法追随mysql 进行故障转移。一旦mysql master故障需要人为介入,并修复数据,故障恢复时间不可控。
canal 挂载从库:相当于直接放弃了高可用问题。
1.3.分库分表场景
数据库数量的增加,也相应的增加了canal的维护成本,因为canal是通过binlog获取数据的,所以每一个分片库都需要配置canal
1.4.热点表问题
我们知道获取binlog数据需要保证有序性,canal在保障有序性的前提下为了提高性能,使用的技术是hash表,通过hash结果将不同的表发送到不同的队列分区中,可以做到让每个表都有一个消费者,且最多一个消费者,因为要保证数据的有序性。
这时候一旦消费者处理逻辑复杂,在大量数据同步的场景下,因为表全局有序,一个表只有一个消费者所以很容易造成MQ消息挤压
1.5.数据丢失问题
很多人反馈 binlog 在数据同步的过程中会出现一些逻辑上的问题,导致部分数据丢失,我还没有碰到过
2.canal 现状
和canal作者聊过,canal 研发团队,因为某些原因,已经从阿里离职创业了,canal的很多问题,他们解决也有心无力,但是他们开发了类似于streamset的cloudcanal商业产品。canal 项目相当于死掉了。
这也是小的开源项目悲哀的地方,没钱没人、没技术、没时间、说停就停,就像前两年阿里巴巴对double说停就停了,停了两年多,挺无语的。
3.其他的方案
如果不使用canal 这种基于binlog同步方案获取mysql的增量数据,那么有什么其他解决办法呢?
3.1.仅同步增量数据的场景
场景:需要同步的数据仅有insert没有update
解决办法:可以直接通过JDBC连接mysql,并通过offset进行偏移位控制,直接读取mysql 指定表数据进行同步,根据业务可以接受的延迟时间,增加定时任务获取增量数据
3.2.同步增量和修改数据的场景
场景:需要同步的数据有insert和update以及delete
解决办法:为了保障数据的可追溯,就是更新前是什么,更新后是什么,通常解决办法是增加数据的审计日志表,审计日志表设计是仅有insert操作,可以使用上面的仅同步增量数据方案。
3.3.双写
通过canal 监听binlog日志变更,通常是将数据发送到Kafka给业务方进行处理。那么也可以考虑双写,一个写入数据库,一个写入MQ。
转载请注明:西门飞冰的博客 » canal基于binlog同步方案的局限性和思考