利用 DNS SRV 記錄為 Postfix 提供負載平衡
2011 年 3 月,蘋果公司提出 RFC 6186,描述了如何利用域名系統服務(DNS SRV)記錄來查找電子郵件的提交以及訪問服務。現在 Postfix 從 3.8.0 版本開始支持 RFC 中提出的設計。這個新增功能讓你可以使用 DNS SRV 記錄進行負載分配和自動配置。
DNS SRV 記錄的形態
DNS SRV 記錄定義在 RFC 2782 中,它指定在區域文件中,並且包含了服務名稱、傳輸協議規範、優先順序、權重、埠,以及提供該服務的主機。
_submission._tcp SRV 5 10 50 bruce.my-domain.com.
欄位 | 值 | 意義 |
---|---|---|
服務名稱 | submission |
服務名為 submission |
傳輸協議規範 | tcp |
本服務使用 TCP 協議 |
優先順序 | 5 |
伺服器優先順序設為 5(數值越小,優先順序越高) |
權重 | 10 |
伺服器應承擔的負載部分 |
埠 | 50 |
伺服器監聽連接的埠 |
目標 | bruce.my-domain.com. |
提供此服務的伺服器名稱 |
記錄解釋
伺服器選擇演算法
客戶端應該按照 RFC 2782 中描述的方式解析 SRV 記錄。這意味著,首先嘗試聯繫擁有最高優先順序(最小的優先順序數字)的伺服器。如果該伺服器無回應,那麼重試聯繫擁有同樣或者更低優先順序的下一台伺服器。當有多台伺服器擁有同樣優先順序的時候,應隨機選擇其中一台,但是必須確保選擇記錄的概率符合下列公式:
其中 i
是 SRV 記錄的標識,k
是具有相同優先順序的 SRV 記錄的數量。
在現實中,這意味著如果你有兩台伺服器,其中一台的處理能力是另一台的三倍,那麼你應該給第一台伺服器的權重賦於另一台三倍的值。這樣就能保證更強大的伺服器會接收到大約 75% 的客戶端請求,而另一台接收大約 25% 的請求。
這些原則使得 SRV 記錄能夠同時作為客戶端自動配置及在伺服器之間分配工作負載的工具。
看看以下這個記錄的例子:
_submission._tcp SRV 0 0 2525 server-one
_submission._tcp SRV 1 75 2625 server-two
_submission._tcp SRV 1 25 2625 server-three
這裡 server-one
總是會被首選來進行聯繫。如果 server-one
無回應,客戶端就會將剩下優先順序為 1 的兩個記錄順序打亂,生成一個從 0 到 100 的隨機數,如果第一條記錄的運行總和大於或者等於這個隨機數,它就會嘗試去聯繫這個記錄。否則,客戶端會倒序聯繫所有伺服器。注意,客戶端會向它優先成功連接的伺服器發送請求。
示例配置
請考慮以下這種情況。你想為大量的電腦配置 Postfix,使其通過公司的郵件伺服器利用 SRV 記錄轉發外部電郵。為了達到這個目標,你需要在每台電腦的 Postfix 中配置 relayhost
參數,即郵件用戶代理(MUA)。如果將 relayhost
參數的值設置為 $mydomain
,你的機器將開始為你的域名查找 MX 記錄,並嘗試按照它們的優先順序順序發送郵件。這種方法雖然有效,但是可能會遇到負載平衡問題。Postfix 會使用優先順序最高的伺服器,直到其變為無響應才會聯繫其他備用伺服器。此外,如果你在環境中使用了動態分配的埠,你無法指明哪個埠正在被特定的伺服器使用。使用 SRV 記錄,你可以應對這些挑戰,並在需要改變伺服器埠的時候維持伺服器的平滑運行。
區域文件
為了使得 DNS 伺服器提供信息給客戶端,可以參考以下使用伺服器 server-one
、server-two
、server-three
作為中繼,並把伺服器 server-four
配置為接收測試郵件的區域文件示例。
$TTL 3600
@ IN SOA example-domain.com. root.example-domain.com. (
1571655122 ; 區域文件的序列號
1200 ; 刷新時間
180 ; 發生問題時的重試時間
1209600 ; 過期時間
10800 ) ; 查詢失敗時的最大緩存時間
;
IN NS ns1
IN A 192.168.2.0
;
ns1 IN A 192.168.2.2
server-one IN A 192.168.2.4
server-two IN A 192.168.2.5
server-three IN A 192.168.2.6
server-four IN A 192.168.2.7
_submission._tcp SRV 0 0 2525 server-one
_submission._tcp SRV 1 50 2625 server-two
_submission._tcp SRV 1 50 2625 server-three
@ MX 0 server-four
Postfix MUA 配置
設置客戶端機器去查找 SRV 記錄:
use_srv_lookup = submission
relayhost = example-domain.com:submission
通過這個配置,你的客戶端機器上的 Postfix 實例會聯絡到 example-domain
的 DNS 伺服器,然後獲取郵件提交的 SRV 記錄。在這個例子中,server-one
有最高的優先順序,Postfix 會先試圖連接它。然後,Postfix 隨機的選擇剩下的兩個伺服器其中一個去嘗試連接。這個配置確保了大約有 50% 的機會會優先聯繫到伺服器一。注意,SRV 記錄的權重值並不等同於百分比。你也可以用 1 和 1 這樣的值達到同樣的目標。
同時,Postfix 也知道 server-one
在監聽 2525 埠,而 server-two
在監聽 2625 埠。如果你正在緩存檢索到的 DNS 記錄,並且你動態改變 SRV 記錄,那麼設置一個低的生存時間(TTL)對你的記錄是很重要的。
整套設置
你可以通過下面的方式嘗試這個配置,包含 podman 和在此處提供的 compose 文件:
$ git clone https://github.com/TomasKorbar/srv_article
$ cd srv_article/environment
$ podman-compose up
$ podman exec -it article_client /bin/bash
root@client # ./senddummy.sh
root@client # exit
完成配置之後,你可以檢查日誌,查看郵件是否經過 server-one
並最終投遞到 server-four
。
$ podman stop article_server1
$ podman exec -it article_client /bin/bash
root@client # ./senddummy.sh
root@client # ./senddummy.sh
root@client # ./senddummy.sh
root@client # ./senddummy.sh
root@client # ./senddummy.sh
root@client # ./senddummy.sh
root@client # exit
現在 server-one
已經關閉了,這六封郵件將會由 server-two
或者 server-three
中轉發出去。
仔細看一下 Dockerfiles 以更深地理解這個配置。
通過執行:$ podman-compose down
完成示例的操作。
(題圖:DA/241079fe-58d6-4dc6-8801-f0fd19dfd64b)
via: https://fedoramagazine.org/using-postfix-dns-srv-record-resolution-feature/
作者:Tomáš Korbař 選題:lujun9972 譯者:ChatGPT 校對:wxy
本文轉載來自 Linux 中國: https://github.com/Linux-CN/archive