最近在梳理Consul健康檢查邏輯的時(shí)候,也發(fā)現(xiàn)了一些潛在的問題,這些問題雖然不會(huì)直接造成業(yè)務(wù)故障,但是在故障發(fā)生的時(shí)候還是存在較高的概率導(dǎo)致一些意料之外的影響。
從解耦的設(shè)計(jì)思路來(lái)看,我們希望很多事情能夠做到多重校驗(yàn),即設(shè)計(jì)一個(gè)組件的時(shí)候,如何涉及外部環(huán)節(jié),我們需要從故障設(shè)計(jì)的角度來(lái)進(jìn)行考量,即認(rèn)為我們的服務(wù)或者組件是存在故障的風(fēng)險(xiǎn),按照這個(gè)來(lái)設(shè)計(jì),就能夠?qū)е乱恍┖罄m(xù)設(shè)計(jì)中的尷尬。
對(duì)于Consul的邏輯檢查,說(shuō)簡(jiǎn)單也可以,說(shuō)復(fù)雜確實(shí)需要補(bǔ)充很多的內(nèi)容,以下是在之前整理的一版基礎(chǔ)上進(jìn)行細(xì)化得到的。
MySQL在Consul服務(wù)中的健康檢查邏輯
整體上腳本分為兩個(gè)部分,第一個(gè)部分是判斷數(shù)據(jù)庫(kù)的角色,第二個(gè)部分根據(jù)讀寫策略進(jìn)行補(bǔ)充。
數(shù)據(jù)庫(kù)角色判斷的邏輯如下:

第二個(gè)部分是根據(jù)角色和讀寫策略完成健康檢查,如果正常返回0,否則返回2

我來(lái)做一下解釋,目前的讀寫分離如果是主庫(kù),則為write,如果是查詢操作主從庫(kù)均可讀,則為Mixed_Read,如果查詢只在從庫(kù)可行,則為Read_only.

在這個(gè)基礎(chǔ)上我們來(lái)梳理一下這種策略的潛在風(fēng)險(xiǎn)。

既然設(shè)置了健康檢查,我們就不能指望服務(wù)狀態(tài)始終不變,如果發(fā)生了服務(wù)宕機(jī),在服務(wù)重啟后,如果因?yàn)榻】禉z查策略導(dǎo)致主從混寫,那這個(gè)問題就嚴(yán)重了。
所以在目前的檢查模式下,如果主庫(kù)宕機(jī),在重啟服務(wù)前需要暫時(shí)停止健康檢查邏輯,否則就會(huì)造成數(shù)據(jù)錯(cuò)亂的嚴(yán)重問題。
如果從庫(kù)宕機(jī),則健康檢查邏輯還是比較穩(wěn)定,除了原本的讀混合模式會(huì)漂移到主庫(kù)之外,其他的部分沒有變化。
如果是主從復(fù)制失敗,則問題依然是可控的。


做完這些分析之后,我覺得目前的健康檢查邏輯是存在潛在風(fēng)險(xiǎn)的,因?yàn)橛行┉h(huán)節(jié)需要依賴人工的檢查,因?yàn)橐坏┦д`,就會(huì)造成數(shù)據(jù)問題。所以在這一點(diǎn)上我覺得健康檢查的邏輯需要進(jìn)行補(bǔ)充和整改。
我們可以換一個(gè)角度來(lái)考慮,就是什么時(shí)候應(yīng)該會(huì)發(fā)生健康檢查狀態(tài)的變化,目前梳理了下主要有以下幾種。

除非主庫(kù)宕機(jī),其實(shí)我們是不希望域名頻繁的做切換的,如果發(fā)生切換,主要有兩個(gè)場(chǎng)景,一個(gè)是異常宕機(jī),另外一個(gè)就是基于ACL的key-value檢測(cè)。

從這個(gè)角度來(lái)看,域名服務(wù)是相對(duì)恒定的,實(shí)時(shí)的檢測(cè)其實(shí)都對(duì)于每一次檢測(cè)都是實(shí)時(shí)的,如果出現(xiàn)超時(shí),連接異常等情況,其實(shí)是盡可能希望在當(dāng)前域名范圍內(nèi)處理,畢竟這個(gè)時(shí)候域名和IP僅僅的連接的形式不同而已,如果要建立更加穩(wěn)定的健康檢查,應(yīng)該是ACL+實(shí)時(shí)檢測(cè)組合的方案,基本思路就是ACL檢測(cè)優(yōu)先,在服務(wù)故障切換之后,會(huì)補(bǔ)充檢測(cè)健康檢查的邏輯,把這兩個(gè)部分整合起來(lái)處理,就會(huì)避免那些意料之外的異常域名切換。
相關(guān)鏈接:
個(gè)人新書 《MySQL DBA工作筆記》