它在MySQL上面创建了一个事件,每隔10s,就将一个uuid写入到一个view里面,而这个是会记录到binlog中的,虽然我们仍然不能像GTID那样直接定位到一个event,但也能定位到一个10s的区间了,这样我们就能在很小的一个区间里面对比两个MySQL的binlog了。
继续上面的例子,假设c最后一次出现uuid的位置为s1,我们在b里面找到该uuid,位置为s2,然后依次对比后续的event,如果不一致,则可能出现了问题,停止复制。当遍历到c最后一个binlog event之后,我们就能得到此时b下一个event对应的filename以及position了,然后让c指向这个位置开始复制。
使用Pseudo GTID需要slave打开log-slave-update的选项,考虑到GTID也必须打开该选项,所以个人感觉完全可以接受。
后续,笔者自己实现的failover工具,将会采用这种Pseudo GTID的方式实现。
在《MySQL High Availability》这本书中,作者使用了另一种GTID的做法,每次commit的时候,需要在一个表里面记录gtid,然后就通过这个gtid来找到对应的位置信息,只是这种方式需要业务MySQL客户端的支持,笔者不很喜欢,就不采用了。
后记MySQL HA一直是一个水比较深的领域,笔者仅仅列出了一些最近研究的东西,有些相关工具会尽量在go-mysql中实现。
更新经过一段时间的思考与研究,笔者又有了很多心得与收获,设计的MySQL HA跟先前有了很多不一样的地方。后来发现,自己设计的这套HA方案,跟facebook这篇文章几乎一样,加之最近跟facebook的人聊天听到他们也正在大力实施,所以感觉自己方向是对了。
新的HA,我会完全拥抱GTID,比较这玩意的出现就是为了解决原先replication那一堆问题的,所以我不会考虑非GTID的低版本MySQL了。幸运的是,我们项目已经将MySQL全部升级到5.6,完全支持GTID了。
不同于fb那篇文章将mysqlbinlog改造支持semi-sync replication协议,我是将go-mysql的replication库支持semi-sync replication协议,这样就能实时的将MySQL的binlog同步到一台机器上面。这可能就是我和fb方案的唯一区别了。
只同步binlog速度铁定比原生slave要快,毕竟少了执行binlog里面event的过程了,而另外真正的slaves,我们仍然使用最原始的同步方式,不使用semi-sync replication。然后我们通过MHA监控整个集群以及进行故障转移处理。
以前我总认为MHA不好理解,但其实这是一个非常强大的工具,而且真正看perl,发现也还是看的懂得。MHA已经被很多公司用于生产环境,经受了检验,直接使用绝对比自己写一个要划算。所以后续我也不会考虑zookeeper,考虑自己写agent了。