目录
Orchestrator
是一款开源的MySQL数据库高可用HA工具。
它稳定可靠,通过分布式的集群部署模式,自身具备容灾能力。
它功能强大,通过周期执行探测SQL,抓取MySQL 实例的基本信息,包括配置信息、复制状态等,可以得到MySQL的拓扑结构topology。并且,可以根据拓扑结构诊断故障analysis failure。
目前,在Github开源社区已有star
4.7k+。
本文对Orchestrator
的基本工作原理做简单介绍。
以个人的理解,从整体功能,Orchestrator
分 三大部分:
- 实例探测 (instances discover/poll)
- 故障分析(failure analysis)
- 故障恢复(failure recovery)
下面对每一部分做下说明。
1.实例探测 (instances discover/poll)
Orchestrator
会对托管的每个MySQL集群实例,进行周期探测。说探测,实际就是,在MySQL实例上执行探测SQL,抓取实例基本信息。例如,show slave status
, show slave hosts
,show master status
, show global status like 'Uptime'
等等。
实例探测周期由InstancePollSeconds
定义,默认是5s。
在实现上,为了保证实例探测的及时性,采用队列 Queue + 生产者/消费者模式。
首先定义一个Queue
用于需要探测的实例。
discoveryQueue = discovery.CreateOrReturnQueue("DEFAULT")
接着,将需要探测的实例push到队列,具体实现在onHealthTick()
中。
最后,由消费者(一组goroutine) 进行探测 discovery。具体见handleDiscoveryRequests()
。
func handleDiscoveryRequests() {
discoveryQueue = discovery.CreateOrReturnQueue("DEFAULT")
// create a pool of discovery workers
for i := uint(0); i < config.Config.DiscoveryMaxConcurrency; i++ {
go func() {
for {
instanceKey := discoveryQueue.Consume()
// Possibly this used to be the elected node, but has
// been demoted, while still the queue is full.
if !IsLeaderOrActive() {
log.Debugf("Node apparently demoted. Skipping discovery of %+v. "+
"Remaining queue size: %+v", instanceKey, discoveryQueue.QueueLen())
discoveryQueue.Release(instanceKey)
continue
}
DiscoverInstance(instanceKey)
discoveryQueue.Release(instanceKey)
}
}()
}
}
2.故障分析(failure analysis)
通过第一部分的实例周期探测,已经抓取到MySQL 集群的拓扑结构topology,实例之间的复制信息等。
接下来,基于这些信息,就可以诊断故障。
具体过程实现在GetReplicationAnalysis()
。
例如,根据主库存活情况、从库存活和复制状态,其中故障类型如下:
如果主库异常,并且没有从库,判定为DeadMasterWithoutReplicas
:
if a.IsMaster && !a.LastCheckValid && a.CountReplicas == 0 {
a.Analysis = DeadMasterWithoutReplicas
a.Description = "Master cannot be reached by orchestrator and has no replica"
如果主库异常,并且所有从库存活且复制异常,判定为DeadMaster
:
if a.IsMaster && !a.LastCheckValid && a.CountValidReplicas == a.CountReplicas && a.CountValidReplicatingReplicas == 0 {
a.Analysis = DeadMaster
a.Description = "Master cannot be reached by orchestrator and none of its replicas is replicating"
如果主库异常,并且所有从库异常,且所有从库复制异常,判定为DeadMasterAndReplicas
:
if a.IsMaster && !a.LastCheckValid && a.CountReplicas > 0 && a.CountValidReplicas == 0 && a.CountValidReplicatingReplicas == 0 {
a.Analysis = DeadMasterAndReplicas
a.Description = "Master cannot be reached by orchestrator and none of its replicas is replicating"
如果主库异常,并且部分从库异常,且所有从库复制异常,判定为DeadMasterAndSomeReplicas
:
if a.IsMaster && !a.LastCheckValid && a.CountValidReplicas < a.CountReplicas && a.CountValidReplicas > 0 && a.CountValidReplicatingReplicas == 0 {
a.Analysis = DeadMasterAndSomeReplicas
a.Description = "Master cannot be reached by orchestrator; some of its replicas are unreachable and none of its reachable replicas is replicating"
}
3.故障恢复(failure recovery)
诊断出故障之后,对于可以进行恢复的,接下来就是故障恢复。
为什么说是,“可以恢复的”?
这是因为,对于某些场景,例如,主库故障,但没有存活从库的情况,是无法进行恢复的。
故障恢复的入口函数是executeCheckAndRecoverFunction()
故障恢复过程如下:
- 停止所有从库的复制
- 选出新主库
- 重建拓扑
- 提升新主库
每个步骤都可以展开一个小节,在这里就不具体阐述了,有兴趣的可以具体看下代码实现。
4.总结
本文主要介绍了Orchestrator
基本工作原理,相信看完之后,一定会有所收获。如果想要了解更多关于Orchestrator
的信息,可以前往该开源项目
Github地址 Orchestrator查看。