一、HAProxy简介

(1)HAProxy 是一款提供高可用性、负载均衡以及基于TCP(第四层)和HTTP(第七层)应用的代理软件,支持虚拟主机,它是免费、快速并且可靠的一种解决方案。 HAProxy特别适用于那些负载特大的web站点,这些站点通常又需要会话保持或七层处理。HAProxy运行在时下的硬件上,完全可以支持数以万计的 并发连接。并且它的运行模式使得它可以很简单安全的整合进您当前的架构中, 同时可以保护你的web服务器不被暴露到网络上。

(2)HAProxy 实现了一种事件驱动、单一进程模型,此模型支持非常大的并发连接数。多进程或多线程模型受内存限制 、系统调度器限制以及无处不在的锁限制,很少能处理数千并发连接。事件驱动模型因为在有更好的资源和时间管理的用户端(User-Space) 实现所有这些任务,所以没有这些问题。此模型的弊端是,在多核系统上,这些程序通常扩展性较差。这就是为什么他们必须进行优化以 使每个CPU时间片(Cycle)做更多的工作。

(3)HAProxy 支持连接拒绝 : 因为维护一个连接的打开的开销是很低的,有时我们很需要限制攻击蠕虫(attack bots),也就是说限制它们的连接打开从而限制它们的危害。 这个已经为一个陷于小型DDoS攻击的网站开发了而且已经拯救

了很多站点,这个优点也是其它负载均衡器没有的。

(4)HAProxy 支持全透明代理(已具备硬件防火墙的典型特点): 可以用客户端IP地址或者任何其他地址来连接后端服务器. 这个特性仅在Linux 2.4/2.6内核打了cttproxy补丁后才可以使用. 这个特性也使得为某特殊服务器处理部分流量同时又不修改服务器的地址成为可能。

二、四层负载均衡与七层负载均衡

2.1 四层负载均衡

以常见的 TCP 应用为例,负载均衡器在接收到第一个来自客户端的 SYN 请求时,会通过设定的负载均衡算法选择一个最佳的后端服务器,同时将报文中目标 IP 地址修改为后端服务器 IP,然后直接转发给该后端服务器,这样一个负载均衡请求就完成了。从这个过程来看,一个 TCP 连接是客户端和服务器直接建立的,而负载均衡器只不过完成了一个类似路由器的转发动作。在某些负载均衡策略中,为保证后端服务器返回的报文可以正确传递给负载均衡器,在转发报文的同时可能还会对报文原来的源地址进行修改。
 

2.2 七层负载均衡

这里仍以常见的 TCP 应用为例,由于负载均衡器要获取到报文的内容,因此只能先代替后端服务器和客户端建立连接,接着,才能收到客户端发送过来的报文内容,然后再根据该报文中特定字段加上负载均衡器中设置的负载均衡算法来决定最终选择的内部服务器。纵观整个过程,七层负载均衡器在这种情况下类似于一个代理服务器。
 

对比四层负载均衡和七层负载均衡运行的整个过程,可以看出,在七层负载均衡模式下, 负载均衡器与客户端及后端的服务器会分别建立一次 TCP 连接,而在四层负载均衡模式下, 仅建立一次 TCP 连接。由此可知,七层负载均衡对负载均衡设备的要求更高,而七层负载均衡的处理能力也必然低于四层模式的负载均衡。
 

三、HAProxy配置详解

HAProxy 配置文件根据功能和用途,主要有 5 个部分组成,但有些部分并不是必须的, 可以根据需要选择相应的部分进行配置。

   3.1、global 部分

用来设定全局配置参数,属于进程级的配置,通常和操作系统配置有关。

 log:全局的日志配置,local0 是日志设备,info 表示日志级别。其中日志级别有err、warning、info、debug 四种可选。这个配置表示使用 127.0.0.1 上的 rsyslog 服务中的local0 日志设备,记录日志等级为info。

maxconn:设定每个 haproxy 进程可接受的最大并发连接数,此选项等同于 Linux命令行选项“ulimit -n”。

user/ group:设置运行 haproxy 进程的用户和组,也可使用用户和组的 uid 和gid 值来替代。

daemon:设置 HAProxy 进程进入后台运行。这是推荐的运行模式。

nbproc:设置 HAProxy 启动时可创建的进程数,此参数要求将HAProxy 运行模式设置为“daemon”,默认只启动一个进程。根据使用经验,该值的设置应该小于服务器的 CPU 核数。创建多个进程,能够减少每个进程的任务队列,但是过多的进程可能会导致进程的崩溃。

pidfile:指定 HAProxy 进程的 pid 文件。启动进程的用户必须有访问此文件的权限。

   3.2、defaults 部分

默认参数的配置部分。在此部分设置的参数值,默认会自动被引用到下面的 frontend、

backend 和 listen 部分中,因此,如果某些参数属于公用的配置,只需在 defaults 部分添加一次即可。而如果在 frontend、backend 和 listen 部分中也配置了与 defaults 部分一样的参数,那么defaults 部分参数对应的值自动被覆盖。

mode:设置 HAProxy 实例默认的运行模式,有 tcp、http、health 三个可选值。
    tcp 模式     在此模式下,客户端和服务器端之间将建立一个全双工的连接,不会对七层报文做任何类型的检查,默认为 tcp 模式,经常用于 SSL、SSH、SMTP 等应用。
   http 模式     在此模式下,客户端请求在转发至后端服务器之前将会被深度分析,所有不与 RFC 格式兼容的请求都会被拒绝。
   health 模式     目前此模式基本已经废弃,不在多说。

retries:设置连接后端服务器的失败重试次数,连接失败的次数如果超过这里设置的值,HAProxy 会将对应的后端服务器标记为不可用。此参数也可在后面部分进行设置。

timeout connect:设置成功连接到一台服务器的最长等待时间,默认单位是毫秒,但也可以使用其他的时间单位后缀。

timeout client:设置连接客户端发送数据时最长等待时间,默认单位是毫秒,也可以使用其他的时间单位后缀。

timeout server:设置服务器端回应客户度数据发送的最长等待时间,默认单位是毫秒,也可以使用其他的时间单位后缀。

timeout check:设置对后端服务器的检测超时时间,默认单位是毫秒,也可以使用其他的时间单位后缀。

   3.3、frontend 部分

此部分用于设置接收用户请求的前端虚拟节点。frontend 是在 HAProxy1.3 版本之后才引入的一个组件,同时引入的还有 backend 组件。通过引入这些组件,在很大程度上简化了 HAProxy 配置文件的复杂性。frontend 可以根据 ACL 规则直接指定要使用的后端。

bind:此选项只能在 frontend 和 listen 部分进行定义,用于定义一个或几个监听的套接字。bind 的使用格式为:bind [<address>:<port_range>] interface <interface>其中,address 为可选选项,其可以为主机名或IP 地址,如果将其设置为“*”或“0.0.0.0”,将监听当前系统的所有 IPv4 地址。port_range 可以是一个特定的 TCP 端口,也可是一个端口范围,小于 1024 的端口需要有特定权限的用户才能使用。interface 为可选选项,用来指定网络接口的名称,只能在 Linux 系统上使用。

option httplog:在默认情况下,haproxy 日志是不记录 HTTP 请求的,这样很不方便 HAProxy 问题的排查与监控。通过此选项可以启用日志记录 HTTP 请求。

option forwardfor:如果后端服务器需要获得客户端的真实  IP,就需要配置此参数。由于 HAProxy 工作于反向代理模式,因此发往后端真实服务器的请求中的客户端 IP 均为 HAProxy 主机的 IP,而非真正访问客户端的地址,这就导致真实服务器端无法记录客户端真正请求来源的 IP,而“X-Forwarded-For”则可用于解决此问题。通过使用“forwardfor”选项,HAProxy 就可以向每个发往后端真实服务器的请求添加“X-Forwarded-For”记录,这样后端真实服务器日志可以通过“X-Forwarded-For”信息来记录客户端来源 IP。

option httpclose:此选项表示在客户端和服务器端完成一次连接请求后,HAProxy 将主动关闭此 TCP 连接。这是对性能非常有帮助的一个参数。

log global:表示使用全局的日志配置,这里的“ global”表示引用在HAProxy 配置文件 global 部分中定义的 log 选项配置格式。

default_backend:#指定默认的后端服务器池,也就是指定一组后端真实服务器,而这些真实服务器组将在 backend 段进行定义。这里的htmpool 就是一个后端服务器组。

 3.4、backend 部分

此部分用于设置集群后端服务集群的配置,也就是用来添加一组真实服务器,以处理前端用户的请求。添加的真实服务器类似于 LVS 中的real server 节点。

option redispatch:此参数用于 cookie 保持的环境中。在默认情况下,HAProxy会将其请求的后端服务器的 serverID 插入到 cookie 中,以保证会话的 SESSION 持久性。而如果后端的服务器出现故障,客户端的 cookie 是不会刷新的,这就出现了问题。此时,如果设置此参数,就会将客户的请求强制定向到另外一个健康的后端服务器上,以保证服务的正常。

option abortonclose:如果设置了此参数,可以在服务器负载很高的情况下, 自动结束掉当前队列中处理时间比较长的链接。

balance:此关键字用来定义负载均衡算法。目前 HAProxy 支持多种负载均衡算法,常用的有如下几种:
HAProxy实现RabbitMQ负载均衡_haproxy

cookie:表示允许向 cookie 插入 SERVERID,每台服务器的 SERVERID 可在下面的 server 关键字中使用 cookie 关键字定义。

option httpchk:此选项表示启用 HTTP 的服务状态检测功能。HAProxy 作为一款专业的负载均衡器,它支持对 backend 部分指定的后端服务节点的健康检查,以保证在后端 backend 中某个节点不能服务时,把从 frotend 端进来的客户端请求分配至 backend 中其他健康节点上,从而保证整体服务的可用性。“option httpchk”的用法如下:

option httpchk <method> <uri> <version> 其中,各个参数的含义如下:
HAProxy实现RabbitMQ负载均衡_服务器技术_02

server:这个关键字用来定义多个后端真实服务器,不能用于 defaults 和frontend部分。使用格式为:server <name> <address>[:port] [param*] 其中,每个参数含义如下:

check:表示启用对此后端服务器执行健康状态检查。

inter:设置健康状态检查的时间间隔,单位为毫秒。

rise:设置从故障状态转换至正常状态需要成功检查的次数,例如。“rise 2”表示 2 次检查正确就认为此服务器可用。

fall:设置后端服务器从正常状态转换为不可用状态需要检查的次数,例如,“fall 3”表示 3 次检查失败就认为此服务器不可用。

cookie:为指定的后端服务器设定 cookie 值,此处指定的值将在请求入站时被检查,第一次为此值挑选的后端服务器将在后
HAProxy实现RabbitMQ负载均衡_haproxy_03

 

3.5、listen 部分

此部分是 frontend 部分和 backend 部分的结合体。在 HAProxy1.3 版本之前,

HAProxy 的所有配置选项都在这个部分中设置。为了保持兼容性,HAProxy 新的版本仍然保留了 listen 组件的配置方式。目前在 HAProxy 中,两种配置方式任选其一即可。

这个部分通过listen 关键字定义了一个名为“admin_stats”的实例,其实就是定义了一个 HAProxy 的监控页面,每个选项的含义如下:

stats refresh:设置 HAProxy 监控统计页面自动刷新的时间。

stats uri:设置 HAProxy 监控统计页面的URL 路径,可随意指定。例如、指定“stats uri /haproxy-status”,就可以过 http://IP:9188/haproxy-status  查看。

stats realm:设置登录 HAProxy 统计页面时密码框上的文本提示信息。

stats auth:设置登录 HAProxy 统计页面的用户名和密码。用户名和密码通过冒号分割。可为监控页面设置多个用户名和密码,每行一个。

stats hide-version:用来隐藏统计页面上 HAProxy 的版本信息。

stats admin if TRUE:通过设置此选项,可以在监控页面上手工启用或禁用后端真实服务器,仅在 haproxy1.4.9 以后版本有效。

3.6、一份完整的配置

global
    log 127.0.0.1 local0 info 
    maxconn 4096
    user nobody 
    group nobody 
    daemon 
    nbproc 1
    pidfile /usr/local/haproxy/logs/haproxy.pid
defaults
    mode http 
    retries 3
    timeout connect 10s 
    timeout client 20s 
    timeout server 30s
    timeout check 5s
frontend www
    bind *:80 
    mode	http
    option	httplog 
    option	forwardfor
    option	httpclose 
    log	global
    #acl host_www	hdr_dom(host)	-i	www.zb.com
    #acl host_img	hdr_dom(host)	-i	img.zb.com
 
    #use_backend htmpool	if	host_www 
    #use_backend imgpool	if	host_img 
    default_backend	htmpool
backend htmpool
    mode http 
    option	redispatch
    option	abortonclose 
    balance  static-rr 
    cookie	SERVERID
    option	httpchk GET /index.jsp
    server	237server 192.168.81.237:8080 cookie server1 weight 6 check inter 2000 rise 2 fall 3
    server	iivey234 192.168.81.234:8080 cookie server2 weight 3 check inter 2000 rise 2 fall 3
backend imgpool
    mode		http 
    option	redispatch
    option	abortonclose
     balance  static-rr 
    cookie  SERVERID
    option	httpchk GET /index.jsp
    server	host236 192.168.81.236:8080 cookie server1 weight 6 check inter 2000 rise 2 fall 3
 
listen admin_stats
    bind 0.0.0.0:9188
    mode http
    log 127.0.0.1 local0 err 
    stats refresh 30s
    stats uri /haproxy-status
    stats realm welcome login\ Haproxy 
    stats auth admin:admin123
    stats hide-version 
    stats admin if TRUE
   

 

四、HAProxy+RabbitMQ的负载均衡实战

最近看了一下RabbitMQ的负载均衡策略,对于RabbitMQ集群来说,主要有两类负载均衡,客户端内部的和服务端的,客户端内部主要是采用负载均衡算法,服务端主要是采用代理服务器,这里记录一下,采用尝试HAProxy实现RabbitMQ负载均衡的操作。

4.1 安装HAProxy

下载HAProxy相关版本,这里下载haproxy-1.8.12.tar.gz,之后准备安装
安装之前查看内核版本

uname -r

根据内核版本选择编译参数:

HAProxy实现RabbitMQ负载均衡_服务器技术_04

解压HAProxy,并安装

tar xf haproxy-1.8.12.tar.gz
cd haproxy-1.7.5
make TARGET=linux2628 PREFIX=/usr/local/haproxy
make install PREFIX=/usr/local/haproxy

安装成功之后,查看版本

/usr/local/haproxy/sbin/haproxy -v

4.2 配置HAProxy

配置启动文件,复制haproxy文件到/usr/sbin下 ,复制haproxy脚本,到/etc/init.d下

cp /usr/local/haproxy/sbin/haproxy /usr/sbin/
cp ./examples/haproxy.init /etc/init.d/haproxy
chmod 755 /etc/init.d/haproxy

创建系统账号

useradd -r haproxy

创建配置文件

mkdir /etc/haproxy
vi /etc/haproxy/haproxy.cfg

更改配置文件

#全局配置
global
    #设置日志
    log 127.0.0.1 local0 info
    #当前工作目录
    chroot /usr/local/haproxy
    #用户与用户组
    user haproxy
    group haproxy
    #运行进程ID
    uid 99
    gid 99
    #守护进程启动
    daemon
    #最大连接数
    maxconn 4096

#默认配置
defaults
    #应用全局的日志配置
    log global
    #默认的模式mode {tcp|http|health}
    #TCP是4层,HTTP是7层,health只返回OK
    mode tcp
    #日志类别tcplog
    option tcplog
    #不记录健康检查日志信息
    option dontlognull
    #3次失败则认为服务不可用
    retries 3
    #每个进程可用的最大连接数
    maxconn 2000
    #连接超时
    timeout connect 5s
    #客户端超时
    timeout client 120s
    #服务端超时
    timeout server 120s

#绑定配置
listen rabbitmq_cluster 
        bind 0.0.0.0:5671
        #配置TCP模式
        mode tcp
        #简单的轮询
        balance roundrobin
        #RabbitMQ集群节点配置
        server rmq_node1 10.110.8.34:5672 check inter 5000 rise 2 fall 3 weight 1
        server rmq_node2 10.110.8.38:5672 check inter 5000 rise 2 fall 3 weight 1

#haproxy监控页面地址
listen monitor 
        bind 0.0.0.0:8100
        mode http
        option httplog
        stats enable
        stats uri /stats
        stats refresh 5s

4.3 启动haproxy

service haproxy start

启动成功后,界面如图:

HAProxy实现RabbitMQ负载均衡_haproxy_05

 

五、haproxy 解决集群 session 共享问题

Haproxy 二种方法保持客户端 session 一致

5.1、用户 IP 识别

haroxy 将用户 IP 经过 hash 计算后 指定到固定的真实服务器上(类似于 nginx 的 IP hash 指令)

配置指令: balance source

backend htmpool
        mode http
        option redispatch
        option abortonclose
        balance source
        cookie SERVERID
        option httpchk GET /index.jsp
        server 237server 192.168.81.237:8080 cookie server1 weight 6 check inter 2000 rise 2 fall 3
        server iivey234 192.168.81.234:8080 cookie server2 weight 3 check inter 2000 rise 2 fall 3

5.2、 cookie 识别

haproxy 将WEB 服务端发送给客户端的 cookie 中插入(或添加加前缀)haproxy 定义的后端的服务器COOKIE ID。

配置指令例举 cookie SESSION_COOKIE insert indirect nocache

backend htmpool
        mode http
        option    redispatch
        option    abortonclose
        balance  static-rr
        cookie    SERVERID   #cookie参数
        option    httpchk GET /index.jsp
        server    237server 192.168.81.237:8080 cookie server1 weight 6 check inter 2000 rise 2 fall 3   #server里面的cookie参数
        server    iivey234 192.168.81.234:8080 cookie server2 weight 3 check inter 2000 rise 2 fall 3   #server里面的cookie参数

——————————————————————

相关文档:http://www.haproxy.org/

                  http://cbonte.github.io/haproxy-dconv/1.8/intro.html#3.1

——————————————————————

作者:DFKyun
链接:https://www.jianshu.com/p/e57c361c8e12
来源:简书
简书著作权归作者所有,任何形式的转载都请联系作者获得授权并注明出处。