configure HAProxy 2+

The path of an engineer in telecom often begins with a technical support service. If you want to grow high-quality specialists from newcomers, you need to give them the opportunity to work on tasks that are beyond the scope of their duties. We try to help active colleagues in development – this is one of the main principles HOSTKEY since the founding of the company. We publish a note on the implementation of proxying the administrative panel FreeIPA through HAProxywritten by our technical support engineer Alexander Tryapkin.

(And here you can read how to synchronize FreeIPA with Active Directory).

Problem

We have three FreeIPA admin panel hosts (freeipa01.inside.mydomain.ru, freeipa02.inside.mydomain.ru and freeipa03.inside.mydomain.ru). It is necessary to provide access to them by one domain name: freeipa.mydomain.ru. Despite the apparent simplicity of the task, some efforts had to be made to solve it, since there were no ready-made recipes for HAProxy version 2.0 and higher on the Internet.

Each FreeIPA installation is tied to its own domain name, which means we need to edit the headers of incoming and outgoing HTTP requests. The self-service portal must be closed with a valid certificate, while the FreeIPA hosts running in the backend must not be changed so as not to affect the interaction between clients and servers through the API.

In older versions of HAProxy (1+), the method used to edit HTTP headers was reqrep/rsprep. There are instructions online for configuring HAProxy and FreeIPA using this method, but in version 2.0 it was marked as deprecated, and in version 2.1 it was completely deprecated. Instead of rsprep we will use the method http-response.

Solution

First, let’s edit the default HAProxy configuration file. It has four sections: global, defaults, front end and backend. We will not touch the first two (standard values ​​​​are enough), but front end and backend Let’s describe in detail:

#Секция frontend
frontend main 
    bind :80
    redirect scheme https code 301 if !{ ssl_fc } # редиректим на https
frontend main_ssl
    bind :443 ssl crt /etc/haproxy/ssl/ # используем сертификаты из директории 
    use_backend freeipa if { ssl_fc_sni freeipa.mydomain.ru  } # в случае если обращаются к freeipa.mydomain.ru используем backend FreeIPA
#Секция backend
backend freeipa
  mode http
  balance roundrobin # по очереди распределяем нагрузку по хостам
  cookie SERVERID insert indirect nocache httponly secure # добавляем cookie для направления трафика на основе него
#acl для request на основе добавленного cookei
  acl hdr_req_ipa01 req.hdr(Cookie) -m sub ipa01 
  acl hdr_req_ipa02 req.hdr(Cookie) -m sub ipa02 
  acl hdr_req_ipa03 req.hdr(Cookie) -m sub ipa03 
#--------------------------------------------------------------------------
#В зависимости от того, каким cookie помечен наш запрос, изменяем заголовки Host и Referer 
  http-request set-header Host freeipa01.inside.mydomain.ru if hdr_req_ipa01
  http-request replace-header Referer ^https?://freeipa\.mydomain\.ru(.*)$   https://freeipa01\.inside\.mydomain\.ru\1  if hdr_req_ipa01
  http-request set-header Host freeipa02.inside.mydomain.ru if hdr_req_ipa02
  http-request replace-header Referer ^https?://freeipa\.mydomain\.ru(.*)$ https://freeipa01\.inside\.mydomain\.ru\1 if hdr_req_ipa02
  http-request set-header Host freeipa03.inside.mydomain.ru if hdr_req_ipa03
  http-request replace-header Referer ^https?://freeipa\.mydomain\.ru(.*)$ https://freeipa01\.inside\.mydomain\.ru\1 if hdr_req_ipa03
#--------------------------------------------------------------------------
#acl для response на основе заголовка Location 
  acl hdr_ipa01 res.hdr(Location) -m sub freeipa01.inside.mydomain.ru
  acl hdr_ipa02 res.hdr(Location) -m sub freeipa02.inside.mydomain.ru
  acl hdr_ipa03 res.hdr(Location) -m sub freeipa03.inside.mydomain.ru
#--------------------------------------------------------------------------
#В зависимости от того с какого хоста пришел ответ редактируем заголовки Set-Cookie и Location Без редактирования заголовка Location мы столкнемся со следующей проблемой: пользователь при переходе по ссылке freeipa.mydomain.ru будет переброшен на один из хостов freeipa0x.inside.mydomain.ru (это важный момент пропущенный во всех найденных руководствах)
  http-response replace-header Set-Cookie ^Domain=freeipa01\.inside\.mydomain\.ru(.*) Domain=freeipa\.mydomain\.ru\1 if hdr_ipa01
  http-response replace-value Location ^https?://freeipa01\.inside\.mydomain\.ru(.*)$ https://freeipa\.mydomain\.ru\1 if hdr_ipa01
  http-response replace-header Set-Cookie ^Domain=freeipa02\.inside\.mydomain\.ru(.*) Domain=freeipa\.mydomain\.ru\1 if hdr_ipa02
  http-response replace-value Location ^https?://freeipa02\.inside\.mydomain\.ru(.*)$ https://freeipa\.mydomain\.ru\1 if hdr_ipa02
  http-response replace-header Set-Cookie ^Domain=freeipa03\.inside\.mydomain\.ru(.*) Domain=freeipa\.mydomain\.ru\1 if hdr_ipa03
  http-response replace-value Location ^https?://freeipa03\.inside\.mydomain\.ru(.*)$ https://freeipa\.mydomain\.ru\1 if hdr_ipa03
#--------------------------------------------------------------------------
#Здесь указываем наши хосты FreeIPA
    server ipa01 freeipa01.inside.mydomain.ru:443 check port 443 inter 5s rise 2 fall 5 cookie ipa01 weight 9 ssl verify none
    server ipa02 freeipa02.inside.mydomain.ru:443 check port 443 inter 5s rise 2 fall 5 cookie ipa02 weight 1 ssl verify none
    server ipa03 freeipa03.inside.mydomain.ru:443 check port 443 inter 5s rise 2 fall 5 cookie ipa03 weight 3 ssl verify none
#check port 443 - проверяем жив ли хост по 443 порту.
#inter 5s - проверяем доступность с интервалом 5 секунд. 
#rise 2 fall 5 - если 2 раза проверка скажет что хост недоступен он будет исключен из балансировки и возвращен после 5 успешных проверок
#cookie ipa0x - указывает какое cookie будет добавляться “cookie SERVERID insert”
#ssl verify none - терминация SSL-сертификата игнорируя ошибки
#weight 3 указываем приоритет распределения нагрузки

You may also encounter an annoying basic authorization window in Chrome, Edge, IE and some other browsers.

The appearance of this window is described in bug report and there is a solution to the problem, but with the help of HAProxy it can be bypassed without changing the configuration of the hosts. To do this, add the following line to the backend section of the configuration file:

http-response del-header www-authenticate

It will remove the header responsible for the intrusive window from the host response.

Results

Comparing the solution of the problem with rsprep and through http-responseyou can better understand the HAProxy logic and learn how to work with HTTP requests at a deeper level.

_________

As you can see, it’s good for the business to keep the technical support engineers on the initiative. We not only help specialists to develop and make a career (which is again beneficial for the employer), but also receive application developments that are useful to clients, as well as interesting notes for a corporate blog. We hope that our solution will be useful to readers.

A special promo code I FROM HABRA» can also come in handy: call it to the consultant on the site when placing an order to get an additional discount. You can pay as always in rubles with VAT for a Russian company or in euros for a company in the Netherlands.

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *