haproxy负载均衡
haproxy详解
借助ai来实现,比如配置文件直接给出,然后讲解
1、概述
1.1、简介
-
HAProxy是一个使用C语言编写开源软件,提供高可用,负载均衡,以及基于TCP(四层)和HTTP(七层)的应用程序代理
-
HAProxy特别适用于那些负载特大的web站点,这些站点通常又需要会话保持或七层处理。HAProxy运行在当前的硬件上,完全可以支持数以万计的并发连接。并且它的运行模式使得它可以很简单安全的整合进您当前的架构中, 同时可以保护你的web服务器不被暴露到网络上
-
haproxy能实现什么
什么是haproxy,能实现什么,动静分离,负载均衡
四层和七层
1.2、haproxy支持的算法
2、配置文件详解
2.1、安装haproxy和查看生成的配置文件
yum -y install haproxy
查看生成的配置文件
# 查看生成的主配置文件
[root@server ~]# rpm -qc haproxy
/etc/haproxy/haproxy.cfg # 主配置文件,等会需要讲解里面的参数
/etc/logrotate.d/haproxy
/etc/sysconfig/haproxy
# 生成的所有文件
[root@server ~]# rpm -ql haproxy
/etc/haproxy
/etc/haproxy/conf.d
/etc/haproxy/haproxy.cfg
/etc/ima/digest_lists.tlv/0-metadata_list-compact_tlv-haproxy-2.6.6-18.oe2203sp3.x86_64
/etc/ima/digest_lists/0-metadata_list-compact-haproxy-2.6.6-18.oe2203sp3.x86_64
/etc/logrotate.d/haproxy
/etc/sysconfig/haproxy
/usr/bin/halog
/usr/bin/ip6range
/usr/bin/iprange
/usr/lib/systemd/system/haproxy.service
/usr/sbin/haproxy
/usr/share/haproxy
/usr/share/haproxy/400.http
/usr/share/haproxy/403.http
/usr/share/haproxy/408.http
/usr/share/haproxy/500.http
/usr/share/haproxy/502.http
/usr/share/haproxy/503.http
/usr/share/haproxy/504.http
/usr/share/haproxy/README
/usr/share/licenses/haproxy
/usr/share/licenses/haproxy/LICENSE
/var/lib/haproxy
2.2、主配置讲解(haproxy.cfg)
# 默认的主配置文件
[root@server haproxy]# cat haproxy.cfg
#---------------------------------------------------------------------
# Example configuration for a possible web application. See the
# full configuration options online.
#
# https://www.haproxy.org/download/1.8/doc/configuration.txt
#
#---------------------------------------------------------------------
global # 定义全局参数,属于进程级别的配置
log 127.0.0.1 local2 # 配置日志转发,将haproxy日志发送到本地的127.0.0.1的local2设备上(syslog的本地设备),需要配合rsyslogs这个服务配置日志存储路径
chroot /var/lib/haproxy
pidfile /var/run/haproxy.pid # 指定pid文件
user haproxy # 进程的用户
group haproxy # 进程的用户组
daemon # 守护进程后台运行
maxconn 4000 # 最大连接数为4000
defaults # 用于配置默认参数,些参数可以被用到frontend,backend,Listen组件,影响后面的配置
mode http # haproxy工作模式http,会解析http请求头,支持http特有功能,cookie,重定向,健康检查
# 四层模式tcp,不解析应用层
log global # 继承global块的日志配置
option httplog # 启用详细的http日志记录,请求头,客户端ip等
option dontlognull # 忽略空连接,即客户端建立请求但是没有发送任何请求就断开的情况,避免日志被无效信息刷屏
retries 3 # 设置后端服务器连接失败后的重试次数,3次仍然失败的话,就切换到下一个节点上
timeout http-request 5s
timeout queue 1m
timeout connect 5s
timeout client 1m
timeout server 1m
timeout http-keep-alive 5s
timeout check 5s # 对后端节点健康检查的超时时间,5秒内没有健康检查的响应,视为节点不健康
maxconn 3000 # 默认配置下的最大并发连接数
frontend main # 接收请求的前端虚拟节点,定义一些acl规则,请求定向到后端的backend
# 客户端请求的入口,监听的端口,协议,请求转发规则,这个命名可以自定义
bind *:80 # 设置haproxy监听地址和端口,*表示监听服务器的所有网卡,80是默认端口
default_backend http_back # 默认的后端服务池,所有匹配此前端的请求,就是不匹配acl规则,就将请求转发到这个后端服务器组上
backend http_back # 定义后端服务集群的配置,真实服务器,一个backend对应一个或者多个实体服务器
# 设置算法,健康检查,这个http_back需要与前端配置的名字一样
balance roundrobin # 设置负载均衡器的算法,轮询算法
server node1 127.0.0.1:5001 check # 定义的后端节点,,node1 节点自定义名称(用于日志和监控识别) ,check 启动健康检查
server node2 127.0.0.1:5002 check
server node3 127.0.0.1:5003 check
server node4 127.0.0.1:5004 check
# 还有一个listen字段, 常用于状态页面的监控,以及对后端的检查是前端和后端的组合
3、haproxy实验
3.1、自定义haproxy日志
-
安装haproxy后,默认是没有这个日志文件的,需要配置
-
还需要借助rsyslog服务
确认haproxy日志配置
global
log 127.0.0.1 local2 # 发送日志到本地rsyslog的local2设备,使用syslog协议
defaults
log global # 前端/后端继承global的日志配置
option httplog # 启用详细的HTTP日志(包含请求方法、URL、状态码等)
option dontlognull # 忽略空连接日志,减少无效信息
编辑rsyslog配置文件
vim /etc/rsyslog.conf
$ModLoad imudp # 启用udp ,加载udp模块
$UDPServerRun 514 # 让rsyslog 监听514端口,syslog默认端口
# 配置haproxy 日志的存储规则,local2设备的所有日志级别(info,warn,err等所有级别都收集信息)
local2.* /var/log/haproxy.log
重启日志服务和haproxy服务
systemctl restart rsyslog
systemctl restart haproxy
查看生成的日志
# 由于后端服务器没有配置,所以就是down状态
[root@server rsyslog.d]# tail -f /var/log/haproxy.log
Oct 18 23:17:32 localhost haproxy[2872]: Server http_back/node1 is DOWN, reason: Layer4 connection problem, info: "Connection refused", check duration: 0ms. 3 active and 0 backup servers left. 0 sessions active, 0 requeued, 0 remaining in queue.
Oct 18 23:17:32 localhost haproxy[2872]: Server http_back/node2 is DOWN, reason: Layer4 connection problem, info: "General socket error (Permission denied)", check duration: 0ms. 2 active and 0 backup servers left. 0 sessions active, 0 requeued, 0 remaining in queue.
Oct 18 23:17:33 localhost haproxy[2872]: Server http_back/node3 is DOWN, reason: Layer4 connection problem, info: "Connection refused", check duration: 0ms. 1 active and 0 backup servers left. 0 sessions active, 0 requeued, 0 remaining in queue.
Oct 18 23:17:33 localhost haproxy[2872]: Server http_back/node4 is DOWN, reason: Layer4 connection problem, info: "Connection refused", check duration: 0ms. 0 active and 0 backup servers left. 0 sessions active, 0 requeued, 0 remaining in queue.
Oct 18 23:17:33 localhost haproxy[2872]: backend http_back has no server available!
还可以分割访问日志和错误日志
# 信息级别(info)及以上的访问日志写入access.log
local2.info /var/log/haproxy/haproxy_access.log
# 警告(warn)和错误(err)级别写入error.log
local2.warn;local2.err /var/log/haproxy/haproxy_error.log
3.2、负载均衡实现
- 四个节点
| 节点 | ip | 角色 |
|---|---|---|
| server | 192.68.50.20 | haproxy服务器 |
| node1 | 192.168.50.21 | 后端服务器 |
| node2 | 192.168.50.22 | 后端服务器 |
| client | 192.168.50.1 | 客户端 |
3.2.1、配置haproxy配置文件
frontend main # 配置前端acl规则
bind *:80 # 所有80请求转发到http_back 这个服务器组
default_backend http_back
backend http_back
balance roundrobin # 轮询算法
server node1 192.168.50.21:80 check # 配置后端服务器
server node2 192.168.50.22:80 check
3.2.2、后端服务器配置
[root@node1 conf.d]# cat site1.conf
server {
listen 80;
root /web/80;
}
[root@node2 conf.d]# cat site.conf
server {
listen 80;
root /web/80;
}
# 网页目录定义,防火墙和selinux关闭
3.2.3、客户端访问和查看日志
[C:\~]$ curl 192.168.50.20 -s
node1:80
[C:\~]$ curl 192.168.50.20 -s
node2:80
haproxy日志
# 192.168.50.1 发起了请求
Oct 18 23:42:03 localhost haproxy[3165]: 192.168.50.1:4510 [18/Oct/2025:23:42:03.624] main http_back/node1 0/0/0/0/0 200 206 - - ---- 1/1/0/0/0 0/0 "GET / HTTP/1.1"
Oct 18 23:42:04 localhost haproxy[3165]: 192.168.50.1:4511 [18/Oct/2025:23:42:04.171] main http_back/node2 0/0/0/0/0 200 206 - - ---- 1/1/0/0/0 0/0 "GET / HTTP/1.1"
查看nginx日志
# 显示了haproxy服务器的ip地址,但是没有显示客户端的真实ip地址,后面可以添加一个选项来实现
192.168.50.20 - - [18/Oct/2025:23:45:36 +0800] "GET / HTTP/1.1" 200 9 "-" "curl/8.16.0" "-"
配置nginx日志显示客户端真实的ip地址,修改haproxy主配置文件
option forwardfor except 127.0.0.0/8
# forwardfo 在转发http请求时,会在请求头中添加客户端的真实ip地址,这个是传递ip地址的核心
# except 表示对127.0.0.0/8这个网段不会添加请求头,减少冗余
# 重启haproxy
systemctl restart haproxy
# 再次查看日志
192.168.50.20 - - [18/Oct/2025:23:53:02 +0800] "GET / HTTP/1.1" 200 9 "-" "curl/8.16.0" "192.168.50.1"
# 显示了客户端的真实ip地址
3.3、haproxy图形化页面
- 图形化的监听非常的方便
修改主配置文件
listen stats # 定义一个监听块
bind :8000 # 监听的地址和端口,监听服务器的所有网卡的8000端口
mode http # http模式
stats enable # 开启
stats uri /stats # 统计页面的访问路径 :8000/stats才能访问到
stats realm Haproxy\ Statistics
stats auth admin:password # 访问账号和密码,可以自定义
浏览器访问
http://192.168.50.20:8000/stats

3.4、acl实现动静分离
- 就是静态的请求转发到node1,动态的请求转发到node2上
3.4.1、配置主配置文件
frontend main
bind *:80
default_backend http_back
# 定义acl规则
acl html path_end .html # 匹配的后缀为html转发到html规则上
acl php path_end .php
use_backend htmlweb if html # 如果符合html规则,将其转发到htmlweb服务器组
use_backend phpweb if php
backend htmlweb # 定义静态页面的服务器组
balance roundrobin
server node1 192.168.50.21:80 check
backend phpweb # 定义动态页面的服务器组
balance roundrobin
server ndoe2 192.168.50.22:80 check
3.4.2、配置动态服务器接收php请求
# 安装php,将php.conf文件拷贝过去
# 重启nginx即可
[root@node2 conf.d]# cat site.conf
server {
listen 80;
root /web/80;
index index.php index.html index.htm;
location ~ \.(php|phar)(/.*)?$ {
fastcgi_split_path_info ^(.+\.(?:php|phar))(/.*)$;
fastcgi_intercept_errors on;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param PATH_INFO $fastcgi_path_info;
fastcgi_pass php-fpm;
}
}
3.4.3、客户端访问


4、acl规则详解
-
这个就是haproxy的核心了
-
可以根据这个acl将请求调度到不同的后端服务器组上
4.1、常见的acl规则(frontend块)
- 定义在前端块里面
acl格式
acl <aclname> <criterion> <flags> <operator> <value>
-
aclname是必须字段,给这个acl规则自定义一个名字
-
criterion是必须字段,匹配标准,根据src(客户端ip),请求url(path),或者后缀名(path_end)
-
src 源ip
-
dst 目标ip
-
path_end 匹配文件后缀
-
-
flags 可选字段,用于修改匹配的行为
-
忽略大小写(-i)
-
正则匹配(-m)
-
反转匹配(!)
-
-
operator 可选字段,匹配运算符,范围的匹配,等于(eq),大于(gt)等等
-
value 必须字段,匹配的目标值,ip,字符串,正则表达式
请求来源控制访问
# 请求来源控制访问:
acl allow src 192.168.1.10
acl deny src 192.168.1.0/24
请求方法控制
# 请求方法控制:
acl allow_get method GET
acl allow_get method POST
域名访问控制
# 域名访问控制:
acl allow_domain hdr(host) -i example.com
url请求来源进行访问控制
acl php url_reg -i \.php$ # 使用正则匹配特定url格式
acl php path_end .php # 直接指定URL的地址为.php结尾的文件
acl dir path /api/v1/ # 匹配指定的路径
4.2、为acl规则引用(frontend块)
-
也是配置在frontend块里面的
-
写了acl规则,匹配即可,转发到后端服务器或者等等操作
4.2.1、use_backend 直接指定后端
use_backend backend_name if acl_name
# 或者使用unless,就是取反,只要不是匹配acl_name的都成功,返回一个true
# if 匹配acl_name规则的,返回一个true
4.2.2、为acl指定跳转或者允许限制访问
redirection location https://example.com/ if acl_name
# 匹配acl规则,就跳转到指定网址
允许访问或者限制访问
# 需要开启mode为http,因为是七层的配置
http-request deny if acl_name # 拒绝一个acl访问
http-request allow if acl_name # 允许一个acl访问
tcp的拒绝和允许
# 客户端与服务器建立连接时进行判断
tcp-request connection {accept | reject} [{if | unless} acl_name
# 服务端发送响应后进行判断
tcp-response connection {accept | reject | close} [{if | unless} acl_name
4.3、acl的逻辑关系
-
逻辑与
-
默认是所有的acl之间都是逻辑与关系,2个条件同时满足即可
-
use_backend backend_name if aclname1 aclname2
-
-
逻辑非
-
多个条件中只要有一个满足即可
-
use_backend backend_name if aclname1 or aclname2
-
-
逻辑或
-
对acl进行取反
-
use_backend backend_name if !aclname
-
4.4、acl案例
4.4.1、允许指定的ip访问haproxy的状态页
listen stats #定义名称
bind *:9099 #监听在9099端口
acl sta src 192.168.29.1 #匹配名为sta且源IP地址为192.168.29.1的ACL规则
http-request deny unless sta #拒绝除匹配sta规则以外的规则访问
stats enable #启用stats页
stats uri /myhaproxy?admin #自定义stats页面uri
stats realm "Hello World"
stats auth admin:admin #设置状态页登录账号和密码
4.4.2、七层规则匹配
-
一个后端服务器,80端口是一个statis 1,8080端口页面是 static 2
-
另外一个后端服务器, 是不同的图片
-
配置haproxy服务器

浙公网安备 33010602011771号