Thank you for reading this post, don't forget to subscribe!
В случае балансировки и терминации HTTP(S)-трафика на HAProxy (Layer 7) данная задача легко решается добавлением заголовка “X-Real-IP” и его обработкой на Nginx при помощи модуля ngx_http_realip_module . При балансировке TCP-трафика от HTTPS-клиентов и передаче его на веб-сервера напрямую без модификации или терминации (Layer 4) добавить данный заголовок невозможно, поэтому требуется воспользоваться возможностями, предоставляемыми Proxy Protocol
Балансировка на прикладном уровне (Layer 7): терминация HTTPS-трафика на HAProxy и передача по HTTPS на Nginx
В данном примере HTTPS-трафик от клиента терминируется на HAProxy, модифицируется и передается на Nginx так же по HTTPS.
1 2 |
<strong>haproxy.cfg </strong> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 |
global maxconn 4096 chroot /usr/share/haproxy uid 99 gid 99 daemon tune.ssl.default-dh-param 2048 defaults <span class="hljs-built_in">log</span> global option redispatch option tcp-smart-accept option tcp-smart-connect retries 3 maxconn 2000 timeout connect 5000 timeout check 3000 timeout client 50000 timeout server 50000 frontend http_frontend *:80 mode http redirect scheme https code 301 <span class="hljs-keyword">if</span> !{ ssl_fc } frontend https_frontend_ssl_terminate mode http <span class="hljs-built_in">bind</span> *:443 ssl crt /etc/haproxy/ssl/public.example.com.pem option forwardfor header X-Real-IP default_backend web_server_http backend web_server_http mode http balance roundrobin <span class="hljs-comment"># Отправляем трафик на backend по HTTPS</span> server s1_https 192.168.1.10:443 ssl verify none server s2_https 192.168.1.20:443 ssl verify none |
1 2 |
1 |
<strong>nginx.conf</strong> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
<span class="hljs-section">server</span> { <span class="hljs-attribute">server_name</span> localhost; <span class="hljs-attribute">listen</span> <span class="hljs-number">443</span> ssl default_server; <span class="hljs-attribute">ssl_certificate</span> /etc/nginx/ssl/internal.example.com.pem; <span class="hljs-attribute">ssl_certificate_key</span> /etc/nginx/ssl/internal.example.com.key; <span class="hljs-comment"># Адрес HAProxy</span> <span class="hljs-attribute">set_real_ip_from</span> <span class="hljs-number">192.168.1.254</span>; <span class="hljs-attribute">real_ip_header</span> X-Real-IP; <span class="hljs-attribute">root</span> /usr/share/nginx/html; <span class="hljs-attribute">index</span> index.html index.htm; <span class="hljs-attribute">error_page</span> <span class="hljs-number">500</span> <span class="hljs-number">502</span> <span class="hljs-number">503</span> <span class="hljs-number">504</span> /50x.html; <span class="hljs-attribute">location</span> = /50x.html { <span class="hljs-attribute">root</span> /usr/share/nginx/html; } <span class="hljs-attribute">location</span> <span class="hljs-regexp">~ /\.ht</span> { <span class="hljs-attribute">deny</span> all; } } |
1 2 |
Балансировка на транспортном уровне (Layer 4): передача TCP-трафика с HAProxy на Nginx
В данном примере HTTPS-трафик клиентов не модифицируется (HAProxy вмешивается в транспортный уровень) и его терминация происходит непосредственно на Nginx.
haproxy.cfg
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 |
global maxconn 4096 chroot /usr/share/haproxy uid 99 gid 99 daemon defaults <span class="hljs-built_in">log</span> global option redispatch option tcp-smart-accept option tcp-smart-connect retries 3 maxconn 2000 timeout connect 5000 timeout check 3000 timeout client 50000 timeout server 50000 frontend http_frontend *:80 mode http redirect scheme https code 301 <span class="hljs-keyword">if</span> !{ ssl_fc } frontend https_frontend_ssl_pass mode tcp <span class="hljs-built_in">bind</span> *:443 default_backend web_server_tcp backend web_server_tcp mode tcp balance roundrobin <span class="hljs-comment"># ВНИМАНИЕ! Работа с send-proxy возможна только,</span> <span class="hljs-comment"># когда принимающая сторона понимает, что это такое.</span> <span class="hljs-comment"># Для Nginx необходимо включить в директиву listen</span> <span class="hljs-comment"># опцию proxy_protocol.</span> server s1_tcp 192.168.1.10:443 send-proxy server s2_tcp 192.168.1.20:443 send-proxy |
1 2 |
<strong>nginx.conf</strong> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
<span class="hljs-section">server</span> { <span class="hljs-attribute">server_name</span> localhost; <span class="hljs-comment"># ВНИМАНИЕ! Работа с директивой proxy_protocol возможна только в связке с haproxy.</span> <span class="hljs-comment"># Для прямого доступа данную директиву необходимо отключить.</span> <span class="hljs-attribute">listen</span> <span class="hljs-number">443</span> ssl default_server proxy_protocol; <span class="hljs-attribute">ssl_certificate</span> /etc/nginx/ssl/public.example.com.pem; <span class="hljs-attribute">ssl_certificate_key</span> /etc/nginx/ssl/public.example.com.key; <span class="hljs-comment"># Адрес HAProxy</span> <span class="hljs-attribute">set_real_ip_from</span> <span class="hljs-number">192.168.1.254</span>; <span class="hljs-attribute">real_ip_header</span> proxy_protocol; <span class="hljs-attribute">root</span> /usr/share/nginx/html; <span class="hljs-attribute">index</span> index.html index.htm; <span class="hljs-attribute">error_page</span> <span class="hljs-number">500</span> <span class="hljs-number">502</span> <span class="hljs-number">503</span> <span class="hljs-number">504</span> /50x.html; <span class="hljs-attribute">location</span> = /50x.html { <span class="hljs-attribute">root</span> /usr/share/nginx/html; } <span class="hljs-attribute">location</span> <span class="hljs-regexp">~ /\.ht</span> { <span class="hljs-attribute">deny</span> all; } } |
1 |
<strong> </strong> |