Почему могут падать процессы phpб в режиме fast_cgi + apache-worker?
Есть ВПС сервер на базе Debian 8, на нем вертится apache-2.4.10 в режиме mpm-worker
для работы php использую mod_fcgi, без suexec.
PHP 5.6.29-0+deb8u1, без модулей кеширования.
настройки в целом ничего особенного:
FcgidIPCDir /var/run/mod_fcgid FcgidProcessTableFile /var/run/mod_fcgid/fcgid_shm FcgidMaxRequestLen 20000000 FcgidConnectTimeout 10 FcgidIdleTimeout 10 PHP_Fix_Pathinfo_Enable 1 FcgidMaxProcesses 200000
#!/bin/bash PHPRC=$PWD/../etc/php5 export PHPRC umask 022 export PHP_FCGI_CHILDREN export PHP_FCGI_MAX_REQUESTS=99999990 SCRIPT_FILENAME=$PATH_TRANSLATED export SCRIPT_FILENAME exec /usr/bin/php5-cgi
На сервере 32Гб оперативки + 8 ядер, на ssd дисках. Основной контент немного статики + легкие php скрипты, данные беруться и записываются в redis на том же сервере. На сервере порядка 30 доменов, все работают по одному принципу.
Странность в том, что периодически, по не выясненным причинам, на ходу начинает падать php, сначала идет несколько таких сообщений:
(104)Connection reset by peer: [client 1.1.1.1:29617] mod_fcgid: error reading data from FastCGI server [core:error] [pid 8840:tid 47795850016512] [client 1.1.1.1:29617] End of script output before headers: script.php
после чего происходит жесткое падение одного домена (самого нагржуеного)
mod_fcgid: can't apply process slot for /path/to/wrapper/php
При этом остальные домены работают без проблем, для каждого домена свой wrapper.
Лечится на время по разному, но вроде как помогает следующая комбинация
/etc/init.d/apache2 stop rm -f /var/run/mod_fcgid/* /etc/init.d/apache2 stop
В скрипт /etc/init.d/apache2 добавил ulimit -s unlimited
Вариант увеличить FcgidMaxProcesses не помогает, все равно периодами падает. Из симптомов еще
— Падает после перезапуска (добавлял домены на сервер — после активации и «reload» для apache2 происходила эта ситуация, так же после ротации логов и просто на ходу.
Есть подозрение что все это как то связано с тайматуами для FCGI и какими то еще лимитами, но не могу понять какими именно, похожий конфиг и с большей нагрузкой есть на другом сервере, но на нем трафика от 2 до 5 раз больше.
Подозреваю что то типа — когда апач рестртуется, релоадится или еще что то, остаются где то в системе подвисшие fcgi таблицы, когда апач стартует, он ожидает от этих таблиц (процессов или как их правильно назвать не знаю) ответа, данных или еще какой то активности, но ее не происходит, в итоге забиваются какие то лимиты и wrapper не может создать еще процессы для обработки запросов, в итоге апач валит 503 и все ложится.
Тут на сервере нагрузка в среднем 30-50 запросов в секунду.
Вариант ставить nginx+php-fpm не рассматриваю так как не вижу смысла, php-fpm не особо отличается от fcgi режима, думаю что при большой нагрузке могут быть похожие проблемы, а тестировать не хочу без серьезных аргументов.
Основная рекомендация в интернете повышать кол-во процессов для FcgidMaxProcesses, но толку нет, так же как и от PHP_FCGI_MAX_REQUESTS.
Так как все остальные домены работают, думаю причина в каких то настройках php, но не могу понять каких. Все домены работают от www-data.
Оценить 2 комментария
Вообще вот эта ошибка «End of script output before headers: script.php» похожа на то, что в скрипте выплевывается в вывод что-то, перед тем как выкидывается заголовки. Там с этим все в порядке?
Или же это наоборот — уже последствия отрубания php?
Максим: вывод до заголовков вряд ли, так как оно в целом работает работает, потом резко падает. После рестарта помогает. Подозреваю что проблема может и со скриптом быть, но на столько смертельная, логика там деревянная и сводится к тому что
1. Пришел запрос на aaa.com/str1.html
2. .hraccess реврфйтит такое обращение === str1.html => script.php
3. script.php делает запрос на тот же домен на aaa.com/123.html?param1¶m2¶m3 + задает заголовки отключающие кеширование.
4. .htaccess делает реврайт === 123.html?param1¶m2¶m3 => script2.php
5. script2.php выбирает данные из редиса и отдает клиенту
Про данную логику работы, не спрашивайте у меня, программист на данный момент менять ничего не будет. Не думаю что это основная проблема, но все же есть подозрение что данная логика работы стоит в цепи событий приводящих к проблеме.
Не проще будет переключить на mod_proxy_fcgi + php-fpm? Если использовать Proxy via Handler все реврайты будут работать. Для автоматического перезапуска php-fpm когда он внезапно упал можно использовать supervisord
а смысл? Какая разница между fcgi и fpm ? Поставил для эксперимента nginx+php-fpm, на высокой нагрузке эта связка очень быстро треснула (сначала лег php-fpm в режиме unix socket, поставил его локал на 9000 порт, то же лег c (104: Connection reset by peer) while reading response header from upstream) — тюнинг не помог, а оттачивать не было ни желания ни времени (нагрузка 10% от ожидаемой была ~50 запросов в секунду), вернул назад на fcgi + apache2-worker. Пока все еще в поисках логического обьяснения почему периодавми падает от нехватки слотов.
Dmitry: проще тюнить и смотреть что произошло. Если у вас при высокой нагрузке падает php-fpm то нужно оптимизировать скрипты плюс включить кеширование. Хотя думаю кеширование на php включено. Проблема в том что fcgi модуль который вы используете, сам запускает php-fpm и это происходит довольно бесконтрольно. Так-как запуском и установкой управляет apache.
Анатолий Шипицын: Я разницы не вижу особой между fpm и fcgi, так как по сути это одно и то же, различие лишь в том, что fpm работает как отдельный процесс, а fcgi запускается apache через mod_fcgi. Кеширование отключил так как с opcache fpm вылетел оч быстро, сейчас без кеширования работает. Ошибки что в fcgi что в fpm модуле связаны с большим кол-вом запросов и нехваткой обработчиков (я так думаю) по сути найдя какой именно параметр нужно регулировать, проблема решится в обоих режимах, на выходных буду пробовать увеличивать для fpm кол-во процессов, как и для fcgi, ну и логику 100% нужно менять, так как сервер должен обрабатывать запрос, а не перебрасывать его несколько разу туда — сюда, при этом после каждого переброса инициируется обработчик в php и потомок в apache. Еще думаю что проблема может быть связана с настройками самой ОС, так как под каждое поделючение и обработку запроса происходит создание процессов, дескрипторов, выделение ресурсов и прочие процессы, возможно тут еще нужно через sysctl какие то параметры регулировать. На счет безконтрольного запуска fcgi — не согласен, так как запуск происходит тогда — когда идет запрос на .php файл, апач через fcgi модуль обращается к php-wrapper и передает ему запрос, запуск на обработку враппера — имхо тяжелая задача, так как это происходит запуск процесса (процесс это всегда тяжело, хотя бы гялнуть на apache-prefork), а завершается процесс после обработки запроса и возвращение ответа родителю — то есть apache. Если даже процесс по какой то причине подвиснет, потеряет связь с родителем и пр. для этого в mod_fcgi есть параметры которые задают через сколько прибить подвисший процесс, по сути так же как и с fpm. То есть процесс запуска как мне кажется совсем не хаотичных и не безконтрольный. В целом fpm режим работает по тому же принципу, разница в наличии tcp-socket в который веб-сервер передает запрос от клиента. Данный сокет принимает запрос, на обработку передает php процессору, который после обработки запроса передает ответ назад веб-серверу, обработка запроса по сути то же генерация процесса со всеми накладными расходами системных ресурсов. В целом да — буду дальше смотреть на подкручивание пармтеров пхп, системы. Возможно стоит вспомнить институтский курс С и разобрать модуль fcgi 🙂
Если у вас fpm вылетает очень быстро с opcache это говорит что вы выделили php слишком много ресурсов одних ресурсов при недостаче других. У вас много процессора и мало памяти. Отключением opcache вы снижаете быстродействие ПО и раз при этом работает, то это говорит, что ваши лимиты сильно больше того что может прожевать сервер и вы упираетесь в память. Нельзя бездумно увеличивать количество процессов. Использование fpm как раз позволяет избегать такой ситуации и контролировать ее. Так что вам бы я посоветовал уменьшить количество процессов в двое и при помощи бинарного поиска найти оптимальное их число. Насчет же fcgi разница есть. Фишка в том что в случае php-fpm у вас запуск процесса происходит ОДИН раз. При запуске php-fpm. В случае mod_fcgi и аналогах если нет запросов происходит прибивание процесса php и при новом обращениии идет запуск. Никогда не забывайте что современные процессоры имеют большую пропускную способность чем память и сильно большую пропускную способность чем система ввода-вывода. Я помнится один раз уже правил систему после такого бездумного увеличения. В итоге после того как был найден баланс между количеством процессов и возможностью системы она начала работать заметно быстрее.
Анатолий Шипицын: нет нет, отключение opcache прошло после падения fpm, сейчас уже не вспомню но поиск инфы в интенете показал что обшибка как раз таки с кешированием связана. После отключения — какое то время поработало и опять упало, но дело не в ресурсах, на сервер стоит мониторинг и если был перегруз по ресурсам это было бы видно, но это не было видно и собственно не было. Опять же из личного опыта — если я поставлю огромный размер кеша для mysql — а кеш на диске ( не в памяти) в итоге тормоза — так как идет повышенная нагрузка на диски. то же и с php, проблема не в кеше или слишком больших параметрах ( в моем случае ), так как если бы это касалось их — было бы видно просадка ресурсов в мониторинге, а этого нет (утилизация процессора, нехватка памяти, высокий IO). По поводу FPM и что что запускается один раз ? Один раз запускается главный процесс, который в свою очередь по мере надобности открывает новые обработчики запросов (процессы, потоки), кол-во которых обусловлено параметрами php-fpm, а значит разницы по сути нет, запускает обработчики apache или fpm, дальше сценарий аналогичный — материнский процесс открывает что то — что обработает запрос и выдаст ответ. Запустите php-fpm в режиме tcp-socket. натравите на него живой траф черз nginx или apache, посмотрите на поведение и увидите что разницы нет, а рассказы про скорость работы — холивар между fpm и fcgi чистой воды (имхо). Соглашусь с вами про бездумное увеличение параметров, на данный момент анализа понял, что есть еще в fcgi + apache зависимость от таймаутов дефолтных и из конфига, но до конца еще не проникся, не набрал критическую массу того — как все работает на низком уровне. Опять же про нагрузку и бездумное использование ресурсов из опыта — поставив параметр PHP_FCGI_MAX_REQUESTS = 99999 в php-wrapper — сервер сразу умер, так как не мог создать ни одного форка и это сразу стало заметно по всем мониторилкам 🙂 и помог ребут сервера, благо апач не стартовал в автомате.
Баланс ресурсов — согласен, но он не может быть ниже чем на аналогичном сервере с аналогичным конфигом, а разница в логике работы и коде (сейчас грешу еще на код, но хочется и говнокод заставить работать, без падений процессов и сервисов, не знаю получится ли), сейчас все же мне удалось заставить клиента и его разработчиков переделать систему на отдачу статики которая генерится динамикой по определнному алгоритму и это работает, на данный момент нагрузка пока не большая, в пике около 50 запросов в секунду, но это статика и все летает, а причину падения все еще ищу.
Постоянно падает php-fpm приходится делать рестарт
Проблема такая: с недавнего времени по нескольку раз в день начал падать php-fpm, приходится делать /etc/init.d/php5-fpm stop /etc/init.d/php5-fpm stop, иначе ни один сайт на сервере не работает. Сервер работает уже полгода и раньше такого не происходило. В логах php-fpm такое:
[09-Aug-2012 04:07:27] WARNING: [pool www] child 12043 exited on signal 11 (SIGSEGV) after 35.646667 seconds from start[09-Aug-2012 04:07:27] NOTICE: [pool www] child 12063 started
[09-Aug-2012 04:32:46] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[09-Aug-2012 06:26:23] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[09-Aug-2012 08:17:44] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[09-Aug-2012 08:51:59] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[09-Aug-2012 09:04:46] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[09-Aug-2012 09:17:01] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[09-Aug-2012 09:19:55] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[09-Aug-2012 09:48:37] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[09-Aug-2012 10:23:50] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it