2009-08-17 10 views
21

Jak określić najlepszą liczbę maxSpare, minSpace i maxThreads, acceptCount itp w Tomcat? Czy istnieją najlepsze praktyki?Jak określić najlepszą liczbę wątków w Tomcat?

Rozumiem, że musi to być oparte na sprzęcie (np. Na rdzeniu) i może być jedynie podstawą do dalszych testów wydajności i optymalizacji na określonym sprzęcie.

Odpowiedz

46

"Ile problemów z wątkami" jest dość dużym i skomplikowanym problemem i nie można udzielić na nie prostej odpowiedzi.

Biorąc pod uwagę, ile masz rdzeni jest przydatna w aplikacjach wielowątkowych, które mają tendencję do zużywania dużej ilości procesora, takich jak zgniecenie numerów i tym podobne. Rzadko zdarza się to w przypadku aplikacji internetowej, która zwykle jest blokowana nie przez procesor, ale przez inne czynniki.

Jednym z powszechnych ograniczeń jest opóźnienie między Tobą a innymi systemami zewnętrznymi, w szczególności Twoim DB. Za każdym razem, gdy przychodzi żądanie, prawdopodobnie kwerenda do bazy danych kilka razy, co oznacza przesyłanie strumieniowe niektórych bajtów przez połączenie JDBC, a następnie oczekiwanie na te bajty, aby dotrzeć do bazy danych (nawet jeśli jest to na lokalnym hoście, wciąż jest małe opóźnienie) , następnie czekanie, aż DB rozpatrzy nasze żądanie, a następnie poczekamy na przetestowanie bazy danych (sama baza danych będzie czekała na dysk w celu przeszukiwania określonego regionu) itp. ...

Przez cały ten czas wątek jest bezczynny, więc inny wątek może z łatwością wykorzystać te zasoby procesora do zrobienia czegoś pożytecznego. Często zdarza się, że od 40% do 80% czasu oczekiwania na odpowiedź DB.

To samo dzieje się również po drugiej stronie połączenia. Podczas gdy twój wątek zapisuje dane wyjściowe do przeglądarki, szybkość połączenia KLIENTA może sprawić, że wątek będzie bezczynny, aż przeglądarka potwierdzi, że dany pakiet został odebrany. (Było to sporą kwestią kilka lat temu, najnowsze jądra i maszyny JVM używają większych buforów, aby zapobiegać wątkom w taki sposób, ale odwrotny serwer proxy przed serwerem aplikacji WWW, nawet po prostu httpd, może być naprawdę użyteczny, aby unikać ludzi ze złym połączeniem internetowym do ataków DDOS :))

Biorąc pod uwagę te czynniki, liczba wątków powinna być zwykle o wiele większa niż liczba rdzeni. Nawet na prostym dwurdzeniowym lub czterordzeniowym serwerze powinieneś skonfigurować przynajmniej kilkadziesiąt wątków.

Co ogranicza liczbę wątków, które można skonfigurować?

Przede wszystkim każdy wątek (używany) zużywa wiele zasobów. Każdy wątek ma stos, który zużywa pamięć RAM. Co więcej, każdy wątek faktycznie przydziela rzeczy na stercie, aby wykonać swoją pracę, zużywając ponownie RAM, a akt przełączania między wątkami (przełączanie kontekstów) jest dość ciężki dla jądra JVM/OS.

To sprawia, że ​​trudno jest uruchomić serwer z tysiącami wątków "sprawnie".

Biorąc pod uwagę ten obraz, istnieje szereg technik (głównie: spróbuj, nie, melodia, spróbuj ponownie), aby określić mniej więcej, ile tematów aplikacja będzie potrzebować:

1) Postaraj się zrozumieć, gdzie wątki spędzają czas. Istnieje wiele dobrych narzędzi, ale nawet profiler jvisualvm może być świetnym narzędziem lub aspektem śledzenia, który generuje statystyki podsumowujące czas. Im więcej czasu spędzają na oczekiwaniu na coś zewnętrznego, tym więcej można odradzać więcej wątków, aby używać procesora w czasie bezczynności.

2) Określ użycie pamięci RAM.Biorąc pod uwagę, że JVM użyje pewnej ilości pamięci (przede wszystkim przestrzeni permen, zwykle do setek megabajtów, znowu powie jvisualvm) niezależnie od tego, ile wątków używasz, spróbuj uruchomić z jednym wątkiem, a następnie z dziesięcioma, a następnie z sto, jednocześnie podkreślając aplikację za pomocą jmetera lub cokolwiek innego i zobaczyć, jak rośnie wykorzystanie sterty. To może stanowić twardy limit.

3) Spróbuj określić cel. Każde żądanie użytkownika wymaga obsługi wątku. Jeśli średni czas odpowiedzi wynosi 200ms na "get" (lepiej byłoby nie uwzględniać ładowania obrazów, CSS i innych zasobów statycznych), każdy wątek może obsłużyć 4/5 stron na sekundę. Jeśli od każdego użytkownika oczekuje się "kliknięcia" co 3/4 sekundy (zależnie od tego, czy jest to gra przeglądarkowa lub witryna z wieloma długimi tekstami?), Jeden wątek "obsłuży 20 równoczesnych użytkowników", cokolwiek to znaczy. Jeśli w godzinach szczytu masz 500 pojedynczych użytkowników trafiających na twoją stronę w ciągu 1 minuty, potrzebujesz wystarczającej ilości wątków, by sobie z tym poradzić.

4) Awaria testu górnego limitu. Użyj jmetera, skonfiguruj serwer z wieloma wątkami na zapasowej maszynie wirtualnej i zobacz, jak czas reakcji pogorszy się po przekroczeniu określonego limitu. To ważniejsze niż sprzęt, implementacja wątku systemu operacyjnego jest tutaj ważna, ale bez względu na to, co osiągnie punkt, w którym procesor spędza więcej czasu, próbując dowiedzieć się, który wątek jest uruchamiany, a nie uruchamiając go, a ta liczba nie jest tak niewiarygodnie wysoki.

5) Zastanów się, jak wątki będą wpływać na inne komponenty. Każdy wątek prawdopodobnie będzie korzystał z jednego (lub może więcej niż jednego) połączenia z bazą danych, czy baza danych jest w stanie obsłużyć 50/100/500 równoległych połączeń? Nawet jeśli używasz sharded cluster nosql servers, czy farma serwerów oferuje wystarczającą przepustowość między tymi maszynami? Co jeszcze będzie działać na tym samym komputerze z serwerem aplikacji WWW? Anach httpd? kałamarnica? sama baza danych? lokalne proxy buforowania do bazy danych, takie jak mongos lub memcached?

Widziałem systemy w produkcji z tylko 4 wątkami + 4 zapasowe wątki, ponieważ praca wykonywana przez ten serwer polegała jedynie na zmianie rozmiaru obrazów, więc było to prawie 100% procesora, a inne skonfigurowane na mniej więcej ten sam sprzęt z kilkoma setkami wątków, ponieważ webapp wykonywał wiele wywołań SOAP do zewnętrznych systemów i spędzał większość czasu na oczekiwaniu na odpowiedzi.

Oce określiłeś ok. Minimalne i maksymalne wątki są optymalne dla Ciebie, wtedy zazwyczaj konfiguruję je w ten sposób:

1) W oparciu o ograniczenia pamięci RAM, innych zewnętrznych zasobów i eksperymentów związanych z przełączaniem kontekstów, istnieje absolutne maksimum, które nie może zostać osiągnięte. Tak więc, użyj maxThreads, aby ograniczyć go do około połowy lub 3/4 tej liczby.

2) Jeśli aplikacja jest stosunkowo szybka (na przykład udostępnia usługi WWW REST, które zazwyczaj wysyłają odpowiedź, jest to kilka milisekund), można skonfigurować duży akceptujący kod, do tej samej liczby wartości maxThread. Jeśli dysponujesz systemem równoważenia obciążenia przed serwerem aplikacji WWW, ustaw mały akceptor, lepiej, aby system równoważenia obciążenia widział niedopuszczalne żądania i przełącz się na inny serwer, niż wstrzymywanie użytkowników na już zajęty.

3) Ponieważ uruchomienie wątku jest (nadal) uważane za ciężką operację, użyj minSpareThreads, aby przygotować kilka wątków po nadejściu godzin szczytu. To znowu zależy od rodzaju obciążenia, którego się spodziewasz. Rozsądne jest posiadanie ustawień minSpareThreads, maxSpareThreads i maxThreads, aby dokładna liczba wątków była zawsze gotowa, nigdy nie odzyskana, a wydajność przewidywalna. Jeśli korzystasz z tomcat na dedykowanej maszynie, możesz podnieść minSpareThreads i maxSpareThreads bez żadnego niebezpieczeństwa przejmowania innych procesów, w przeciwnym razie przestroić je, ponieważ wątki są zasobami współdzielonymi z resztą procesów działających na większości systemów operacyjnych.

Powiązane problemy