Haproxy 詳解以及基於 Haproxy 的高可用實戰
1.Haproxy 與 Keepalived VRRP 介紹
軟件:haproxy---主要是做負載均衡的7層,也可以做4層負載均衡
apache也可以做7層負載均衡,但是很麻煩。實際工作中沒有人用。
負載均衡是通過OSI協議對應的
7層負載均衡:用的7層http協議,
4層負載均衡:用的是tcp協議加端口號做的負載均衡
------------------------------------------------------------------------------------------------------------------------------
ha-proxy概述
ha-proxy是一款高性能的負載均衡軟件。因爲其專注於負載均衡這一些事情,因此與nginx比起來在負載均衡這件事情上做更好,更專業。
ha-proxy的特點
ha-proxy 作爲目前流行的負載均衡軟件,必須有其出色的一面。下面介紹一下ha-proxy相對LVS,Nginx等負載均衡軟件的優點。
•支持tcp / http 兩種協議層的負載均衡,使得其負載均衡功能非常豐富。
•支持8種左右的負載均衡算法,尤其是在http模式時,有許多非常實在的負載均衡算法,適用各種需求。
•性能非常優秀,基於單進程處理模式(和Nginx類似)讓其性能卓越。
•擁有一個功能出色的監控頁面,實時瞭解系統的當前狀況。
•功能強大的ACL支持,給用戶極大的方便。
haproxy算法:
1.roundrobin
基於權重進行輪詢,在服務器的處理時間保持均勻分佈時,這是最平衡,最公平的算法.此算法是動態的,這表示其權重可以在運行時進行調整.
2.static-rr
基於權重進行輪詢,與roundrobin類似,但是爲靜態方法,在運行時調整其服務器權重不會生效.不過,其在後端服務器連接數上沒有限制
3.leastconn
新的連接請求被派發至具有最少連接數目的後端服務器.
keepalived是什麼
keepalived是集羣管理中保證集羣高可用的一個服務軟件,用來防止單點故障。
keepalived工作原理
keepalived是以VRRP協議爲實現基礎的,VRRP全稱Virtual Router Redundancy Protocol,即虛擬路由冗餘協議。(雲服務器不支持VRRP)
虛擬路由冗餘協議,可以認爲是實現高可用的協議,即將N臺提供相同功能的路由器組成一個路由器組,這個組裏面有一個master和多個backup,master上面有一個對外提供服務的vip(該路由器所在局域網內其他機器的默認路由爲該vip),master會發組播,當backup收不到vrrp包時就認爲master宕掉了,這時就需要根據VRRP的優先級來選舉一個backup當master。這樣的話就可以保證路由器的高可用了。
keepalived主要有三個模塊,分別是core、check和vrrp。core模塊爲keepalived的核心,負責主進程的啓動、維護以及全局配置文件的加載和解析。check負責健康檢查,包括常見的各種檢查方式。vrrp模塊是來實現VRRP協議的。
=========================================================================================
腦裂(裂腦):
Keepalived的BACKUP主機在收到不MASTER主機報文後就會切換成爲master,如果是它們之間的通信線路出現問題,無法接收到彼此的組播通知,但是兩個節點實際都處於正常工作狀態,這時兩個節點均爲master強行綁定虛擬IP,導致不可預料的後果,這就是腦裂。
解決方式:
1、添加更多的檢測手段,比如冗餘的心跳線(兩塊網卡做健康監測),ping對方等等。儘量減少"裂腦"發生機會。(指標不治本,只是提高了檢測到的概率);
2、做好對裂腦的監控報警(如郵件及手機短信等或值班).在問題發生時人爲第一時間介入仲裁,降低損失。例如,百度的監控報警短倍就有上行和下行的區別。報警消息發送到管理員手機上,管理員可以通過手機回覆對應數字或簡單的字符串操作返回給服務器.讓服務器根據指令自動處理相應故障,這樣解決故障的時間更短.
3、爆頭,將master停掉。然後檢查機器之間的防火牆。網絡之間的通信
2. 項目準備
準備四臺虛擬機,兩臺做代理服務器,兩臺做真實服務器(真實服務器只是用來進行 web 測試) 1、選擇兩臺 Haproxy 服務器作爲代理服務器(一臺 master 一臺 backup)。真實服務器需要 nginx 來提供 web 服務進行測試 2、給兩臺代理服務器安裝 keepalived 製作高可用生成 VIP 3、配置 nginx 的負載均衡 以上兩臺 nginx 服務器配置文件一致 根據站點分區進行調度 配置 upstream 文件
[root@master ~]# 192.168.13.128 主節點
[root@backup ~]# 192.168.13.129 備用節點
[root@real-server1 ~]# 192.168.13.133 第一臺真實服務器
[root@real-server2 ~]# 192.168.13.137 第二臺真實服務器
我們也可以養成一個良好的習慣,不管用不用的到,我們都要對 IP 進行解析,不僅是爲了自己方便,也便於其他人。
所有虛擬機
[root@master ~]# cat /etc/hosts
127.0.0.1 localhost
192.168.13.128 master
192.168.13.129 backup
192.168.13.133 real-server1
192.168.13.137 real-server2
3.nginx 安裝
只給兩臺真實服務器配置安裝 nginx ,所有機器關閉防火牆和 selinux
192.168.13.133
[root@real-server1 ~]# systemctl stop firewalld && setenforce 0
[root@real-server1 ~]# cd /etc/yum.repos.d/
[root@real-server1 yum.repos.d]# vim nginx.repo
[nginx-stable]
name=nginx stable repo
baseurl=http://nginx.org/packages/centos/$releasever/$basearch/
gpgcheck=0
enabled=1
[root@real-server1 yum.repos.d]# yum install yum-utils -y
[root@real-server1 yum.repos.d]# yum install nginx -y
[root@real-server1 yum.repos.d]# systemctl start nginx #啓動
[root@real-server1 ~]# echo "this is first real-server" > /usr/share/nginx/html/index.html #方便區分,看出效果
[root@real-server1 ~]# vim /etc/nginx/nginx.conf
keepalive_timeout 0; #設置長鏈接
[root@real-server1 ~]# nginx -s reload
192.168.13.138
[root@real-server2 ~]# systemctl stop firewalld && setenforce 0
[root@real-server2 ~]# cd /etc/yum.repos.d/
[root@real-server2 yum.repos.d]# vim nginx.repo
[nginx-stable]
name=nginx stable repo
baseurl=http://nginx.org/packages/centos/$releasever/$basearch/
gpgcheck=0
enabled=1
[root@real-server2 yum.repos.d]# yum install yum-utils -y
[root@real-server2 yum.repos.d]# yum install nginx -y
[root@real-server2 yum.repos.d]# systemctl start nginx #啓動
[root@real-server2 ~]# echo "this is second real-server"> /usr/share/nginx/html/index.html
[root@real-server2 ~]# vim /etc/nginx/nginx.conf
keepalive_timeout 0;#默認keepalive_timeout 65;
[root@real-server2 ~]# nginx -s reload
#修改後端nginx服務器的長連接是爲了方便測試
4. 調度器配置 Haproxy(主 / 備)都執行
192.168.13.128
[root@ha-proxy-master ~]# yum -y install haproxy
[root@ha-proxy-master ~]# cp -rf /etc/haproxy/haproxy.cfg{,.bak} #備份
[root@master ~]# sed -i -r '/^[ ]*#/d;/^$/d' /etc/haproxy/haproxy.cfg #修改配置文件去掉註釋,或者你可以直接複製我的代碼
[root@ha-proxy-master ~]# vim /etc/haproxy/haproxy.cfg
global
log 127.0.0.1 local2 info
pidfile /var/run/haproxy.pid
maxconn 4000 #優先級低
user haproxy
group haproxy
daemon #以後臺形式運行ha-proxy
nbproc 1 #工作進程數量 cpu內核是幾就寫幾
defaults
mode http #工作模式 http ,tcp 是 4 層,http是 7 層
log global
retries 3 #健康檢查。3次連接失敗就認爲服務器不可用,主要通過後面的check檢查
option redispatch #服務不可用後重定向到其他健康服務器。
maxconn 4000 #優先級中
contimeout 5000 #ha服務器與後端服務器連接超時時間,單位毫秒ms
clitimeout 50000 #客戶端超時
srvtimeout 50000 #後端服務器超時
listen stats
bind *:81
stats enable
stats uri /haproxy #使用瀏覽器訪問 http://192.168.246.169/haproxy,可以看到服務器狀態
stats auth yjssjm:123 #用戶認證,客戶端使用elinks瀏覽器的時候不生效
frontend web
mode http
bind *:80 #監聽哪個ip和什麼端口
option httplog #日誌類別 http 日誌格式
acl html url_reg -i \.html$ #1.訪問控制列表名稱html。規則要求訪問以html結尾的url(可選)
use_backend httpservers if html #2.如果滿足acl html規則,則推送給後端服務器httpservers
default_backend httpservers #默認使用的服務器組
backend httpservers #名字要與上面的名字必須一樣
balance roundrobin #負載均衡的方式
server http1 192.168.13.133:80 maxconn 2000 weight 1 check inter 1s rise 2 fall 2
server http2 192.168.13.137:80 maxconn 2000 weight 1 check inter 1s rise 2 fall 2
192.168.13.129
[root@ha-proxy-master ~]# yum -y install haproxy
[root@ha-proxy-master ~]# cp -rf /etc/haproxy/haproxy.cfg{,.bak} #備份
[root@master ~]# sed -i -r '/^[ ]*#/d;/^$/d' /etc/haproxy/haproxy.cfg #修改配置文件去掉註釋,或者你可以直接複製我的代碼
[root@ha-proxy-master ~]# vim /etc/haproxy/haproxy.cfg
global
log 127.0.0.1 local2 info
pidfile /var/run/haproxy.pid
maxconn 4000 #優先級低
user haproxy
group haproxy
daemon #以後臺形式運行ha-proxy
nbproc 1 #工作進程數量 cpu內核是幾就寫幾
defaults
mode http #工作模式 http ,tcp 是 4 層,http是 7 層
log global
retries 3 #健康檢查。3次連接失敗就認爲服務器不可用,主要通過後面的check檢查
option redispatch #服務不可用後重定向到其他健康服務器。
maxconn 4000 #優先級中
contimeout 5000 #ha服務器與後端服務器連接超時時間,單位毫秒ms
clitimeout 50000 #客戶端超時
srvtimeout 50000 #後端服務器超時
listen stats
bind *:81
stats enable
stats uri /haproxy #使用瀏覽器訪問 http://192.168.246.169/haproxy,可以看到服務器狀態
stats auth yjssjm:123 #用戶認證,客戶端使用elinks瀏覽器的時候不生效
frontend web
mode http
bind *:80 #監聽哪個ip和什麼端口
option httplog #日誌類別 http 日誌格式
acl html url_reg -i \.html$ #1.訪問控制列表名稱html。規則要求訪問以html結尾的url(可選)
use_backend httpservers if html #2.如果滿足acl html規則,則推送給後端服務器httpservers
default_backend httpservers #默認使用的服務器組
backend httpservers #名字要與上面的名字必須一樣
balance roundrobin #負載均衡的方式
server http1 192.168.13.133:80 maxconn 2000 weight 1 check inter 1s rise 2 fall 2
server http2 192.168.13.137:80 maxconn 2000 weight 1 check inter 1s rise 2 fall 2
其中你需要修改的地方
如果我們訪問 http://192.168.13.144:81/haproxy
頁面主要參數解釋
Queue
Cur: current queued requests //當前的隊列請求數量
Max:max queued requests //最大的隊列請求數量
Limit://隊列限制數量
Errors
Req:request errors //錯誤請求
Conn:connection errors //錯誤的連接
Server列表:
Status:狀態,包括up(後端機活動)和down(後端機掛掉)兩種狀態
LastChk: 持續檢查後端服務器的時間
Wght: (weight) : 權重
========================================================
如果出現bind失敗的報錯,執行下列命令
setsebool -P haproxy_connect_any=1
5.Keepalived 實現調度器 HA(兩個節點都需要下載)
注:主 / 備調度器均能夠實現正常調度 1. 主 / 備調度器安裝軟件
192.168.13.128
[root@localhost ~]# yum install -y keepalived
[root@localhost ~]# cp /etc/keepalived/keepalived.conf /etc/keepalived/keepalived.conf.bak #備份
[root@localhost ~]# vim /etc/keepalived/keepalived.conf
! Configuration File for keepalived
global_defs {
router_id directory1 #只是名字而已,輔節點改爲directory2(兩個名字一定不能一樣)
}
vrrp_instance VI_1 {
state MASTER #定義主還是備,備用的話寫backup
interface ens33 #VIP綁定接口
virtual_router_id 80 #整個集羣的調度器一致(在同一個集羣)
priority 100 #(優先權)back改爲50(50一間隔)
advert_int 1 #發包
authentication {
auth_type PASS #主備節點認證
auth_pass 1111
}
virtual_ipaddress {
192.168.13.144/24 #VIP(自己網段的)
}
}
192.168.13.129
[root@backup ~]# yum install -y keepalived
[root@backup ~]# mv /etc/keepalived/keepalived.conf /etc/keepalived/keepalived.conf.bak
[root@backup ~]# vim /etc/keepalived/keepalived.conf
! Configuration File for keepalived
global_defs {
router_id directory2
}
vrrp_instance VI_1 {
state BACKUP #設置爲backup
interface ens33
nopreempt #設置到back上面,不搶佔資源
virtual_router_id 80
priority 50 #輔助改爲50
advert_int 1 #檢測間隔1s
authentication {
auth_type PASS
auth_pass 1111 #認證類型和密碼主備一樣,要不然無法互相認證
}
virtual_ipaddress {
192.168.13.144/24 #搶佔的VIP也一樣
}
}
- 啓動 KeepAlived(主備均啓動)
[root@master ~]# systemctl start keepalived
[root@backup ~]# systemctl start keepalived
開機自啓(可以不設置)
[root@master ~]# systemctl enable keepalived
[root@backup ~]# systemctl enable keepalived
注意:如果你網頁訪問不到,可能是配置文件出錯了。如果你是直接複製本文章的代碼,建議你將註釋都去掉,有時候可能你的輸入法的問題,導致配置文件出現一些多餘的空格之類的。訪問你自己設置的 VIP 192.168.13.144
查看兩個節點服務器,你會發現 VIP 在主節點
如果這個時候主節點服務器宕機了(我們把服務停止了用來測試),VIP 會自己漂移到備用節點上。
但是用戶訪問時卻感覺不到
網頁照樣可以繼續使用,這就是高可用性。
5. 基於 nginx 的高可用性
以上我們只是實現了高可用,基於 Haproxy 的前提是 Haproxy 服務是正常。如果有突發情況使得 nginx 服務不能啓動,但是我們的 keepalived 服務是正常,這個時候用戶是訪問不到的,VIP 也不會自動漂移到備用的節點服務器上。所以我們需要寫一些代碼來判斷一下 Haproxy 服務是不是正常,如果不正常的話我們就將 Haproxy 服務關掉,然後實現 VIP 的漂移,這個時候用戶就不會出現無法訪問的情況了。
思路:
讓Keepalived以一定時間間隔執行一個外部腳本,腳本的功能是當Haproxy失敗,則關閉本機的Keepalived
[root@master ~]# vim /etc/keepalived/check_haproxy_status.sh
#!/bin/bash
/usr/bin/curl -I http://localhost &>/dev/null
if [ $? -ne 0 ];then
# /etc/init.d/keepalived stop
systemctl stop keepalived
fi
[root@localhost ~]# chmod a+x /etc/keepalived/check_haproxy_status.sh #一定要加執行權限
(2)keepalived使用script
[root@localhost ~]# vim /etc/keepalived/keepalived.conf
! Configuration File for keepalived
global_defs {
router_id director1
}
vrrp_script check_haproxy {
script "/etc/keepalived/check_haproxy_status.sh"
interval 5 #每5秒執行一次
}
vrrp_instance VI_1 {
state MASTER
interface ens33
virtual_router_id 80
priority 100
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
virtual_ipaddress {
192.168.13.144/24
}
track_script {
check_haproxy
}
}
注:必須先啓動Haproxy,再啓動keepalived,建議備用節點也添加上.
測試訪問:將 keepalived 集羣的主節點的 nginx 服務關閉,查看 vip 是否漂移,如果漂移,即成功
- 配置 haproxy 的日誌
兩臺機器都配置 haproxy 的日誌: 需要打開註釋並添加
[root@master ~]# vim /etc/rsyslog.conf
# Provides UDP syslog reception #由於haproxy的日誌是用udp傳輸的,所以要啓用rsyslog的udp監聽
$ModLoad imudp
$UDPServerRun 514
找到 #### RULES #### 下面添加
local2.* /var/log/haproxy.log
[root@master ~]# systemctl restart rsyslog
[root@master ~]# systemctl restart haproxy
[root@master ~]# tail -f /var/log/haproxy.log #實時查看日誌
Mar 19 12:53:27 localhost haproxy[73866]: Proxy stats started.
Mar 19 12:53:27 localhost haproxy[73866]: Proxy web started.
Mar 19 12:53:27 localhost haproxy[73866]: Proxy httpservers started.
本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源:https://mp.weixin.qq.com/s/oxGa6RFXwOeYfRt2rHlegw