Событие Apache 2.4 MPM + php-fpm + php-opcache приводит к ошибкам "Сброс соединения по пиру"
У меня есть сервер CentOS 7 под управлением Apache 2.4.6 с Event MPM и php-fpm версии 5.6.10 (из репозитория REMI). Вот соответствующая конфигурация Apache для отправки запросов php-fpm в vhost (это единственный сайт на этом сервере):
<FilesMatch \.php$>
SetHandler "proxy:unix:/var/run/php-fpm/www.sock|fcgi://localhost"
</FilesMatch>
Вот соответствующий пул php-fpm:
listen = /var/run/php-fpm/www.sock
listen.owner = apache
listen.group = apache
pm = static
pm.max_children = 50
pm.max_requests = 0
Вот конфигурация php-opcache (конфигурация установки по умолчанию):
zend_extension=opcache.so
opcache.enable=1
opcache.memory_consumption=128
opcache.max_accelerated_files=4000
opcache.blacklist_filename=/etc/php.d/opcache*.blacklist
Моя проблема: всякий раз, когда я устанавливаю и включаю php-opcache, в моем журнале ошибок начинают появляться следующие ошибки:
[Thu Jun 18 08:10:58.499871 2015] [mpm_event:debug] [pid 16546:tid 139798115227392] event.c(986): (104)Connection reset by peer: [client 157.55.39.233:15962] AH00470: network write failure in core output filter
[Thu Jun 18 08:10:58.527424 2015] [mpm_event:debug] [pid 16546:tid 139797922195200] event.c(986): (103)Software caused connection abort: [client 157.55.39.233:15990] AH00470: network write failure in core output filter
Если я удалю php-opcache, ошибки прекратятся. Пользователи сообщают об ошибке 502 Service Unavailable на веб-интерфейсе всякий раз, когда это происходит.
Я буквально потратил как минимум 6 часов, пытаясь найти Google и найти решения. Кто-то сказал, что Opcache fastshutdown
Опция была проблемой, но она отключена в конфигурации по умолчанию. Я изменил метод управления процессом php-fpm на статический без повторного использования (max_requests=0), но это тоже ничего не изменило. Я также пытался использовать метод прокси TCP с Apache (вместо сокетов), и это также не имело никакого эффекта.
Я не уверен, является ли это актуальным или нет, но независимо от того, установлен php-opcache или нет, я получаю следующие ошибки в журнале ошибок (но с гораздо меньшей частотой, <0,5% от всего трафика, который может отдельная тема)
[Thu Jun 18 08:32:37.223430 2015] [proxy_fcgi:error] [pid 19187:tid 140598765840128] [client 37.46.115.238:55624] AH01068: Got bogus version 10, referer: ...
[Thu Jun 18 08:32:37.223462 2015] [proxy_fcgi:error] [pid 19187:tid 140598765840128] (22)Invalid argument: [client 37.46.115.238:55624] AH01075: Error dispatching request to :, referer: ...
Эта проблема очень похожа на эту, хотя этот человек использует ProxyPassMatch с методом TCP, который я не использую (потому что обходит.htaccess).
У кого-нибудь есть идеи, которые я еще не упомянул?
1 ответ
Когда я встречал подобные проблемы в наших средах, это происходило из-за того, что OpCache (по умолчанию) совместно использует один кэш для всех пользователей в среде общего хостинга. Была отправлена ошибка (и вы можете, и должны, пойти и проголосовать, чтобы сообщить сопровождающим, насколько это может быть важно для вашего варианта использования), хотя никаких обязательств по доставке исправления не было.
TL; DR: по умолчанию, когда включен OpCache, кеш, который используется для хранения скомпилированного байт-кода, используется всеми пользователями. В среде, где хостинг распределяется между несколькими сайтами / пользователями, это может привести к тому, что сайт получит кэшированный вывод сценариев php с другого сайта или, если определенные параметры безопасности включены, даже генерирует ошибки.
Если вы планируете использовать PHP-FPM со встроенным opcache в PHP 5.5+, пожалуйста, прочитайте блог ниже, прежде чем вы действительно это сделаете. Оказывается, что кэш кода операции может быть прочитан любым пользователем на сервере. Это означает, что если, скажем, есть 10 отдельных пользователей со своими собственными vhosts и каталогами, и вы настраиваете один пул PHP-FPM на пользователя, каждый пользователь по-прежнему может видеть, какие сценарии кэшируются и их местоположения. Так как у них есть доступ на чтение к кешу, они потенциально могут просматривать все эти данные.
Это, очевидно, серьезная проблема безопасности, и даже если никто не воспользуется этим, все равно есть вероятность, что скрипты будут прочитаны не тем пользователем при создании страницы, поэтому веб-сайты могут отображать неверные данные / информацию, если существует несколько индексов. Скрипты.php в кеше.
Хотя официально не было выпущено ни одного исправления, если вы используете cPanel, в этой вики есть документированный способ настройки пулов php-fpm, которые будут создаваться и защищаться для каждого пользователя, и если вы будете следовать приведенным ниже инструкциям, а также ВАЖНЫЕ ЗАМЕЧАНИЯ В нижней части этого ответа вы сможете без проблем получить желаемую функциональность
В этом посте также документируется, как вы можете настроить это вручную для каждого сайта / для каждого пользователя (хотя я бы поспорил, что это может стать утомительным, если вы размещаете много сайтов). Если вы не используете cPanel, вам может потребоваться изменить сценарии, чтобы указать ваши индивидуальные пути и имена пользователей вместо переменных, используемых механизмом конфигурации cPanel.
ВАЖНЫЕ ЗАМЕТКИ
Во время тестирования и дополнительных исследований я наткнулся на эту статью, в которой приведены некоторые пояснения, которые могут иметь отношение к вашей конкретной ситуации:
- Вы должны убедиться, что
opcache.use_cwd
параметр установлен вtrue
для конфигурации вашего приложения OpCache - он установлен вfalse
по умолчанию, если оставить значение по умолчанию, это может вызвать конфликты, если в вашей системе размещено более одного приложения PHP:
Прежде всего, вероятно, в каждом типичном проекте вам нужно убедиться, что для опции opcache.use_cwd установлено значение true. Включение этого параметра означает, что механизм OpCache будет просматривать полные пути к файлам, чтобы различать файлы с одинаковыми именами. Установка его в false приведет к конфликтам между файлами с одинаковым базовым именем.
- Если вы работаете с приложением, основанным на Zend Framework или другой подобной платформе, которая использует аннотации, вы также должны убедиться, что
opcache.load_comments
а такжеopcache.save_comments
директивы установлены вtrue
, Вам следует дважды проверить это предложение в документации по вашему приложению / фреймворку, поскольку большинство из них уже обновили свои документы с конкретными инструкциями по правильному использованию OpCache для своих систем:
Существует также параметр, который важен в инструментах и средах, которые используют аннотации. Если вы используете Doctrine, Zend Framework 2 или PHP Unit, не забудьте установить для параметров opcache.load_comments и opcache.save_comments значение true. В результате комментарии документации к вашим файлам также будут включены в предварительно скомпилированный код, сгенерированный OpCache. Этот параметр позволит вам работать с аннотациями без сбоев.
Если ваш проект основан на конкретной платформе или веб-приложении, всегда полезно проверить документацию на предмет каких-либо рекомендаций, касающихся конфигурации OpCache.
ВАЖНЫЕ ЗАМЕТКИ
Надеюсь, это помогло - и если вы используете cPanel, оставьте комментарий, чтобы сообщить нам, как вы справились с этой частью конфигурации! Смотрите также этот вопрос и соответствующие комментарии.