1. 程式人生 > >linux下 使用keepalived 實現nginx 負載均衡+主備高可用

linux下 使用keepalived 實現nginx 負載均衡+主備高可用

1.什麼是負載均衡高可用

        nginx作為負載均衡器,所有請求都到了nginx,可見nginx處於非常重點的位置,如果nginx伺服器宕機後端web服務將無法提供服務,影響嚴重。

        為了遮蔽負載均衡伺服器的宕機,需要建立一個備份機。主伺服器和備份機上都執行高可用(High Availability)監控程式,通過傳送諸如“I am alive”這樣的資訊來監控對方的執行狀況。當備份機不能在一定的時間內收到這樣的資訊時,它就接管主伺服器的服務IP並繼續提供負載均衡服務;當備份管理器又從主管理器收到“I am alive”這樣的資訊時,它就釋放服務IP地址,這樣的主伺服器就開始再次提供負載均衡服務。

  1. keepalived+nginx實現主備
  2. 什麼是keepalived

        keepalived是叢集管理中保證叢集高可用的一個服務軟體,用來防止單點故障。

       Keepalived的作用是檢測web伺服器的狀態,如果有一臺web伺服器宕機,或工作出現故障,Keepalived將檢測到,並將有故障的web伺服器從系統中剔除,當web伺服器工作正常後Keepalived自動將web伺服器加入到伺服器群中,這些工作全部自動完成,不需要人工干涉,需要人工做的只是修復故障的web伺服器。

  1. keepalived工作原理

        keepalived是以VRRP協議為實現基礎的,VRRP全稱Virtual Router Redundancy Protocol,即虛擬路由冗餘協議。

        虛擬路由冗餘協議,可以認為是實現路由器高可用的協議,即將N臺提供相同功能的路由器組成一個路由器組,這個組裡面有一個master和多個backup,master上面有一個對外提供服務的vip(VIP = Virtual IP Address,虛擬IP地址,該路由器所在區域網內其他機器的預設路由為該vip),master會發組播,當backup收不到VRRP包時就認為master宕掉了,這時就需要根據VRRP的優先順序來選舉一個backup當master。這樣的話就可以保證路由器的高可用了。

        keepalived主要有三個模組,分別是core、check和VRRP。core模組為keepalived的核心,負責主程序的啟動、維護以及全域性配置檔案的載入和解析。check負責健康檢查,包括常見的各種檢查方式。VRRP模組是來實現VRRP協議的。

2.實現

環境介紹:

    兩臺nginx,一主一備:192.168.1.117和192.168.1.118

    兩臺tomcat伺服器:192.168.1.117、192.168.1.118

1.首先在兩臺nginx伺服器上安裝keepalived: 可參考之前的教程:https://blog.csdn.net/u013278314/article/details/82772410

2.修改主nginx下/etc/keepalived/keepalived.conf檔案,修改結果如下:

! Configuration File for keepalived

#全域性配置
global_defs {
   notification_email {  #指定keepalived在發生切換時需要傳送email到的物件,一行一個
     [email protected]
   }
   notification_email_from [email protected]  #指定發件人
   #smtp_server XXX.smtp.com                             #指定smtp伺服器地址
   #smtp_connect_timeout 30                               #指定smtp連線超時時間
   router_id LVS_DEVEL                                    #執行keepalived機器的一個標識
}

vrrp_instance VI_1 { 
    state MASTER           #標示狀態為MASTER 備份機為BACKUP
    interface eth0         #設定例項繫結的網絡卡
    virtual_router_id 51   #同一例項下virtual_router_id必須相同
    priority 100           #MASTER權重要高於BACKUP 比如BACKUP為99  
    advert_int 1           #MASTER與BACKUP負載均衡器之間同步檢查的時間間隔,單位是秒
    authentication {       #設定認證
        auth_type PASS     #主從伺服器驗證方式
        auth_pass 8888
    }
    virtual_ipaddress {    #設定vip
        192.168.1.100       #可以多個虛擬IP,換行即可
    }
}

3.修改備nginx下/etc/keepalived/keepalived.conf檔案

   配置備nginx時需要注意:需要修改state為BACKUP , priority比MASTER低,virtual_router_id和master的值一致

! Configuration File for keepalived

#全域性配置
global_defs {
   notification_email {  #指定keepalived在發生切換時需要傳送email到的物件,一行一個
    [email protected]
   }
   notification_email_from [email protected]  				#指定發件人
   #smtp_server XXX.smtp.com                             	#指定smtp伺服器地址
   #smtp_connect_timeout 30                               #指定smtp連線超時時間
   router_id LVS_DEVEL                                    #執行keepalived機器的一個標識
}

vrrp_instance VI_1 { 
    state BACKUP           #標示狀態為MASTER 備份機為BACKUP
    interface eth0         #設定例項繫結的網絡卡
    virtual_router_id 51   #同一例項下virtual_router_id必須相同
    priority 99            #MASTER權重要高於BACKUP 比如BACKUP為99  
    advert_int 1           #MASTER與BACKUP負載均衡器之間同步檢查的時間間隔,單位是秒
    authentication {       #設定認證
        auth_type PASS     #主從伺服器驗證方式
        auth_pass 8888
    }
    virtual_ipaddress {    #設定vip
        192.168.1.100     #可以多個虛擬IP,換行即可
    }
}

4.分配啟動117 和 118 的tomcat,並測試能否訪問

5.修改兩臺伺服器上面的nginx.conf 檔案 配置117 和 118的地址 形成負載均衡

首先修改主機(自己電腦) 域名對映 在 C:\Windows\System32\drivers\etc 下面的hosts檔案 新增: 

      192.168.1.118 www.mytest1.com

      192.168.1.117 www.mytest2.com

cd nginx

vim conf/nginx.conf

新增如下引數:

upstream tomcat1{
     server 192.168.1.117:8080 weight=1;
     server 192.168.1.118:8080 weight=1;
         }

server {
        listen       80;
        server_name  www.mytest1.com;

        location / {
            proxy_pass   http://tomcat1;
            index  index.html index.htm;
        }

先單獨啟動117的nginx伺服器: 測試能否訪問 www.mytest2.com

再單獨啟動118的nginx伺服器: 測試能否訪問 www.mytest1.com

上面沒問題的話,單獨的nginx伺服器和兩臺tomcat伺服器的 負載均衡就好了,我們要實現的是 訪問一個ip或者域名 兩臺nginx的結果都一樣 實現主備 現在兩臺nginx的訪問地址是不一樣的,下面開始主備設定:

同樣在  C:\Windows\System32\drivers\etc 下面的hosts檔案 新增我們上面再nginx設定的 virtual_ipaddress:

192.168.1.100 www.mytest3.com

然後修改主、備nginx的nginx.conf如下:

upstream tomcat1{
     server 192.168.1.117:8080 weight=1;
     server 192.168.1.118:8080 weight=1;
         }

server {
        listen       80;
        server_name  www.mytest3.com;

        location / {
            proxy_pass   http://tomcat1;
            index  index.html index.htm;
        }

然後重啟兩臺伺服器上keepalived和nginx:

117:

          service keepalived start

          ./nginx

118:

          service keepalived start

         ./nginx

啟動完成後使用 sbin/nginx -s reload 檢視哪臺伺服器搶到了 192.168.1.100這個虛擬ip:

118:

117:

從上面可以看到 118主機先獲取 我們設定的ip地址。

下面訪問www.mytest03.com 測試:

 

可以看到訪問成功,到這裡我們的 nginx主備就實現成功

主機宕機

     我們關閉118的keepalived和nginx服務:

     service keepalived stop

    ./nginx -s stop

再次檢視118的ip地址:

可以看到118上面已經沒有1.100這個虛擬地址了,下面我們看看117上面

發現1.100這個ip地址漂到了117上面,我們再次訪問www.mytest3.com測試能否訪問:

測試成功,在nginx主機宕機的情況下面,192.168.1.100這個虛擬ip漂到了117機器上,說明nginx的主備沒問題。

主機恢復:

   下面我們重啟118的keepalived和nginx:

    service keepalived start

    ./nginx

再次檢視ip地址:

發現100這個虛擬地址又回到了118,主機畢竟是主機 一旦恢復 備機就會交出虛擬地址。

解決nginx程序和keepalived不同時存在問題

  1. 問題描述

     keepalived是通過檢測keepalived程序是否存在判斷伺服器是否宕機,如果keepalived程序在但是nginx程序不在了那麼       keepalived是不會做主備切換,所以我們需要寫個指令碼來監控nginx程序是否存在,如果nginx不存在就將keepalived程序殺掉。

在主nginx上需要編寫nginx程序檢測指令碼(check_nginx.sh),判斷nginx程序是否存在,如果nginx不存在就將keepalived程序殺掉,check_nginx.sh內容如下:

#!/bin/bash
# 如果程序中沒有nginx則將keepalived程序kill掉
A=`ps -C nginx --no-header |wc -l`      ## 檢視是否有 nginx程序 把值賦給變數A 
if [ $A -eq 0 ];then                    ## 如果沒有程序值得為 零
       service keepalived stop          ## 則結束 keepalived 程序
fi

將check_nginx.sh拷貝至/etc/keepalived下: cp  check_nginx.sh  /etc/keepalived/

設定指令碼執行許可權:chmod +x /etc/keepalived/check_nginx.sh

將nginx停止,將keepalived啟動,執行指令碼:sh /etc/keepalived/check_nginx.sh

可以看到執行指令碼後 keepalived程序被殺掉了

修改keepalived.conf

修改主nginx的keepalived.conf,新增指令碼定義檢測:

注意下邊紅色標識地方:

#全域性配置

global_defs {

   notification_email {  #指定keepalived在發生切換時需要傳送email到的物件,一行一個

     [email protected]

   }

   notification_email_from [email protected]  #指定發件人

   #smtp_server XXX.smtp.com                             #指定smtp伺服器地址

   #smtp_connect_timeout 30                               #指定smtp連線超時時間

   router_id LVS_DEVEL                                    #執行keepalived機器的一個標識

}

vrrp_script check_nginx {

    script "/etc/keepalived/check_nginx.sh"         ##監控指令碼

    interval 2                                      ##時間間隔,2

    weight 2                                        ##權重

}

vrrp_instance VI_1 {

    state MASTER           #標示狀態為MASTER 備份機為BACKUP

    interface eth0         #設定例項繫結的網絡卡

    virtual_router_id 51   #同一例項下virtual_router_id必須相同

    priority 100           #MASTER權重要高於BACKUP 比如BACKUP為99

    advert_int 1           #MASTER與BACKUP負載均衡器之間同步檢查的時間間隔,單位是秒

    authentication {       #設定認證

        auth_type PASS     #主從伺服器驗證方式

        auth_pass 8888

    }

   track_script {

        check_nginx        #監控指令碼

   }

    virtual_ipaddress {    #設定vip

        192.168.101.100       #可以多個虛擬IP,換行即可

    }

}

下面再給出一個方便複製的內容:

#全域性配置
global_defs {
   notification_email {  #指定keepalived在發生切換時需要傳送email到的物件,一行一個
     [email protected]
   }
   notification_email_from [email protected]  #指定發件人
   #smtp_server XXX.smtp.com                             #指定smtp伺服器地址
   #smtp_connect_timeout 30                               #指定smtp連線超時時間
   router_id LVS_DEVEL                                    #執行keepalived機器的一個標識
}
vrrp_script check_nginx {
    script "/etc/keepalived/check_nginx.sh"         ##監控指令碼
    interval 2                                      ##時間間隔,2秒
    weight 2                                        ##權重
}
vrrp_instance VI_1 {
    state MASTER           #標示狀態為MASTER 備份機為BACKUP
    interface eth0         #設定例項繫結的網絡卡
    virtual_router_id 51   #同一例項下virtual_router_id必須相同
    priority 100           #MASTER權重要高於BACKUP 比如BACKUP為99
    advert_int 1           #MASTER與BACKUP負載均衡器之間同步檢查的時間間隔,單位是秒
    authentication {       #設定認證
        auth_type PASS     #主從伺服器驗證方式
        auth_pass 8888
    }
   track_script {
        check_nginx        #監控指令碼
   }
    virtual_ipaddress {    #設定vip
        192.168.101.100       #可以多個虛擬IP,換行即可
    }

}

修改後重啟keepalived

測試

開啟兩臺伺服器上面的keepalived和nginx,檢視主nginx已經獲取虛擬ip

關閉主機的nginx:

sbin/nginx -s stop

觀察keepalived日誌:

tail -f /var/log/keepalived.log

檢視keepalived程序已經不存在。

檢視eth0已經沒有繫結vip。