通過(guò)分析主從庫(kù)間次數(shù)據(jù)同步的過(guò)程,你可以看到,一次全量復(fù)制中,對(duì)于主庫(kù)來(lái)說(shuō),需要完成兩個(gè)耗時(shí)的操作:生成 RDB 文件和傳輸 RDB 文件。
如果從庫(kù)數(shù)量很多,而且都要和主庫(kù)進(jìn)行全量復(fù)制的話,就會(huì)導(dǎo)致主庫(kù)忙于 fork 子進(jìn)程生成 RDB 文件,進(jìn)行數(shù)據(jù)全量復(fù)制。fork 這個(gè)操作會(huì)阻塞主線程處理正常請(qǐng)求,從而導(dǎo)致主庫(kù)響應(yīng)應(yīng)用程序的請(qǐng)求速度變慢。此外,傳輸 RDB 文件也會(huì)占用主庫(kù)的網(wǎng)絡(luò)帶寬,同樣會(huì)給主庫(kù)的資源使用帶來(lái)壓力。那么,有沒(méi)有好的解決方法可以分擔(dān)主庫(kù)壓力呢?
其實(shí)是有的,這就是“主 - 從 - 從”模式。
在剛才介紹的主從庫(kù)模式中,所有的從庫(kù)都是和主庫(kù)連接,所有的全量復(fù)制也都是和主庫(kù)進(jìn)行的?,F(xiàn)在,我們可以通過(guò)“主 - 從 - 從”模式將主庫(kù)生成 RDB 和傳輸 RDB 的壓力,以級(jí)聯(lián)的方式分散到從庫(kù)上。
簡(jiǎn)單來(lái)說(shuō),我們?cè)诓渴鹬鲝募旱臅r(shí)候,可以手動(dòng)選擇一個(gè)從庫(kù)(比如選擇內(nèi)存資源配置較高的從庫(kù)),用于級(jí)聯(lián)其他的從庫(kù)。然后,我們可以再選擇一些從庫(kù)(例如三分之一的從庫(kù)),在這些從庫(kù)上執(zhí)行如下命令,讓它們和剛才所選的從庫(kù),建立起主從關(guān)系。
這樣一來(lái),這些從庫(kù)就會(huì)知道,在進(jìn)行同步時(shí),不用再和主庫(kù)進(jìn)行交互了,只要和級(jí)聯(lián)的從庫(kù)進(jìn)行寫(xiě)操作同步就行了,這就可以減輕主庫(kù)上的壓力,如下圖所示:
級(jí)聯(lián)的“主-從-從”模式好了,到這里,我們了解了主從庫(kù)間通過(guò)全量復(fù)制實(shí)現(xiàn)數(shù)據(jù)同步的過(guò)程,以及通過(guò)“主 - 從 - 從”模式分擔(dān)主庫(kù)壓力的方式。那么,一旦主從庫(kù)完成了全量復(fù)制,它們之間就會(huì)一直維護(hù)一個(gè)網(wǎng)絡(luò)連接,主庫(kù)會(huì)通過(guò)這個(gè)連接將后續(xù)陸續(xù)收到的命令操作再同步給從庫(kù),這個(gè)過(guò)程也稱為基于長(zhǎng)連接的命令傳播,可以避免頻繁建立連接的開(kāi)銷。