Puncte:0

Creștere neașteptată de la PHP5 la PHP7 a utilizării memoriei în interiorul containerului

drapel ug

Săptămâna trecută am actualizat mai multe site-uri wordpress care rulează Alpine Linux ca containere într-o gazdă (Ubuntu 20.04) prin LXD.

Un rezumat al actualizării este următorul:

Alpine Linux v3.8 -> 3.14
PHP 5.3.6 -> 7.4.24
Wordpress 5.0.3 -> 5.7.3

Problemă

Am început să avem probleme cu performanța serverului după acele actualizări și am descoperit că containerele actualizate foloseau de 3 ori sau mai multă memorie (memorie rezidentă) decât cele mai vechi (aproximativ 150MB vs 50MB), ceea ce a făcut ca serverul să înceapă să schimbe mai des.

În versiunile mai vechi (folosind PHP 5.3), memoria folosită de php (procesul) crește pe măsură ce pagina este procesată (așa cum era de așteptat), dar imediat după ce se termină, revine la normal. Cu alte cuvinte, ceva de genul: 10 MB ---> 95 MB ---> 10 MB.

În containerele actualizate, memoria utilizată de php crește în același mod, dar nu revine la „normal”: 10 MB ---> 95 MB ---> 95 MB. Și de fiecare dată când este utilizat un nou proces, se întâmplă același lucru, crescând utilizarea memoriei cu numărul de procese copii disponibile (care în acest caz sunt 4 pe site).

Ce am incercat

  • Trecerea versiunii PHP până la 7.2.x și 7.3.x : același lucru
  • Actualizat la php 8.0.11 : aceeași problemă
  • Folosind apache2 în loc de lighttpd (în prezent php rulează ca fcgi): același comportament
  • Actualizați doar Alpine și PHP pentru a identifica dacă Wordpress poate fi cauza: wordpress nu este cauza
  • Rularea wordpress fără pluginuri (pentru a ști dacă un plugin poate cauza o problemă): nicio schimbare
  • A executat o buclă simplă de concatenare (php pur): același lucru
  • Testat pe un alt server cu un alt site wordpress: același comportament

Care este motivul pentru care nu își recuperează memoria? Cum se poate repara?

Actualizați

  • Am configurat o curățare Alpin 3.14 container și a efectuat testul „buclă simplă”. În acest caz, memoria rezidentă a fost redusă conform așteptărilor. Cu toate acestea, odată ce am testat cu un site wordpress real, problema a persistat.
  • Am configurat o curățare Ubuntu 20.04 container și a făcut aceleași teste. Rezultatul a fost același ca cu curățarea Alpin 3.14.
drapel lr
Duplicat: https://stackoverflow.com/questions/39740398/i-am-facing-more-memory-consumption-in-php-7-compare-to-php-5-6
lepe avatar
drapel ug
@BarnabasBusa îmi pare rău, nu cred că are legătură cu problema mea. Când testați cu un script PHP simplu (concatenarea șirurilor cu o buclă), de fapt, PHP7 ia mai puțină memorie la pornire și la rularea testului simplu. Problema este că nu recuperează memoria după utilizare. De asemenea, bănuiesc că ar putea fi legat de un fel de cache (deoarece opcache-ul este activat implicit în PHP7), dar modulul opcache nici măcar nu este instalat și am încercat să-l dezactivez și în setări.
lepe avatar
drapel ug
Raport de eroare: https://bugs.php.net/bug.php?id=81536 și înrudit: https://bugs.php.net/bug.php?id=80108
Puncte:0
drapel ug

Conform acest raport de eroare nu este cu adevărat un bug, ci o caracteristică în PHP7+ sub Gestionarea memoriei motorului Zend:

[email protected] : Acesta este comportamentul așteptat. La cerere, închiderea Zend Managerul de memorie nu eliberează toate bucățile alocate, ci mai degrabă le păstrează unele[1] pentru a evita necesitatea realocării lor eventual pentru următoarea cerere.

Soluția sugerată este să sunați la: gc_mem_caches(). Poți să folosești auto_prepend_file și auto_append_file directive în php.ini să-l execute întotdeauna dacă este necesar.

Cu toate acestea, acea soluție nu a ajutat în situația mea, așa că nu este o garanție că va funcționa.

Deoarece nu există o modalitate ușoară de a schimba acest comportament în acest moment, am găsit o altă modalitate de a rezolva problema memoriei (ar trebui să funcționeze pentru PHP7,PHP8):

  1. În loc de a folosi php-cgi, utilizare php-fpm
  2. Configurați configurația FPM pentru a utiliza cel mai mic număr de procese copii, dar lăsați-l să creeze copii dacă este necesar, pentru aceasta, puteți fie să utilizați la cerere modul sau dinamic:

/etc/php7/php-fpm.d/www.conf :

pm = la cerere
; Ajustați după cum este necesar:
pm.max_children = 10

sau:

pm = dinamic
; Ajustați după cum este necesar:
pm.max_children = 10
pm.start_servers = 1
pm.min_spare_servers = 1
pm.max_spare_servers = 1

Principala diferență dintre ele este că la cerere va folosi mai puțină memorie când este inactiv, dar va fi mai lent când un client se conectează.

Aceasta este o comparație a rezultatelor mele:

PHP Modul Copii Max Inactiv Mem. Max Mem. Timp de încărcare Timp maxim*
PHP5 CGI 4 4 50 MB 200 MB 5s 15s
PHP7 CGI 4 4 200 MB 200 MB 5s 30 de ani
PHP7 FPM / la cerere 0 10 15 MB 500 MB 7s 10s
PHP7 FPM / dinamic 1 10 25 MB 500 MB 6s 10s
  • Timpul maxim de încărcare este testat rulând 50 de clienți simultan

Valorile din tabel sunt aproximative și doar în scop ilustrativ (nu sunt în niciun fel un punct de referință real).

Postează un răspuns

Majoritatea oamenilor nu înțeleg că a pune multe întrebări deblochează învățarea și îmbunătățește legătura interpersonală. În studiile lui Alison, de exemplu, deși oamenii își puteau aminti cu exactitate câte întrebări au fost puse în conversațiile lor, ei nu au intuit legătura dintre întrebări și apreciere. În patru studii, în care participanții au fost implicați în conversații ei înșiși sau au citit transcrieri ale conversațiilor altora, oamenii au avut tendința să nu realizeze că întrebarea ar influența – sau ar fi influențat – nivelul de prietenie dintre conversatori.