讓 HAProxy 1.5 感知 MySQL 複製的延遲

來源:互聯網
上載者:User

讓 HAProxy 1.5 感知 MySQL 複製的延遲

在MySQL世界裡,HAProxy 通常來作為軟體負載平衡器使用。彼得.博羅什在過去的郵件中解釋了如何使用percona xtradb叢集(pxc)來對其設定。所以它只發送查詢到可應用的節點。同樣的方法可用於常規主從設定來讀取負載並分散到多個從節點。不過,使用MySQL複製,另一個因素開始發揮作用:複寫延遲。在這種情況下,被提及到的 Percona xtraDB 叢集以及我們提出只返回“向上”或者“向下”的檢查方法行不通。我們將希望依賴其複寫延遲來調整內部Haproxy的一個權重。這就是我們要做的在這篇文章中使用HAProxy 1.5。

HAProxy的代理檢測

HAProxy 1.5運行我們運行一個代理檢測,這是一項可以添加到常規健康檢測項的檢測。代理檢測的好處是傳回值可以是‘up’或 ‘down’,但也可以是個權重值。

代理是什麼呢?它是一個簡單的可以訪問給定連接埠上TCP串連的程。所以,如果我們要在一台MySQL伺服器上運行代理,這需要:

  • 如果不運行複製的話確保服務在HAProxy上是停止的
  • 如果複寫延遲小於10s,設定weight為100%
  • 如果延遲大於等於10s,小於50s,設定weight為50%
  • 在其他情況下設定weight為5%

我們可以使用這樣一個指令碼:

$ less agent.php
<!--?php
// Simple socket server
// See http://php.net/manual/en/function.stream-socket-server.php
$port = $argv[1];
$mysql_port = $argv[2];
$mysql = "/usr/bin/mysql";
$user = 'haproxy';
$password = 'haproxy_pwd';
$query = "SHOW SLAVE STATUS";
function set_weight($lag){
    # Write your own rules here
    if ($lag == 'NULL'){
        return "down";
    }
    else if ($lag < 10){
        return "up 100%";
    }
    else if ($lag -->= 10 && $lag < 60){
        return "up 50%";
    }
    else
        return "up 5%";
}
set_time_limit(0);
$socket = stream_socket_server("tcp://127.0.0.1:$port", $errno, $errstr);
if (!$socket) {
    echo "$errstr ($errno)
n";
} else {
    while ($conn = stream_socket_accept($socket,9999999999999)) {
        $cmd = "$mysql -h127.0.0.1 -u$user -p$password -P$mysql_port -Ee "$query" | grep Seconds_Behind_Master | cut -d ':' -f2 | tr -d ' '";
        exec("$cmd",$lag);
        $weight = set_weight($lag[0]);
        unset($lag);
        fputs ($conn, $weight);
        fclose ($conn);
    }
    fclose($socket);
}
?>

如果你希望指令碼從連接埠6789發出串連到運行在3306連接埠上的MySQL執行個體,這樣運行:

$ php agent.php 6789 3306

你還需要指定MySQL使用者:

mysql> GRANT REPLICATION CLIENT ON *.* TO 'haproxy'@'127.0.0.1' IDENTIFIED BY 'haproxy_pwd';

代理啟動後,你可以檢測一下它是否正常運行:

# telnet 127.0.0.1 6789
Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.
up 100%
Connection closed by foreign host.

假設它運行在本地的應用伺服器上,有兩個複製正在運行(192.168.10.2和192.168.10.3),應用的讀請求在3307連接埠,你需要在HAProxy中配置一個前端和後端,像這樣:
 
frontend read_only-front
bind *:3307
mode tcp
option tcplog
log global
default_backend read_only-back
backend read_only-back
mode tcp
balance leastconn
server slave1 192.168.10.2 weight 100 check agent-check agent-port 6789 inter 1000  rise 1  fall 1 on-marked-down shutdown-sessions
server slave2 192.168.10.3 weight 100 check agent-check agent-port 6789 inter 1000  rise 1  fall 1 on-marked-down shutdown-sessions

現在所有的都準備好了,現在讓我們看看怎麼使用HAProxy來動態改變重滯伺服器,代碼如下:
 
# Slave1
$ mysql -Ee "show slave status" | grep Seconds_Behind_Master
        Seconds_Behind_Master: 0
# Slave2
$ mysql -Ee "show slave status" | grep Seconds_Behind_Master
        Seconds_Behind_Master: 0
# HAProxy
$ echo "show stat" | socat stdio /run/haproxy/admin.sock | cut -d ',' -f1,2,18,19
# pxname,svname,status,weight
read_only-front,FRONTEND,OPEN,
read_only-back,slave1,UP,100
read_only-back,slave2,UP,100
read_only-back,BACKEND,UP,200

時延1

# Slave1
$ mysql -Ee "show slave status" | grep Seconds_Behind_Master
        Seconds_Behind_Master: 25
# Slave2
$ mysql -Ee "show slave status" | grep Seconds_Behind_Master
        Seconds_Behind_Master: 0
# echo "show stat" | socat stdio /run/haproxy/admin.sock | cut -d ',' -f1,2,18,19
# pxname,svname,status,weight
read_only-front,FRONTEND,OPEN,
read_only-back,slave1,UP,50
read_only-back,slave2,UP,100
read_only-back,BACKEND,UP,150

時延2

# Slave1
$ mysql -Ee "show slave status" | grep Seconds_Behind_Master
        Seconds_Behind_Master: 0
# Slave2
$ mysql -Ee "show slave status" | grep Seconds_Behind_Master
        Seconds_Behind_Master: NULL
# echo "show stat" | socat stdio /run/haproxy/admin.sock | cut -d ',' -f1,2,18,19
# pxname,svname,status,weight
read_only-front,FRONTEND,OPEN,
read_only-back,slave1,UP,100
read_only-back,slave2,DOWN (agent),100
read_only-back,BACKEND,UP,100 

結論

在HAProxy 1.5中代理檢查是一個很好的新增功能。 在上面的設定中是簡單的: 舉例來說, 如果 HAProxy 串連代理失敗,它就不會被標記。 推薦與代理檢查一起,保持常規的健康度檢查。

細心的讀取者們(reads)將會注意到這個配置,如果在所有節點上都被複製, HAProxy將會停止發送給讀取者. 這可能不是最好的解決方案。但可能的選項是:停止代理並標記伺服器為UP,使用狀態通訊端(socket)或者添加主節點作為備份伺服器。

最後一點,使用Percona工具集的pt-heartbeat替代Seconds_Behind_Master,您可以編輯代理的代碼,可以對複製的延遲進行測量 。

Haproxy+Keepalived搭建Weblogic高可用負載平衡叢集

Keepalived+HAProxy配置高可用負載平衡

CentOS 6.3下Haproxy+Keepalived+Apache配置筆記

Haproxy + KeepAlived 實現WEB群集 on CentOS 6

Haproxy+Keepalived構建高可用負載平衡

HAproxy 的詳細介紹:請點這裡
HAproxy 的:請點這裡

本文永久更新連結地址:

相關文章

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.