概述

在生产环境中,越来越多的人选择使用https, 也就是ssl 证书,如果你生产环境中也使用了HAproxy,那我们我门就得决定我门如何配置我们的HAproxy来

正常来说,我们的HAproxy 作为一个中间件在客户端和我们真正接受请求的服务器中间,如果我们要在这样的格局下启用SSL我们有两个选择

SSL Termination  是指我们把解密的工作交给我们的HAproxy来做,然后将揭秘后的请求发送给后端的服务器,这意味着HAproxy需要来做解密工作,这个工作会产生一个耗时和cpu消耗

这与另外一个方式正好相反 SSL Pass-Through, 在这个模式中,我们会直接将加密的请求发送给后端服务器,HAproxy不做任何的处理,仅仅是转发

在这种模式下,确实可以将解密的压力分散给后端服务器,但是同时我们也失去了我们对请求的修改能力,例如修改HTTP header,因为HAproxy仅仅是转发

HAProxy with SSL Termination

We’ll cover the most typical use case first – SSL Termination. As stated, we need to have the load balancer handle the SSL connection. This means having the SSL Certificate live on the load balancer server.

我们先讲一下最常规的模式,这种模式,我们要先要HAproxy 服务器配置ssl

Default
frontend localhost
bind *:80
bind *:443 ssl crt /etc/ssl/xip.io/xip.io.pem
mode http
default_backend nodes


然后我们配置后端

Default
backend nodes
mode http
balance roundrobin
option forwardfor
option httpchk HEAD / HTTP/1.1\r\nHost:localhost
server web01 172.17.0.3:9000 check
server web02 172.17.0.3:9001 check
server web03 172.17.0.3:9002 check
http-request set-header X-Forwarded-Port %[dst_port]
http-request add-header X-Forwarded-Proto https if { ssl_fc }


因为请求在发送给后端服务器的时候已经解密,是正常的HTTP请求,所以我们的配置无需做任何修改

SSL Only

If you’d like the site to be SSL-only, you can add a redirect directive to the frontend configuration:

如果我们希望我们的网站仅仅接受https请求,配置一下自动跳转(http->https)

Default
frontend localhost
bind *:80
bind *:443 ssl crt /etc/ssl/xip.io/xip.io.pem
redirect scheme https if !{ ssl_fc }
mode http
default_backend nodes


在ssl pass-through模式下,我们让后端服务器处理加密后的请求

这个时候我们的HAproxy的工作仅仅是转发,但是因为这个时候请求仍然是加密的,我们的HAproxy无法对请求做的任何的操作(除了转发)

所以,在HAproxy的配置中,我们需要使用HAproxy的Tcp 模式,而不是之前的HTTP模式

配置修改如下:

Default
frontend localhost
bind *:80
bind *:443
option tcplog
mode tcp
default_backend nodes


端口是不变的,但是模式我们需要修改为tcp,并且修改相关的tcplog

接下来我们需要修改backend,同样的,我们要把模式修改为tcp,并且我们删除了option forwardfor 和http-request , 这两个配置在tcp模式下无法使用,因为我们无法注入没解密的数据,相应的检测我们也修改改成了ssh-hello-chk

Default
backend nodes
mode tcp
balance roundrobin
option ssl-hello-chk
server web01 172.17.0.3:443 check
server web02 172.17.0.4:443 check


这样的话两种方式就完成了

Reading custom headers in Nginx – Not mentioned in this edition specifically, but useful in context of reading X-Forwarded-* headers sent to Nginx

So You Got Yourself a Load Balancer, an article about considerations to make in your applications when using a load balancer.