keepalived高級應用解析


續上篇博文,本博文內容包含:如何配置ipvs,高可用實際應用。
css


1、如何配置ipvs?
html

keepalived的核心就是將IPVS配置成高可用,生成ipvs規則來完成負載均衡效果。前端

virtualserver(虛擬服務)的定義:node

virtual_server IP port       #定義虛擬主機IP地址及其端口
virtual_server fwmark int    #ipvs的防火牆打標,實現基於防火牆的負載均衡集羣
virtual_server group string  #將多個虛擬服務器定義成組,將組定義成虛擬服務
lb_algo{rr|wrr|lc|wlc|lblc|lblcr} #定義LVS的調度算法
lb_kind {NAT|DR|TUN}               #定義LVS的模型
presitence_timeout<INT>           #定義支持持久鏈接的時長
protocol TCP                       #規則所能支持的協議
sorry_server <IPADDR><PORT>       #若是全部real_server都出現故障了,利用此返回信息

real_server(真實服務器)的定義:nginx

real_server<IPADDR><PORT>           #定義地址和端口
{                                   #每一組都要用花括號定義自有的屬性的
weight <INT>                        #定義權重
notify_up<STRING>|<QUOTED-STRING>   #通知腳本,一旦腳本up就通知
notify_down<STRING>|<QUOTED-STRING>  #通知腳本,一旦腳本down就通知
HTTP_GET|SSL_GET|TCP_CHECK|SMTP_CHECK|MISC_CHECK    #定義健康狀態檢測(HTTP_GET:使用此方法檢測的;SSL_GET:若是是HTTPS使用此方式檢測;TCP_CHECK:檢測TCP協議的服務器健康情況;SMTP_CHECK:用來專門檢測SMTP服務器;MISC_CHECK:其餘檢測機制不多使用通常只使用前三種檢測方法)
}

健康狀態檢測的常見的兩種方法作闡述瞭解:web

############HTTP_GET|SSL_GET#############
{
# Aurlto test, can have multiple entries here
url{            #url字段
path<STRING>   #指明檢查哪一個url
#healthcheckneedsstatus_codeor status_codeand digest .Digest computed with genhash, egdigest9b3a0c85a887a256d6939da88aabd8cd
digest<STRING>    #獲取檢測那個url的校驗碼
status_code<INT>   #明確指定那個url的校驗碼和上面的digest不可同時存在
}
connect_port<PORT>      #指望鏈接後端服務器的哪些端口
bindto<IPADDR>          #檢測哪一個IP的哪一個端口,若不指定應和外圍的real_server指定的端口地址是一致
connect_timeout<INT>     #超時時間
nb_get_retry<INT>        #重試次數
delay_before_retry<INT>  #重試以前等待的時間
}
##############3TCK_CHECK##############
{
 connect_port <PORT>     #鏈接哪一個端口
 bindto <IPADDR>         #鏈接哪一個地址
 connect_timeout <INT>   #超時時間是多少
}

定義好這些以後它自行會檢測自行判斷可以鏈接上可以收到信息就說明是正常的不然就是失敗的。算法

定義一個real_server:而且能夠實現web健康狀態檢測??apache

一、編輯主服務器配置文件定義虛擬服務:vim

[root@node1keepalived]# vim keepalived.conf  
virtual_server172.16.18.100 80 {
    delay_loop 6
    lb_algo rr
    lb_kind DR
    nat_mask 255.255.0.0
    persistence_timeout 0
    protocol TCP
#
    real_server 172.16.18.5 80 {
        weight 1
        HTTP_GET {
            url {
              path /
              status_code 200
            }
            connect_timeout 3
            nb_get_retry 3
            delay_before_retry 3
        }
    }
    real_server 172.16.18.6 80 {
        weight 1
        HTTP_GET {
            url {
              path /
              status_code 200
            }
            connect_timeout 3
            nb_get_retry 3
            delay_before_retry 3
        }
    }
}
######備服務器一樣定義虛擬服務########

二、查看規則:後端

[root@node1keepalived]# yum -y install ipvsadm
[root@node1keepalived]# ipvsadm -L -n
IPVirtual Server version 1.2.1 (size=4096)
ProtLocalAddress:Port Scheduler Flags
  -> RemoteAddress:Port           Forward Weight ActiveConn InActConn
TCP  172.16.18.100:80 rr

顯然已生成規則,因此總結可得知無須安裝ipvsadm依然能夠生成規則,只是沒法校驗規則。

還有這裏兩個real_server都不存在,緣由是健康監測沒法經過因此致使這裏不存在。

三、測試:

開啓real_server主機:172.16.18.6

[root@node~]# vim /var/www/html/index.html
[root@nodehtml]# service httpd start
[root@node1keepalived]# ipvsadm -L -n
IPVirtual Server version 1.2.1 (size=4096)
ProtLocalAddress:Port Scheduler Flags
  -> RemoteAddress:Port           Forward Weight ActiveConn InActConn
TCP  172.16.18.100:80 rr
  -> 172.16.18.6:80               Route   1     0          0



2、綜合應用實現:

構建keepalived+Nginx實現雙主模式高可用集羣。

架構說明:這種模式須要使用兩個虛擬IP地址,前端有兩臺Nginx服務器互爲主備並同時工做,不會形成資源浪費;若是其中一臺服務器出現故障時,將會把全部請求都轉發到另外一臺服務器上面,繼續提供服務。

架構拓撲:

150838128.jpg

應用環境介紹:

系統版本:centosx86_64
keepalived版本:1.2.7
Nginx:1.4.2
Apache:yum源安裝

IP地址和主機名介紹:

Nginx1:172.16.18.7([root@node1 ~]#)
Nginx2:172.16.18.9([root@node2 ~]#)
Apache1:172.16.18.10([root@node ~]#)
Apache2:172.16.18.11([root@stu18 ~]#)
VIP:172.16.18.100
VIP:172.16.18.200

實現步驟:

一、在Nginx1上編譯安裝Nginx

############安裝依賴包組#########
[root@node1 ~]# yum groupinstall "Development tools" "Server Platform Development" –y
[root@node1 ~]# yum -y install pcre-devel
############建立用戶############
[root@node1 ~]# useradd -r nginx
############解壓Nginx###########
[root@node1 ~]# tar xf nginx-1.4.2.tar.gz
############編譯安裝############
[root@node1 ~]# cd nginx-1.4.2
[root@node1 nginx-1.4.2]# ./configure \
>   --prefix=/usr \
>   --sbin-path=/usr/sbin/nginx \
>   --conf-path=/etc/nginx/nginx.conf \
>   --error-log-path=/var/log/nginx/error.log \
>   --http-log-path=/var/log/nginx/access.log \
>   --pid-path=/var/run/nginx/nginx.pid  \
>   --lock-path=/var/lock/nginx.lock \
>   --user=nginx \
>   --group=nginx \
>   --with-http_ssl_module \
>   --with-http_flv_module \
>   --with-http_stub_status_module \
>   --with-http_gzip_static_module \
>   --http-client-body-temp-path=/var/tmp/nginx/client/ \
>   --http-proxy-temp-path=/var/tmp/nginx/proxy/ \
>   --http-fastcgi-temp-path=/var/tmp/nginx/fcgi/ \
>   --http-uwsgi-temp-path=/var/tmp/nginx/uwsgi \
>   --http-scgi-temp-path=/var/tmp/nginx/scgi \
>   --with-pcre
[root@node1 nginx-1.4.2]# make && make install
#############提供systemV腳本########
[root@node1 nginx-1.4.2]# vim /etc/rc.d/init.d/nginx
#!/bin/sh
#
# nginx - this script starts and stops the nginx daemon
#
# chkconfig:   - 85 15
# description:  Nginx is an HTTP(S) server, HTTP(S) reverse \
#               proxy and IMAP/POP3 proxy server
# processname: nginx
# config:      /etc/nginx/nginx.conf
# config:      /etc/sysconfig/nginx
# pidfile:     /var/run/nginx.pid
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
# Source function library.
. /etc/rc.d/init.d/functions
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
# Source networking configuration.
. /etc/sysconfig/network
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
# Check that networking is up.
[ "$NETWORKING" = "no" ] && exit 0
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
nginx="/usr/sbin/nginx"
prog=$(basename $nginx)
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
NGINX_CONF_FILE="/etc/nginx/nginx.conf"
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
[ -f /etc/sysconfig/nginx ] && . /etc/sysconfig/nginx
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
lockfile=/var/lock/subsys/nginx
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
make_dirs() {
   # make required directories
   user=`nginx -V 2>&1 | grep "configure arguments:" | sed 's/[^*]*--user=\([^ ]*\).*/\1/g' -`
   options=`$nginx -V 2>&1 | grep 'configure arguments:'`
   for opt in $options; do
       if [ `echo $opt | grep '.*-temp-path'` ]; then
           value=`echo $opt | cut -d "=" -f 2`
           if [ ! -d "$value" ]; then
               # echo "creating" $value
               mkdir -p $value && chown -R $user $value
           fi
       fi
   done
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
start() {
    [ -x $nginx ] || exit 5
    [ -f $NGINX_CONF_FILE ] || exit 6
    make_dirs
    echo -n $"Starting $prog: "
    daemon $nginx -c $NGINX_CONF_FILE
    retval=$?
    echo
    [ $retval -eq 0 ] && touch $lockfile
    return $retval
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
stop() {
    echo -n $"Stopping $prog: "
    killproc $prog -QUIT
    retval=$?
    echo
    [ $retval -eq 0 ] && rm -f $lockfile
    return $retval
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
restart() {
    configtest || return $?
    stop
    sleep 1
    start
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
reload() {
    configtest || return $?
    echo -n $"Reloading $prog: "
    killproc $nginx -HUP
    RETVAL=$?
    echo
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
force_reload() {
    restart
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
configtest() {
  $nginx -t -c $NGINX_CONF_FILE
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
rh_status() {
    status $prog
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
rh_status_q() {
    rh_status >/dev/null 2>&1
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            
case "$1" in
    start)
        rh_status_q && exit 0
        $1
        ;;
    stop)
        rh_status_q || exit 0
        $1
        ;;
    restart|configtest)
        $1
        ;;
    reload)
        rh_status_q || exit 7
        $1
        ;;
    force-reload)
        force_reload
        ;;
    status)
        rh_status
        ;;
    condrestart|try-restart)
        rh_status_q || exit 0
            ;;
    *)
        echo $"Usage: $0 {start|stop|status|restart|condrestart|try-restart|reload|force-reload|configtest}"
        exit 2
esac
#############賦予權限#########
[root@node1 nginx-1.4.2]# chmod +x /etc/rc.d/init.d/nginx
############啓動服務##########
[root@node1 init.d]# service nginx start

二、在Nginx2上編譯安裝Nginx

 具體步驟請參考Nginx1編譯安裝。

三、測試訪問

162715124.png

162718129.png

四、配置後端靜態網頁

###########http1############
[root@node ~]# yum -y install httpd   #yum源安裝
[root@node ~]# cd /var/www/html/
[root@node html]# vim index.html
    hello       #網頁內容
[root@node html]# service httpd restart
##########http2#############
[root@stu18 ~]# yum -y install httpd
[root@stu18 ~]# cd /var/www/html/
[root@stu18 html]# vim index.html
     hello2     #網頁內容
[root@stu18 html]# service httpd restart

五、配置Nginx實現負載均衡

#############編輯Nginx1主配置文件###########
[root@node1 ~]# cd /etc/nginx/
[root@node1 nginx]# vim nginx.conf
#user  nobody;
worker_processes  1;
                                                                                                                                                                                                                                                                                                              
#error_log  logs/error.log;
#error_log  logs/error.log  notice;
#error_log  logs/error.log  info;
                                                                                                                                                                                                                                                                                                              
#pid        logs/nginx.pid;
                                                                                                                                                                                                                                                                                                              
                                                                                                                                                                                                                                                                                                              
events {
    worker_connections  1024;
}
                                                                                                                                                                                                                                                                                                              
                                                                                                                                                                                                                                                                                                              
http {
    include       mime.types;
    default_type  application/octet-stream;
                                                                                                                                                                                                                                                                                                              
    #log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
    #                  '$status $body_bytes_sent "$http_referer" '
    #                  '"$http_user_agent" "$http_x_forwarded_for"';
                                                                                                                                                                                                                                                                                                              
    #access_log  logs/access.log  main;
                                                                                                                                                                                                                                                                                                              
    sendfile        on;
    #tcp_nopush     on;
                                                                                                                                                                                                                                                                                                              
    #keepalive_timeout  0;
    keepalive_timeout  65;
    upstream httpdweb {                #設置負載均衡
        server 172.16.18.6:80 max_fails=3 fail_timeout=2s;
        server 172.16.18.1:80 max_fails=3 fail_timeout=2s;
            }
    #gzip  on;
                                                                                                                                                                                                                                                                                                              
    server {
        listen       80;
        server_name  localhost;
                                                                                                                                                                                                                                                                                                              
        #charset koi8-r;
                                                                                                                                                                                                                                                                                                              
        #access_log  logs/host.access.log  main;
                                                                                                                                                                                                                                                                                                              
        location / {
            root   html;
            index  index.html index.htm;
        }
                                                                                                                                                                                                                                                                                                              
        #error_page  404              /404.html;
                                                                                                                                                                                                                                                                                                              
        # redirect server error pages to the static page /50x.html
        #
        error_page   500 502 503 504  /50x.html;
        location = /50x.html {
            root   html;
        }
       location ~ \.(html|htm|gif|jpg|jpeg|bmp|png|ico|txt|js|css)$ {
          root /var/www/html;                #定義後端httpd服務器網頁位置
        proxy_pass http://apacheweb;
        }
#############Nginx2上依然更改配置文件#######
[root@node1 nginx]# scp nginx.conf 172.16.18.9:/etc/nginx
############重啓服務#######################
[root@node1 nginx]# service nginx restart
[root@node2 ~]# service nginx restart

163451782.png

163453327.png

163456734.png

163458876.png

六、安裝配置keepalived:

 Nginx1上:

#############安裝keepalived##########
[root@node1 nginx]# yum -y install keepalived
#############編輯配置 文件###########
[root@node1 nginx]# vim /etc/keepalived/keepalived.conf
! Configuration File for keepalived
                                                                                                                                                                                                                                                                              
global_defs {
   notification_email {
     root@localhost
   }
   notification_email_from Nginx@localhost
   smtp_server 127.0.0.1
   smtp_connect_timeout 30
   router_id LVS_DEVEL
}
vrrp_script chk_nginx {
     script "killall -0 nginx"     #檢測nginx服務是否存在
     interval 1                    #時間間隔1秒檢測一次
     weight -2                     #當nginx不存在將當前權重減2
}
vrrp_instance VI_1 {
    state MASTER                #主
    interface eth0
    virtual_router_id 59
    priority 100
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass 1111
    }
    virtual_ipaddress {
        172.16.18.100
    }
    track_script {        #引用上面定義的腳本
     chk_nginx
}
}
vrrp_instance VI_2 {
    state BACKUP              #備
    interface eth0
    virtual_router_id 68
    priority 99
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass 2222
    }
    virtual_ipaddress {
        172.16.18.200
    }
    track_script {
     chk_nginx
}
}
#virtual_server 192.168.200.100 443 {       #如下部分註釋掉或直接刪除
#    delay_loop 6
#    lb_algo rr
#    lb_kind NAT
#    nat_mask 255.255.255.0
#    persistence_timeout 50
#    protocol TCP
#
#    real_server 192.168.201.100 443 {
#        weight 1
#        SSL_GET {
#            url {

Nginx2上:

#############安裝##############
[root@node2 ~]# yum -y install keepalived
#############複製配置文件######
[root@node1 nginx]# scp /etc/keepalived/keepalived.conf 172.16.18.9:/etc/keepalived/
#############編輯配置文件#####
[root@node2 ~]# vim /etc/keepalived/keepalived.conf             
! Configuration File for keepalived
global_defs {
   notification_email {
     root@localhost
   }
   notification_email_from Nginx@localhost
   smtp_server 127.0.0.1
   smtp_connect_timeout 30
   router_id LVS_DEVEL
}
vrrp_script chk_nginx {
     script "killall -0 nginx"
     interval 1
     weight -2
}
vrrp_instance VI_1 {
    state BACKUP            #備
    interface eth0
    virtual_router_id 59
    priority 99            #優先級下降
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass 1111
    }
    virtual_ipaddress {
        172.16.18.100
    }
    track_script {
     chk_nginx
}
}
vrrp_instance VI_2 {
    state MASTER           #主
    interface eth0
    virtual_router_id 68
    priority 100
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass 2222
    }
    virtual_ipaddress {
        172.16.18.200
    }
    track_script {
     chk_nginx
}
}

七、測試高可用效果:

##############啓動服務###################
[root@node1 ~]# service keepalived start
[root@node2 ~]# service keepalived start
#############查看Nginx1的VIP##############
[root@node1 nginx]# ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 16436 qdisc noqueue state UNKNOWN
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000
    link/ether 00:0c:29:06:a6:49 brd ff:ff:ff:ff:ff:ff
    inet 172.16.18.7/16 brd 172.16.255.255 scope global eth0
    inet 172.16.18.100/32 scope global eth0
    inet6 fe80::20c:29ff:fe06:a649/64 scope link
       valid_lft forever preferred_lft forever
#############查看Nginx2的VIP##############
[root@node2 ~]# ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 16436 qdisc noqueue state UNKNOWN
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000
    link/ether 00:0c:29:12:c8:b5 brd ff:ff:ff:ff:ff:ff
    inet 172.16.18.9/16 brd 172.16.255.255 scope global eth0
    inet 172.16.18.200/32 scope global eth0
    inet6 fe80::20c:29ff:fe12:c8b5/64 scope link
       valid_lft forever preferred_lft forever

164932460.png

164935788.png

164938488.png

164944282.png

八、模擬其中一臺前端Nginx服務器出現故障不能正常提供服務

############關閉Nginx1##############
[root@node1 nginx]# service nginx stop
Stopping nginx:                                            [  OK  ]
[root@node1 nginx]# ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 16436 qdisc noqueue state UNKNOWN
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000
    link/ether 00:0c:29:06:a6:49 brd ff:ff:ff:ff:ff:ff
    inet 172.16.18.7/16 brd 172.16.255.255 scope global eth0
    inet6 fe80::20c:29ff:fe06:a649/64 scope link
       valid_lft forever preferred_lft forever
[root@node2 ~]# ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 16436 qdisc noqueue state UNKNOWN
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000
    link/ether 00:0c:29:12:c8:b5 brd ff:ff:ff:ff:ff:ff
    inet 172.16.18.9/16 brd 172.16.255.255 scope global eth0
    inet 172.16.18.200/32 scope global eth0
    inet 172.16.18.100/32 scope global eth0
    inet6 fe80::20c:29ff:fe12:c8b5/64 scope link
       valid_lft forever preferred_lft forever
##############關閉Nginx2##############
[root@node1 nginx]# service nginx start
[root@node2 ~]# service nginx stop
[root@node2 ~]# ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 16436 qdisc noqueue state UNKNOWN
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000
    link/ether 00:0c:29:12:c8:b5 brd ff:ff:ff:ff:ff:ff
    inet 172.16.18.9/16 brd 172.16.255.255 scope global eth0
    inet6 fe80::20c:29ff:fe12:c8b5/64 scope link
       valid_lft forever preferred_lft forever
[root@node1 nginx]# ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 16436 qdisc noqueue state UNKNOWN
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000
    link/ether 00:0c:29:06:a6:49 brd ff:ff:ff:ff:ff:ff
    inet 172.16.18.7/16 brd 172.16.255.255 scope global eth0
    inet 172.16.18.100/32 scope global eth0
    inet 172.16.18.200/32 scope global eth0
    inet6 fe80::20c:29ff:fe06:a649/64 scope link
       valid_lft forever preferred_lft forever

至此keepalived實現Nginx高可用就完成了,其中郵件通知機制(利用腳本通知)未定義,如有興趣可參考上篇博文《keepalived基礎應用解析》自行配置解決(很簡單)。

請各位博友多提建議和錯誤糾正,博主在此先謝過了。

相關文章
相關標籤/搜索