1. 程式人生 > >docker下用keepalived+Haproxy實現高可用負載均衡叢集

docker下用keepalived+Haproxy實現高可用負載均衡叢集

先記錄下遇到的坑,避免之後忘了;

花時間最多去解決的一個題是:在docker下啟動haproxy服務後在這個docker服務內安裝keepalived無法ping通的問題,雖然最後也是莫名其妙就好了,但是加強了不少對docker的理解和還需深入學習的地方。

為什麼要用keepalived+haproxy實現docker下的高可用負載均衡?在不同環境下有哪些方式可以實現高可用負載均衡?

首先第一點,實現負載均衡並不是只有haproxy一箇中間件,網上還有很多方案是用keepalived+LVS等等,所以對於docker下的高可用負載均衡不一定只有keepalived+haproxy。只是本次我是基於之前搭建的pxc叢集進行繼續搭建的,所以用的是haproxy。

為什麼這裡強調的是docker、keepalived?

首先我們執行環境是docker,keepalived的作用是搶佔虛擬ip,docker環境下,映象內的網段外網是無法訪問的,所以我們需要一個外網在宿主機上對映到docker內的ip上,keepalived一方面可以對映ip到docker服務內,二可以在docker服務內強佔虛擬ip。所以在docker搭建負載均衡的多種方案中都常見會出現keepalived。

為什麼要搶佔虛擬ip?為什麼要用keepalived呢?

負載均衡中介軟體(haproxy,lvs)等等在實際中不可能只是單節點存在(單節點不需要keepalived),都要有冗餘設計,即叢集設計,和資料庫叢集不一樣的是,docker中實現負載均衡中介軟體的叢集是通過搶佔一個ip地址實現的,有主備和主主方式,雖然方式不一樣,但都有一個心跳檢測的共同點,在主節點搶佔虛擬ip時,主從節點上會有心跳檢測線,如果發現主節點心跳檢測連不上,則從節點會主動搶佔ip實現資料不中斷的冗餘機制;

總結描述:由於是在docker環境下,我們要搭建負載均衡叢集需要通過keepalived搶佔虛擬ip實現,二負載均衡功能需要haproxy中介軟體實現,所以本次我搭建的是一個在docker環境下高可用的負載均衡方案是:keepalived+haproxy。

haproxy具體方法:

下載docker映象;
Docker pull haproxy

重新命名
docker tag docker.io/haproxy haproxy 

刪除多餘映象
docker rmi docker.io/haproxy

ftp上傳docker配置檔案,目錄自行定義,目錄對映根據定義目錄名對映

檢視配置檔案(需要編輯可編輯)
cat haproxy.cfg

啟動建立docker-haproxy服務
docker run -it -d -p 4001:8888 -p 4002:3306 -v /data/haproxy/config:/usr/local/etc/haproxy --name haproxy01 --privileged --net=net1 --ip 172.20.0.07  haproxy

埠8888是監控頁面埠,3006是MySQL服務埠,引數都可以在配置檔案中調整


進入docker-haproxy服務
docker exec -it haproxy01 /bin/bash


啟用配置檔案(啟用完配置檔案才算是真的啟動了haproxy服務)
haproxy -f /usr/local/etc/haproxy/haproxy.cfg

退出haproxy互動,回到宿主機
ctrl+D

haproxy配置資訊:

global
	#工作目錄
	chroot /usr/local/etc/haproxy
	#日誌檔案,使用rsyslog服務中local5日誌裝置(/var/log/local5),等級info
	log 127.0.0.1 local5 info
	#守護程序執行
	daemon

defaults
	log	global
	mode	http
	#日誌格式
	option	httplog
	#日誌中不記錄負載均衡的心跳檢測記錄
	option	dontlognull
    #連線超時(毫秒)
	timeout connect 5000
    #客戶端超時(毫秒)
	timeout client  50000
	#伺服器超時(毫秒)
    timeout server  50000

#監控介面	
listen  admin_stats
	#監控介面的訪問的IP和埠
	bind  0.0.0.0:8888
	#訪問協議
    mode        http
	#URI相對地址
    stats uri   /dbs
	#統計報告格式
    stats realm     Global\ statistics
	#登陸帳戶資訊
    stats auth  admin:abc123456
#資料庫負載均衡
listen  proxy-mysql
	#訪問的IP和埠(前面ip=0代表任何ip都可訪問)
	bind  0.0.0.0:3306  
    #網路協議
	mode  tcp
	#負載均衡演算法(輪詢演算法)
	#輪詢演算法:roundrobin
	#權重演算法:static-rr
	#最少連線演算法:leastconn
	#請求源IP演算法:source 
    balance  roundrobin
	#日誌格式
    option  tcplog
	#在MySQL中建立一個沒有許可權的haproxy使用者,密碼為空。Haproxy使用這個賬戶對MySQL資料庫心跳檢測
    option  mysql-check user haproxy
    server  NODE1 172.20.0.2:3306 check weight 1 maxconn 2000  
    server  NODE2 172.20.0.3:3306 check weight 1 maxconn 2000  
	server  NODE3 172.20.0.4:3306 check weight 1 maxconn 2000 
	server  NODE4 172.20.0.5:3306 check weight 1 maxconn 2000
	server  NODE5 172.18.0.6:3306 check weight 1 maxconn 2000
	#使用keepalive檢測死鏈
    option  tcpka  

要解釋配置檔案真的可以寫個單獨的說明,我這裡只說下連結資料庫的幾點,即option引數後面的;

NODE1+ip這個是指的PXC叢集的docker映象名和所制定的ip地址,這個要和資料庫叢集一致,後面的權重,最大連結數可以執行設定,也可以直接套用我的,其他的說明配置檔案中都有;可直接使用;最後在網頁上輸入宿主機IP+監控埠+/dbs即可進入監控頁面。

keepalived搭建:

keepalived的實現是要在docker服務內建立,最後宿主機中也要建立實現docker內外的連線;
docker服務內建立,我們需要進入到該服務並安裝keepalived


進入docker-haproxy服務
docker exec -it haproxy01 /bin/bash

更新update,安裝keepalived
apt-get update
apt-get install keepalived

安裝vim 安裝ifconfig命令 安裝ping
apt-get install net-tools    
apt-get install iputils-ping


新建並寫入一個keepalived的配置檔案
vim /etc/keepalived/keepalived.conf


配置檔案資訊:
#取名為K1,可自定義
vrrp_instance  VI_1 {
#定義節點屬性
    state  MASTER
	#定義虛擬網絡卡
    interface  eth0
	#定義組vriid
    virtual_router_id  100
	#定義權重
    priority  100
	#定義心跳檢測時間1秒
    advert_int  1
	#定義組使用者密碼
    authentication {
        auth_type  PASS
        auth_pass  123456
    }
	#定義docker內ip地址,必須要在和haproxy同一個網段
    virtual_ipaddress {
        172.20.0.100
    }
}


啟動
service keepalived start

到這一步理論上就完事了,只需要在新建一個haproxy+keepalived組成叢集即可,在這裡我遇到一個坑是:

啟動keepalived後宿主機無法ping通用keepalived,報錯:

[[email protected] ~]# ping 172.20.0.8
PING 172.20.0.8 (172.20.0.8) 56(84) bytes of data.
From 172.20.0.1 icmp_seq=1 Destination Host Unreachable
From 172.20.0.1 icmp_seq=2 Destination Host Unreachable

解決方案:

大多數都是我把配置檔案沒寫對,重寫配置檔案,重啟服務;

這裡檢查能否ping通,需要看服務內你的配置檔案寫入的ip有沒有出現在docker的網絡卡上,具體方法是:

進入到docker服務內,不是在宿主機上哦,檢視配置檔案
[email protected]:/etc/keepalived# cat keepalived.conf
vrrp_instance  VI_1 {
    state  MASTER
    interface  eth0
    virtual_router_id  100
    priority  100
    advert_int  1
    authentication {
        auth_type  PASS
        auth_pass  123456
    }
    virtual_ipaddress {
        172.20.0.100
    }
}
如果配置檔案資訊都是正確的,通過ip a命令會顯示如當前docker服務有的網絡卡
[email protected]:/etc/keepalived# ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host 
       valid_lft forever preferred_lft forever
73: [email protected]: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default 
    link/ether 02:42:ac:14:00:07 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 172.20.0.7/24 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::42:acff:fe14:7/64 scope link 
       valid_lft forever preferred_lft forever

很明顯沒有我配置檔案中的172.20.0.100ip地址,代表配置檔案未生效,大多數配置檔案錯誤

停掉keepalived服務重新修改編輯後重啟
[email protected]:/etc/keepalived# service keepalived stop
[ ok ] Stopping keepalived: keepalived.
重啟服務
[email protected]:/etc/keepalived# service keepalived start
[ ok ] Starting keepalived: keepalived.

再次檢視docker服務的ip
[email protected]:/etc/keepalived# ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host 
       valid_lft forever preferred_lft forever
73: [email protected]: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default 
    link/ether 02:42:ac:14:00:07 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 172.20.0.7/24 scope global eth0
       valid_lft forever preferred_lft forever
這裡出現了我的配置檔案ip地址
    inet 172.20.0.100/32 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::42:acff:fe14:7/64 scope link 
       valid_lft forever preferred_lft forever

在服務內直接ping這個ip,發現能ping通,切換宿主機,也能ping通,解決問題
[email protected]:/etc/keepalived# ping 172.20.0.100
PING 172.20.0.100 (172.20.0.100) 56(84) bytes of data.
64 bytes from 172.20.0.100: icmp_seq=1 ttl=64 time=0.042 ms
64 bytes from 172.20.0.100: icmp_seq=2 ttl=64 time=0.059 ms
64 bytes from 172.20.0.100: icmp_seq=3 ttl=64 time=0.060 ms
^C

最後,再新建一個haproxy再新增slave的keepalive,加入到master中,即完成負載均衡叢集的搭建。