Dziwny przypadek Mr. Time To First Byte


14

Mam serwer sieciowy oparty na Linode 1024 VPS

  • Ubuntu 11.10
  • Nginx 1.0.5
  • PHP 5.3.6 (z PHP-FPM, APC)
  • Lakier 3.0.2

I kilka blogów tam opartych na WordPress 3.3.1. Jednym z nich jest zwykły blog z domyślną konfiguracją, motywem i postem „Hello World”, aby przetestować serwer. Drugi to blog sklonowany z innego serwera z prawie 10 000 postów i ponad 10 000 komentarzy. Ten blog ma około 5 tysięcy unikatów dziennie.

Serwer podaje dobre liczby w teście ab dla testowego bloga , ale ten sam test ze sklonowanym blogiem jest niemożliwy do zrobienia: test ab zbytnio ładuje serwer, a ja muszę przerwać proces, który i tak powoduje ab ten naprawdę słaby wynik .

Htop pokazuje również „normalne” obciążenie podczas normalnej pracy , ale nienormalnie duże obciążenie podczas testu ab.

Dzieje się jeszcze jedna dziwna rzecz (najważniejsza dla mnie): czas do pierwszego bajtu jest bardzo wysoki , ale po tym czasie strona ładuje się naprawdę szybko. Można to łatwo przetestować za pomocą usług takich jak tools.pingdom.com, co daje ten wynik . Proszę zwrócić uwagę na ten żółty region, który oznacza „Czas oczekiwania”.

Dlaczego to się dzieje? Możliwe pomysły:

  • Zła konfiguracja PHP-FPM
  • Czas odpowiedzi DNS na Linode jest okropny. Bzdury - blog testowy rozwiązuje problem DNS, TTFB jest fantastyczny
  • Zła konfiguracja Nginx

Jeśli ktoś potrzebuje więcej informacji,


Myślę, że może to mieć coś wspólnego z if -fdyrektywą, której używasz w locationkontenerze w konfiguracji nginx. Na podstawie tego, co czytam tutaj wiki.nginx.org/Pitfalls , mam wrażenie, że -frobi nieefektywne wyszukiwanie pliku, co może powodować problem z czasem do pierwszego bajtu, szczególnie jeśli masz katalogi z dużą liczbą akta.
d34dh0r53

1
Kilka myśli: a) jakie są różnice w stosunku do oryginalnego serwera, z którego sklonowany jest blog (np. Czy działa na tym samym stosie?) B) jeśli możesz, uruchom ab bezpośrednio z serwera, używając localhost i portu. Spróbuj uzyskać dostęp za pośrednictwem lakieru, a następnie uzyskać bezpośredni dostęp do nginx). c) Włącz powolne dzienniki MySQL i PHP-FPM. d) uruchom mysqltuner.pl i sprawdź, czy możesz poprawić swoją wydajność MySQL (byłaby to najbardziej oczywista różnica między blogami - lub wtyczkami). e) Wydana konfiguracja PHP-FPM nie wydaje się być tą używaną przez nginx (/var/run/php5-fpm-tpnet.sock! = /var/run/php5-fpm-www-data.sock)
cyberx86 15.01.12

1
Zdecydowanie problem z PHP. Wordpress jest naprawdę wolny. Będziesz potrzebować wtyczki buforującej, aby uzyskać przyzwoity czas ładowania, gdy masz tyle treści.
Martin Fjordvald,

2
Powiedziałeś, że „możesz uruchomić ab na localhost i uzyskać 4k req / s” - do którego localhost (poprzedni / bieżący) masz na myśli? Jeśli ta wartość pochodzi z twojego obecnego serwera - tego z wysokim TTFB - twój problem stał się o wiele bardziej interesujący - ponieważ skutecznie wyeliminowałeś PHP, MySQL i twój serwer WWW. TTFB obejmuje DNS, czas podróży w obie strony i czas przetwarzania. Długi TTFB jest zwykle spowodowany przetwarzaniem (np. PHP / MySQL). Punktem uruchomienia ab bezpośrednio przeciwko nginx jest wyeliminowanie innych komponentów. Ponadto, Lakier, jeśli poprawnie skonfigurowany, powinien ominąć backend, dając bardzo wysokie wymagania / s.
cyberx86

1
Twoje testy hosta lokalnego nie wydają się prawidłowe - nie odzyskałeś swojego bloga. Zwróć uwagę na różnicę wielkości strony: 7500 bajtów przy dostępie z domeny, 151 bajtów z hosta lokalnego. Ponieważ prawdopodobnie masz wiele wirtualnych hostów, musisz przekazać nagłówek hosta do ab. ab -n 1000 -c 100 -H 'Host: mysite.com' http://127.0.0.1/To powiedziawszy - różnica między wynikami w pamięci podręcznej (Varnish) a wynikami niebuforowanymi wystarcza do zweryfikowania pozycji, że problem nie jest związany z siecią, dns itp. I polega na przetwarzaniu, zgodnie z oczekiwaniami.
cyberx86 16.01.12

Odpowiedzi:


24

Po pierwsze, nie jest to odpowiedź, lecz podejście diagnostyczne.

Nie jest to bynajmniej wyczerpujące - ani nawet cokolwiek bliskiego, to tylko punkt wyjścia.

Czas na pierwszy bajt

Czas do pierwszego bajtu (TTFB) składa się z wielu elementów:

  • Wyszukiwanie DNS: znajdź adres IP domeny (możliwa poprawa: więcej / rozproszone / responsywne serwery DNS)
  • Czas połączenia: otwórz gniazdo do serwera, negocjuj połączenie (typowa wartość powinna wynosić około czasu pingowania - zwykle konieczna jest podróż w obie strony - utrzymywanie aktywności powinno pomóc w przypadku kolejnych żądań)
  • Oczekiwanie: konieczne jest wstępne przetworzenie przed wysłaniem pierwszego bajtu (to właśnie tam powinno być Twoje ulepszenie - będzie to najbardziej znaczące dla zawartości dynamicznej.

Gdy spojrzysz na wynik ApacheBench, zobaczysz również:

  • Przetwarzanie: Jest to suma oczekiwania + całkowity transfer zawartości (jeśli czas przesyłania jest znacznie dłuższy niż oczekiwany do pobrania ilości odebranych danych, następuje dalsze przetwarzanie (po otrzymaniu pierwszego bajtu) (np. Strona jest opróżnianie zawartości, gdy jest dostępna)

Porównania w celu wyeliminowania komponentów

Z nielicznymi wyjątkami, twój problem będzie polegał na przetwarzaniu backendu, co zwykle sprowadza się do zbyt skomplikowanego / nieefektywnego kodu lub źle skonfigurowanego MySQL.

Dobrym sposobem na rozwiązanie tego problemu jest seria porównań, które wyeliminują różne aspekty konfiguracji. Dobre porównanie powinno utrzymywać możliwie stałą wartość, aby pomóc zawęzić problem. Obecnie podałeś następujące porównania:

  1. Identyczna (sklonowana) witryna działająca na starym serwerze i nowym serwerze:
    • Różnica: serwer
    • Wynik: stary serwer jest szybki; nowy serwer jest wolny
    • Uwagi: Potrzebne jest tutaj określenie ilościowe różnic między tymi serwerami - zarówno pod względem stosu (Nginx itp.), Jak i sprzętu (czy stary serwer jest szybszy, ponieważ jest maszyną o większej mocy?)
    • Wniosek: kod może być w stanie szybko działać przy właściwej konfiguracji
  2. Strona testowa a pełna witryna na nowym serwerze
    • Różnica: treść, motywy, wtyczki itp
    • Wynik: strona testowa jest szybka, pełna strona działa wolno
    • Uwagi: teoretycznie test ten powinien pomóc Ci wyeliminować wiele aspektów konfiguracji - DNS, sieć, a nawet konfigurację nginx / php / mysql - jednak nie jest to całkiem „uczciwe”.
    • Wniosek: dodatkowa treść ma znaczący wpływ na wydajność

Idealny test polegałby na skopiowaniu całej witryny, a następnie usunięciu całej zawartości oprócz jednego artykułu i powiązanych komentarzy. Celem tego testu byłoby ostateczne ustalenie, czy problem stanowi duża ilość treści, czy przyczyną są inne aspekty konfiguracji (wtyczki WordPress, motyw itp.). Zasadniczo porównałbyś wydajność identycznych witryn na tym samym (nowym) serwerze - ładowanie tej samej strony (ta sama długość itp.) - jedyną różnicą jest całkowita zawartość witryny (np. Istnieje duża szansa, że ​​niektóre wtyczki nie dobrze skalować ze zwiększoną zawartością).

Nie zmieniając niczego, możesz wykonać kilka innych porównań:

  • Testuj z lokalizacji zdalnej w porównaniu z lokalną - pomoże to ustalić, czy przyczyną jest sieć, opóźnienie, dns itp
    • Już to (nieco) zrobiłeś i w większości doszedłeś do wniosku, że nie masz problemu z siecią.
  • Testuj przez Varnish (tj. Port 80) w porównaniu z nginx bezpośrednio (port 8080) - staraj się nie zmieniać konfiguracji między testami - po prostu użyj właściwego portu. To pokaże ci wpływ lakieru. Ponieważ Varnish jest warstwą buforującą, powinien bardzo szybko obsłużyć wszystkie żądania po pierwszym - zasadniczo powinien ominąć backend i przetwarzanie potrzebne do wygenerowania dynamicznej strony i bardzo szybko udostępnić buforowaną kopię.
    • Zrobiłeś to (chociaż nie lokalnie) i wykazałeś, że Lakier ma znaczący pozytywny wpływ na twoją wydajność.

Strojenie backendu

W tym momencie powinieneś znaleźć problem lub stwierdzić, że leży on w twoim backendie. To pozostawia Nginx, PHP lub MySQL.

(Należy tu wspomnieć, że jest ona zawsze pod ręką, aby wiedzieć, czy wąskim gardłem jest procesor, RAM, lub I / O - między sar, top, iostat, vmstat, free., Etc powinieneś być w stanie dojść do jakiegoś wniosku w tej sprawie)

Nginx

Nginx po prostu przyjmuje żądania i albo podaje statyczną zawartość, albo przesuwa żądania do PHP-FPM - zwykle nie ma wiele do optymalizacji z Nginx.

  • Ustaw pracowników = # rdzeni procesora
  • Włącz utrzymanie aktywności (wartość 10-15 jest dobra)
  • Wyłącz niepotrzebne rejestrowanie
  • W razie potrzeby zwiększ rozmiary buforów
  • Unikaj instrukcji if (w miarę możliwości używaj nazw statycznych zamiast wyrażeń regularnych, eliminuj niepotrzebne rozszerzenia)

Idealnie, twój blog testowy i sklonowany blog mają identyczne konfiguracje, w którym to przypadku skutecznie wyeliminowałeś Nginx jako problem.

Podanie

W przypadku, gdy próbujesz zidentyfikować problem w kodzie (na przykład powolną wtyczkę itp.), Powinieneś zacząć od powolnych logów.

  • Włącz powolny dziennik MySQL i powolny dziennik PHP-FPM uruchom swój test porównawczy i zobacz, co będzie wolno.

MySQL

  • Zwiększ pamięć podręczną i uruchom mysqltuner.pl, aby uzyskać dobry punkt wyjścia.

PHP

  • wyłącz niepotrzebne rozszerzenia,
  • wyłącz register_globals, magic_quotes_ *, expose_php, register_argc_argv, always_populate_raw_post_data
  • zwiększ limit pamięci
  • open_basedir i safe_mode mają znaczący wpływ na wydajność, ale mogą także zapewnić dodatkową warstwę obrony. Testuj z nimi i bez nich, aby ustalić, czy ich wpływ na wydajność jest dopuszczalny.

PHP-FPM

  • Dostosuj wartości pm. * - zwiększ je, aby poradzić sobie z dużym obciążeniem

Warto zauważyć, że wyniki htop pokazują php-fpm jako pochłaniające większość procesora - a twój problem wydaje się być bezpośrednio z tym związany.

Buforowanie

Po zoptymalizowaniu każdego prawdopodobnego wąskiego gardła rozpocznij buforowanie.

  • Masz już pamięć podręczną opCode (APC) - upewnij się, że działa (zawiera plik testowy) - sprawdź liczbę trafień w pamięci podręcznej i, jeśli to możliwe, umieść pamięć podręczną APC w pamięci zamiast na dysku.
  • Skonfiguruj swój kod do buforowania (np. Za pomocą wtyczki do Wordpress, takiej jak W3TC)
  • Dzięki nginx możesz ustawić buforowanie FastCGI - ale ponieważ masz Varnish, najlepiej tego uniknąć.
  • Skonfiguruj warstwę buforującą, taką jak Lakier (którą już zrobiłeś) - i upewnij się, że działa (np. Użyj lakieru, przeczytaj Osiągnięcie wysokiego Hitrate )
  • Dodaj więcej pamięci podręcznej dla komponentów witryny - np. MemCached, jeśli dotyczy

Czasami, biorąc pod uwagę ograniczenia twojej aplikacji i sprzętu, możesz nie być w stanie tak bardzo poprawić wydajności backendu - ale to jest sens buforowania - aby zminimalizować użycie backendu.

Dalsza lektura


2
To fantastyczne podsumowanie punktów do analizy. Dziękuję bardzo za komentarz, spróbuję przeprowadzić ciężki test z tymi wszystkimi sugestiami - niektóre z nich, jak już powiedziałeś, są już jasne - i zobaczę, czy w końcu mogę wykryć problem. Z pozdrowieniami, cyberx86.
javipas

O tym memory_limitzostało wskazane w innym poście , że nie pomaga w wydajności.
forloop
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.