Willy dostał odpowiedź e-mailem. Pomyślałem, że się tym podzielę. Jego odpowiedzi są pogrubione.
Mam pytanie odnośnie mojej konfiguracji haproxy:
#---------------------------------------------------------------------
# Global settings
#---------------------------------------------------------------------
global
log 127.0.0.1 syslog emerg
maxconn 4000
quiet
user haproxy
group haproxy
daemon
#---------------------------------------------------------------------
# common defaults that all the 'listen' and 'backend' sections will
# use if not designated in their block
#---------------------------------------------------------------------
defaults
mode http
log global
option abortonclose
option dontlognull
option httpclose
option httplog
option forwardfor
option redispatch
timeout connect 10000 # default 10 second time out if a backend is not found
timeout client 300000 # 5 min timeout for client
timeout server 300000 # 5 min timeout for server
stats enable
listen http_proxy localhost:81
balance roundrobin
option httpchk GET /empty.html
server server1 myip:80 maxconn 15 check inter 10000
server server2 myip:80 maxconn 15 check inter 10000
Jak widać, jest to proste, ale jestem trochę zdezorientowany, jak działają właściwości maxconn.
Na serwerze, w bloku nasłuchu, znajduje się jeden globalny i maxconn.
Jest też inny w bloku nasłuchiwania, który domyślnie wynosi około 2000.
Moje myślenie jest takie: połączenie globalne zarządza całkowitą liczbą połączeń, które haproxy, jako usługa, będzie kolejkować lub przetwarzać jednocześnie.
Poprawny. Jest to maksymalna liczba równoczesnych połączeń na proces.
Jeśli liczba przekroczy tę, albo zrywa połączenie, albo gromadzi się w jakimś gnieździe linuxowym?
Później po prostu przestaje akceptować nowe połączenia i pozostają one w kolejce gniazd w jądrze. Liczba gniazd w kolejce jest określana przez wartość min z (net.core.somaxconn, net.ipv4.tcp_max_syn_backlog i maxconn bloku nasłuchiwania).
Nie mam pojęcia, co się stanie, jeśli liczba przekroczy 4000.
Nadmiarowe połączenia czekają na zakończenie kolejnego, zanim zostaną zaakceptowane. Jednak dopóki kolejka jądra nie jest zapełniona, klient nawet tego nie zauważa, ponieważ połączenie jest akceptowane na poziomie TCP, ale nie jest przetwarzane. Tak więc klient zauważa tylko pewne opóźnienie w przetworzeniu żądania. Ale w praktyce maxconn bloku nasłuchiwania jest znacznie ważniejszy, ponieważ domyślnie jest mniejszy niż globalny. Maksymalne połączenie nasłuchiwania ogranicza liczbę połączeń na odbiorcę. Ogólnie rzecz biorąc, rozsądnie jest skonfigurować go dla liczby połączeń, które chcesz dla usługi, i skonfigurować globalne maxconn do maksymalnej liczby połączeń, które pozwolisz obsłużyć procesowi haproxy. Jeśli masz tylko jedną usługę, obie mogą mieć tę samą wartość. Ale jeśli masz wiele usług,
Następnie masz właściwość maxconn serwera ustawioną na 15. Po pierwsze, ustawiłem to na 15, ponieważ mój php-fpm, to jest przekazywanie na oddzielny serwer, ma tylko tyle procesów potomnych, których może użyć, więc upewniam się, że jestem gromadzenie żądań tutaj, zamiast w php-fpm. Co myślę, że jest szybsze.
Tak, nie tylko powinno być szybsze, ale także pozwala haproxy znaleźć inny dostępny serwer, kiedy tylko jest to możliwe, a także pozwala na zabicie żądania w kolejce, jeśli klient osiągnie „stop”, zanim połączenie zostanie przekazane do serwera.
Ale wracając do tematu, moja teoria dotycząca tej liczby jest taka, że każdy serwer w tym bloku będzie miał tylko 15 połączeń naraz. Następnie połączenia będą czekać na otwarty serwer. Gdybym miał włączone pliki cookie, połączenia czekałyby na PRAWIDŁOWY otwarty serwer. Ale ja nie.
To jest dokładnie zasada. Istnieje kolejka na serwer proxy i kolejka na serwer. Połączenia z trwałym plikiem cookie przechodzą do kolejki serwera, a inne połączenia do kolejki proxy. Ponieważ jednak w Twoim przypadku nie jest skonfigurowany żaden plik cookie, wszystkie połączenia trafiają do kolejki proxy. Możesz spojrzeć na diagram doc / queuing.fig w źródłach haproxy, jeśli chcesz, wyjaśnia on, jak / gdzie są podejmowane decyzje.
Oto pytania:
Co się stanie, jeśli liczba połączeń globalnych przekroczy 4000? Czy umierają? Lub w jakiś sposób bilard w Linuksie?
Są w kolejce w Linuksie. Gdy przytłoczysz kolejkę jądra, zostaną one upuszczone do jądra.
Czy połączenie globalne jest powiązane z połączeniami z serwerem, poza faktem, że całkowita liczba połączeń z serwerem nie może być większa niż globalna?
Nie, ustawienia globalne i ustawienia połączenia z serwerem są niezależne.
Czy przy obliczaniu połączeń globalnych nie powinna to być liczba połączeń zsumowanych w sekcji serwera plus pewien procent dla puli? I oczywiście masz inne ograniczenia na połączeniach, ale tak naprawdę to ile chcesz wysłać do serwerów proxy?
Masz rację. Jeśli czas odpowiedzi serwera jest krótki, nie ma nic złego w ustawianiu tysięcy połączeń w kolejce, aby obsłużyć tylko kilka naraz, ponieważ znacznie skraca to czas przetwarzania żądań. Praktycznie, ustanowienie połączenia zajmuje obecnie około 5 mikrosekund w gigabitowej sieci LAN. Dlatego warto pozwolić haproxy na jak najszybszą dystrybucję połączeń ze swojej kolejki do serwera z bardzo małym maxconn. Pamiętam, że jedna witryna z grami kolejkuje ponad 30000 jednoczesnych połączeń i działa z kolejką 30 na serwer! Był to serwer Apache, a Apache jest znacznie szybszy przy małej liczbie połączeń niż przy dużych liczbach. Ale do tego naprawdę potrzebujesz szybkiego serwera, ponieważ nie Chcę, aby wszyscy klienci byli w kolejce, czekając na miejsce połączenia, ponieważ serwer czeka na przykład na bazę danych. Coś, co działa bardzo dobrze, to dedykowanie serwerów. Jeśli Twoja witryna ma wiele statystyk, możesz skierować żądania statyczne do puli serwerów (lub pamięci podręcznych), aby nie kolejkować na nich żądań statycznych i aby żądania statyczne nie zjadały drogich gniazd połączeń. Mam nadzieję, że to pomoże, Willy