11. Nginx實現(xiàn)負載均衡

6.2 實現(xiàn)Nginx TCP負載均衡

Nginx在1.9.0版本開始支持tcp模式的負載均衡, 在1.9.13版本開始支持udp協(xié)議的負載均衡, udp主要用于DNS的域名解析, 其配置方式和指令和http代理類似, 其基于ngx_stream_proxy_module模塊實現(xiàn)tcp負載, 另外基于模塊ngx_http_upstream_module實現(xiàn)后端服務器分組轉發(fā), 權重分配, 狀態(tài)監(jiān)測, 調度算法等高級功能

如果是編譯安裝, 需要指定--with-stream選項才能支持ngx_stream_proxy_module模塊

6.2.1 tcp 負載均衡配置參數

stream { # 定義stream相關的服務, 定義在main語句塊和http平級
    upstream backend { # 定義后端服務器
        hash $remote_addr consistent; # 定義調度算法
        server backend1.example.com:12345 weight=5; # 定義具體server
        server 127.0.0.1:12345 max_fails=3 fail_timeout=30s;
        server unix:/tmp/backend3;
    }

    upstream dns { # 定義后端服務器
        server 10.0.0.1:53535; # 定義具體server
        server dns.example.com:53;
    }

    server { # 定義server, 定義nginx如何接收和轉發(fā)遠程用戶的請求
        listen 12345; # 監(jiān)聽ip:port
        proxy_connect_timeout 1s; # 連接超時時間
        proxy_timeout 3s; # 轉發(fā)超時時間
        proxy_pass backend; # 轉發(fā)到具體服務器組
    }
    
    server {
        listen 127.0.0.1:53 udp reuseport;
        proxy_timeout 20s;
        proxy_pass dns;
    }

    server {
        listen [::1]:12345;
        proxy_pass unix:/tmp/stream.socket;   
    }
} 

6.2.2 負載均衡案例: Redis

6.2.2.1 準備環(huán)境

準備兩臺后端服務器, 安裝redis
可以基于每臺服務器的run_id測試調度結果
yum -y install redis
vim /etc/redis.conf
bind 0.0.0.0 
systemctl enable --now redis

6.2.2.2 nginx配置負載均衡

# 先在nginx主配置文件定義tcp負載均衡的子配置文件路徑
[13:50:26 root@nginx ~]#vim /apps/nginx/conf/nginx.conf
include /apps/nginx/conf/tcp/tcp.conf; # 注意: tcp負載均衡的子配置文件路徑指令要和http語句塊平級, 一般寫在主配置文件最后即可, 由于stream是一級語句塊, 整個nginx只能有一個, 因此, 所有的tcp/udp負載均衡配置, 都寫在同一個文件里
[00:30:17 root@nginx /apps/nginx/conf/tcp]#vim redis.conf

stream {                                                                                                                                                                            

    upstream redis-server {
        server 10.0.0.85:6379 weight=2;
        server 10.0.0.84:6379 weight=1;

    }
    server{
        # 配置負載均衡時, server語句塊不支持server_name, 客戶端直接訪問nginx的ip地址和端口
        listen 6379;
        proxy_pass redis-server;
    }

}

[00:35:51 root@nginx /apps/nginx/conf/tcp]#nginx -s reload
[13:51:16 root@nginx ~]#ss -ntl
State                   Recv-Q                  Send-Q                                    Local Address:Port                                     Peer Address:Port                  
LISTEN                  0                       128                                             0.0.0.0:6379     # 驗證監(jiān)聽6379端口                                      0.0.0.0:*                     
LISTEN                  0                       128                                             0.0.0.0:80                                            0.0.0.0:*                     
LISTEN                  0                       128                                             0.0.0.0:22                                            0.0.0.0:*                     
LISTEN                  0                       128                                                [::]:22                                               [::]:*  

6.2.2.3 客戶端連接nginx測試

# 可以看到1:2調度
[00:38:02 root@client ~]#redis-cli -h 10.0.0.86 info server | grep run_id
run_id:6c86d33bf1002c7839f43a6ac9055f0406d61b7a
[00:38:25 root@client ~]#redis-cli -h 10.0.0.86 info server | grep run_id
run_id:580343970ae2d5078ff064260e170a8932a48338
[00:38:27 root@client ~]#redis-cli -h 10.0.0.86 info server | grep run_id
run_id:6c86d33bf1002c7839f43a6ac9055f0406d61b7a
[00:38:28 root@client ~]#redis-cli -h 10.0.0.86 info server | grep run_id
run_id:6c86d33bf1002c7839f43a6ac9055f0406d61b7a

6.2.3 負載均衡案例: MySQL

圖片.png

6.2.3.1 準備環(huán)境

為了測試效果, 后端分別使用mariadb和mysql
數據庫上創(chuàng)建用戶, 需要對nginx的ip地址進行授權
nginx基于四層的調度是偽四層, 因此nginx會拆分請求和響應報文, 重新封裝
# 10.0.0.85 - MySQL
[23:34:16 root@mysql ~]#yum -y install mysql-server
[23:35:30 root@mysql ~]#systemctl enable --now mysqld
Created symlink /etc/systemd/system/multi-user.target.wants/mysqld.service → /usr/lib/systemd/system/mysqld.service.
[23:42:31 root@mysql ~]#mysql -e 'create user admin@"10.0.0.%" identified by "000000"'
# 10.0.0.84 - MariaDB
[23:34:41 root@mariadb ~]#yum -y install mariadb-server
[23:35:13 root@mariadb ~]#systemctl enable --now mariadb
Created symlink /etc/systemd/system/mysql.service → /usr/lib/systemd/system/mariadb.service.
Created symlink /etc/systemd/system/mysqld.service → /usr/lib/systemd/system/mariadb.service.
Created symlink /etc/systemd/system/multi-user.target.wants/mariadb.service → /usr/lib/systemd/system/mariadb.service.
[23:44:03 root@mariadb ~]#mysql -e 'create user admin@"10.0.0.%" identified by "000000"'

6.2.3.2 nginx配置負載均衡

# 單獨指定存放tcp負載均衡的配置文件, 關于tcp的負載均衡配置, 都可以寫到tcp目錄下某個.conf文件里, 因為stream是一級語句塊, 一個服務器只能有一個, 因此只能存在一個.conf配置文件, 專門來配置tcp負載均衡, 如果多個文件都有stream模塊, 那么重啟nginx會報錯
include /apps/nginx/conf/tcp/*.conf;                                                                                                                                                                                                                                                                            
[23:47:05 root@nginx /apps/nginx/conf]#mkdir  /apps/nginx/conf/tcp
[23:47:44 root@nginx /apps/nginx/conf]#cd  /apps/nginx/conf/tcp
[23:47:45 root@nginx /apps/nginx/conf/tcp]#
[23:47:46 root@nginx /apps/nginx/conf/tcp]#
[23:47:46 root@nginx /apps/nginx/conf/tcp]#vim mysql.conf
[23:47:46 root@nginx /apps/nginx/conf/tcp]#vim mysql.conf

stream {

     upstream mysql-server { # upstream定義后端服務器組
        server 10.0.0.85:3306 max_fails=3 fail_timeout=30s;
        server 10.0.0.84:3306; # 后端服務器監(jiān)聽的端口
     }

     server { # server定義nginx如何接收和處理客戶端請求, 包括監(jiān)聽的端口, 和轉發(fā)到的后端群組
        listen 3306; # 面對客戶端的端口
        proxy_pass mysql-server;
     }
                                                                                                                                                                                    
}

[23:59:02 root@nginx /apps/nginx/conf/tcp]#nginx -t
nginx: the configuration file /apps/nginx/conf/nginx.conf syntax is ok
nginx: configuration file /apps/nginx/conf/nginx.conf test is successful
[23:59:05 root@nginx /apps/nginx/conf/tcp]#nginx -s reload
[23:59:10 root@nginx /apps/nginx/conf/tcp]#ss -ntl
State                   Recv-Q                  Send-Q                                    Local Address:Port                                     Peer Address:Port                  
LISTEN                  0                       128                                             0.0.0.0:3306                                          0.0.0.0:*                     
LISTEN                  0                       128                                             0.0.0.0:80                                            0.0.0.0:*                     
LISTEN                  0                       128                                             0.0.0.0:22                                            0.0.0.0:*                     
LISTEN                  0                       128                                                [::]:22                                               [::]:*

6.2.3.3 客戶端連接nginx測試

# 10.0.0.187安裝mysql客戶端

[00:00:27 root@client ~]#yum -y install mysql
# 連接nginx

[00:00:44 root@client ~]#mysql -h 10.0.0.86 -uadmin -p000000
MySQL [(none)]> 
# 驗證版本
圖片.png

此時后端服務器會認為是nginx在訪問, 因此數據庫授權也是針對nginx進行授權

圖片.png

通過nginx的tcp負載均衡, 可以實現(xiàn)對后端的PXC集群進行調度

圖片.png

補充: lvs和nginx四層負載均衡的區(qū)別

nginx對于tcp的負載均衡實際是偽四層, 因為nginx會代替客戶端向后端服務器發(fā)起請求, 而不是單獨的轉發(fā), 后端服務器看到的是nginx服務器的ip地址
lvs對于tcp的負載均衡是只轉發(fā), 后端服務器看到的是客戶端的源ip地址
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
【社區(qū)內容提示】社區(qū)部分內容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內容

友情鏈接更多精彩內容