備援,不是備位充數

有備援就無敵?!

古哥
pgsql-tw
Sep 15, 2021

--

資料庫備援在很直覺得思考下,當然是絕對的好事。但凡事都有現實的一面,所以本篇我整理一些在備援上設計思考,讓你的備援更有意義。許多人會把備援侷限在使用什麼技術上,但備援是否有效其實和你多瞭解你的服務設計更為相關。

如果你財大氣粗,或者你不是真正付出金錢或人力成本的人,那疊床架屋的架構就不會是你會關心的問題。如果你的既有觀念是,「有備援,資料庫就不會壞」的話,那很明顯你的資料風險不會是在資料庫系統上。

如果你打算建置備援環境,最好先確認可以派得上用場,不要徒增成本又瞎忙。

本文以 PostgreSQL 為例來作為具體上的想像,也就是 Streaming Replication 的機制,會即時抄寫所有資料庫的變更,在邏輯上可以把 Replication 的資料庫視為相同的資料庫內容。以下所談到的備援思維,你也可以套用到其他的資料庫系統設計上。

成本

首先是成本的部份,是很多人會小看的部份。如果是租用的雲端環境,訂價一般都是2倍的價格;而如果是私有機房的話,則是可能會降低系統資源的使用率。特別因為資料庫通常在資料傳輸的處理量是相對大的,也就是會佔用大量的儲存裝置與網路設備的頻寬,每筆交易所耗用的頻寬和儲存空間至少是2倍,它可能是有效益的成本支出,但絕對不是可以忽略的細節。

相對應比較的對象可能是「備份」,只需要儲存空間,不用常態性佔用主機運算資源。雖然功能上不能完全相互替代,但可以作為成本的想像比較。

你不會只是多一台主機,只是多一個資料庫服務。比較完整的機制,你會需要額外的監控機制,也可能需要切換網路設定,在資料庫的前端程式也需要撰寫容錯的交易機制。以上任何一點沒做到,備援就不會完整,這些都是你在決策的時候就必須考慮的成本。

另外,還有永遠會被刻意忽略的是人力成本。任何備援機制不會憑空出現,也不會完美無瑕,它仍然需要佔用一定程度的維運人力。

效益

這點是大家唯一會在乎的事,備援機制當然有其效用,只是你不一定用得到而已。所以在思考效益的同時,也還是需要同時考慮其成本需求。

  • 政治效益
    簡而言之就是用於宣稱已經盡力強化系統穩定度。這並非幹話,如果能滿足決策者心靈上的安心感,進而用於爭取到更多團隊分潤的話,那麼這點就可以是重要的策略方向。
  • 即時備援
    如同多數人所熟知的情況,當資料庫主機失效時,能夠在最短的時間內接手。但是必須先行瞭解的是,有可能接手不是好的決定。它唯一也是最重要的優勢就是,在備援主機完好的情況下,你擁有接手與不接手的選擇權。
  • 分散流量
    這是備援主機的延伸效益,你可以建立數個備援資料庫,分擔主要資料庫的負載,例如備份、資料查詢、資料分析、批次作業等等,能夠有效提升主要資料庫用於線上交易的處理能量。

不適合的情況

資料庫備援最原始的期待是能處理主機失效的問題,粗略來想是在某個瞬間資料庫突然消失了,備援主機可以立即遞補。但仔細思考的話,資料庫發生問題的情況有很多,備援不一定能夠解決問題,反而讓問題更糟。

在建立備援服務之前,你得先理解,有些事情備援不是最好的做法,甚至不會是能夠達到你的訴求的做法。

  • 主機容錯
    在實體主機的情況下,如果主機失效了,要在短時間建置相同的軟硬體系統並不容易,事先建立備援主機有其必要性。但現在多數服務都已經虛擬化,許多意外的情況在虛擬化層次的的 HA(主機遷移或在另一個 Host 重啓),就已經能夠順利復原。如果你想要避免這種情況發生,那應該把更多心力花在虛擬化的管理機制上,會更有效益。
  • 外部異常
    所謂外部錯誤指的是主機本身是正常的,但因為外部情況異常而造成你以為資料庫服務失效。其中一個常見的情況是網路異常,網路斷線時,如果你的備援服務立即嘗試取代主要服務時,時常會產生 Split-brain 的情況,你會有兩個資料庫都宣稱自己是主要的資料庫。這時候如果前端的 AP 也都分別寫入了交易資料的話,就有可能發生資料不一致的情況。這通常不會是讓人期待產生的結果。另一種情況是大量異常連線造成服務中斷,如果這時候備援主機立即替補上場,也只是多一台主機被打掛而已。

許多工具會提供方便的 Auto-Failover 功能,但請注意,可以 Auto-Failover,並不代表不會再次 Fail。我的建議是越重要的服務,越不應該 Auto-Failover。在系統建置過程中,現實上的限制或弱點應該多數都能被發現,進而建立自動化避免踩雷的機制;而那些在預想以外的情境,你仍然需要專業的人類來做出有效解決問題的判斷。

有限備援

就實際情況來談,在虛擬化時代之後,備援資料庫的必要性已經大幅減少,多數都是為了資料複寫延伸其資料用途而建立。在虛擬化之後,運算資源和儲存資源其實都已經有相對應的 HA 機制了。資料庫主機通常只需要確認重啓的狀態是否正常即可。

因為資源有限,一個備援就是多一倍的資料傳輸和寫入,你需要在儲存與網路資源上投資更多,當然,運算資源也一定多少會被分食。策略上應該是針對重建服務比較困難的主機建立備援服務,這些主機也應該僅佔整體服務的部份比例,而不會是全部。事實上,虛擬化的備份幾乎就取決於備份檔案的傳輸成本而已,更何況有一些備份儲存架構是可以直接掛上 Hypervisor 的,那就幾乎和直接重開機的速度沒有差別。

在資料重建上,備援是幫不上忙的,因為錯誤的資料在備援資料庫上當然也是錯的。你需要建立的是 PITR 的全時資料還原機制。

如果資料庫是被打掛的,那你需要檢討的是網路安全或程式設計的問題,再多一個備援也只是多證明一次你的系統架構需要重新檢視而已。

在決策建立資料庫備援服務時,明確列出備援情況再建置,在現代的系統環境下,會是更有意義的事。

PostgreSQL Streaming Replication

在你已經思考過以上說明的內容之後,再來瞭解資料庫的抄寫備援機制會更好。在市場上有許多協助 PostgreSQL 管理備援的工具,都是基於 Streaming Replication 來完成的,建議最好先熟悉以原生的 PostgreSQL 環境手動操作過之後,再去嘗試其他的管理工具,會更清楚你要的是什麼。

--

--

古哥
pgsql-tw

解決不了問題,就解決提出問題的人