У нас есть сервер, на котором работает сайт WordPress со стеком nginx, установленным serverpilot, на Ubuntu 20 LTS.
Кажется, что очень большие загрузки застревают в передаче между прокси-сервером nginx и PHP, и я пришел к концу того, что знаю, как устранять неполадки, не просто тыкая в них, чтобы посмотреть, что происходит (что редко является хорошим использованием времени или способ двигаться вперед). Насколько я могу судить, я увеличил необходимые тайм-ауты и увеличил все дисковые лимиты, но, очевидно, я все еще что-то упускаю.
Для нашего варианта использования нам нужно разрешить загрузку до 50 ГБ, что у нас работает без проблем в тестовой среде, в которой работает стандартный стек LAMP. У нас нет проблем с файлами меньше ~ 2 ГБ, но все, что больше, может или не может выйти из строя на основе некоторых критериев, которые я не смог отследить. При устранении проблемы в более раннее время время остановки копирования файла казалось произвольным (с успехом до 10 ГБ), но с текущей конфигурацией (см. ниже) оно постоянно останавливается, когда PHP температура
файл достигает 2 ГБ.
Когда мы загружаем очень большие файлы, мы можем наблюдать, как входящий временный файл занимает место на диске до тех пор, пока весь файл не появится в памяти. /mnt/tmp/[nginx_tmp_path]
(да, свободного места на диске предостаточно). После этого мы видим, что файл копируется в php температура
путь, но через несколько секунд файл php температура
файл перестает увеличиваться в размере, и процесс копирования зависает. В конце концов, достигается один из 600-секундных тайм-аутов, и регистрируются ошибки (см. ниже). На этом снимке экрана у нас есть завершенная (с точки зрения браузера/конечного пользователя) загрузка 14,8 ГБ, которая зависла при передаче файла tmp примерно на 2 ГБ.
В конце 600-секундного периода в журнале ошибок Apache появляется следующее:
(70008) Частичные результаты действительны, но обработка не завершена: [client <MY_IP>] AH01075: Ошибка отправки запроса на: (чтение входной бригады), реферер: https://<THE_URL>/wp-admin/media-new.php
И журнал ошибок nginx сказал следующее:
2512066#0: *9 истекло время ожидания восходящего потока (110: время ожидания соединения истекло) при отправке запроса восходящему потоку, клиент: <MY_IP>, сервер: <INTERNAL_IP>, запрос: "POST /wp-admin/async-upload.php HTTP/ 2.0", исходящий: "http://127.0.0.1:81/wp-admin/async-upload.php", хост: "<THE_URL>", реферер: "https://<THE_URL>/wp-admin/ медиа-new.php"
Важно отметить, что эти сообщения не появляются в файле журнала до тех пор, пока не пройдет 10 минут после того, как загрузка полностью поступит на сервер, то есть через 9 минут или более после того, как копирование файла окажется приостановленным/зависшим. Я убежден, что что-то вызывает зависание копии файла, а затем, в конце концов, достигается тайм-аут - я не верю, что проблема связана с самим тайм-аутом. В промежутке между остановкой копирования файла и появлением в файле журнала ошибки тайм-аута на сервере нет повышенной или необычной активности, и все службы функционируют и реагируют должным образом.
В текущей конфигурации PHP температура
файл всегда увеличивается до 2097152 КБ (согласно ду -а
), что заставляет меня поверить, что я достиг встроенного ограничения размера файла, которое я еще не обнаружил.
Соответствующие параметры конфигурации сервера nginx:
в сервер
контекст:
proxy_connect_timeout 600;
proxy_read_timeout 600;
proxy_send_timeout 600;
proxy_max_temp_file_size 51200 м;
fastcgi_connect_timeout 600;
fastcgi_read_timeout 600;
fastcgi_send_timeout 600;
fastcgi_request_buffering выключен;
keepalive_timeout 600;
send_timeout 600;
client_max_body_size 0;
client_body_temp_path /mnt/tmp;
client_body_in_file_only чистый;
Конфигурация Apache VirtualHost:
Заголовок RequestReadTimeout = 0, тело = 0
Таймаут 3600
Прокситаймаут 3600
И, наконец, конфигурация PHP:
memory_limit = -1
максимальное_время_исполнения = 0
max_input_time = -1
post_max_size = 50G
upload_max_filesize = 50G
default_socket_timeout = -1
Я в недоумении относительно того, что может быть причиной симптома, который я вижу.Любые указатели приветствуются!
Дополнительные примечания: Симптомы заставляют меня чувствовать, что это не имеет значения, но если это так... Сайт работает через WP Rocket, но нет внешнего прокси-сервиса, такого как CloudFlare.
ОБНОВИТЬ: я добавил эти строки в конфиг nginx:
прокси_http_версия 1.1;
proxy_set_header Соединение "";
Это немного изменило симптом, но не решило проблему. С этим изменением поведение вернулось к тому, что я объяснял ранее, и передача файлов останавливается в непредсказуемом месте. Первый пример ниже остановился на 3823176 КБ, а второй остановился на 3264364 КБ. Причина разницы в поведении мне непонятна, но стоит сообщить.
ОБНОВЛЕНИЕ 2: я смог окончательно связать это с проблемой передачи температура
файл между nginx и php, но я не могу определить конкретную вещь, которая вызывает зависание процесса.
Мы можем пропустить прокси nginx и использовать только PHP температура
добавив эти строки в конфиг nginx:
прокси_буферизация выключена;
proxy_request_buffering выключен;
В этой конфигурации файлы попадают непосредственно в /mnt/tmp/php<RND_STR>
и когда загрузка завершена, наше приложение правильно выбирает файл из температура
и выполняет свои задачи.
Однако это замедляет загрузку примерно до 1/3 доступной пропускной способности, поэтому это не очень хорошее решение. Однако это доказывает, что это не проблема приложения.
Итак, вот что происходит:
- Пользователь загружает большой файл (максимум 50 ГБ)
- Файл приходит в nginx
температура
локация целиком
- Делается попытка скопировать файл из nginx
температура
в PHP температура
- процесс копирования остановится в течение нескольких секунд где-то непредсказуемо, но между 3ГБ и 10ГБ. [3b] В настоящее время мы можем видеть оба температура
файлы и PHP температура
файл содержит количество байтов, которое должно увеличиваться, пока не сравняется с размером файла nginx. температура
файл, но это не так.Оба файла будут оставаться как есть до тех пор, пока не будет достигнут один из 600-секундных тайм-аутов (см. выше), затем в файлах журнала появится ошибка, и оба температура
файлы исчезают. [3c] Если размер файла менее 3 ГБ, он будет работать каждый раз. Если файл больше 3 Гб, то иногда он будет работать, а иногда нет - чем меньше файл, тем больше шансов, что он сработает.
- Обход nginx
температура
работает полностью, как и ожидалось, за исключением того, что загрузка медленная.
Что-то определенно зависает во время температура
передача файлов между nginx и PHP, когда файлы ужасно огромные, и я хотел бы выяснить, что это такое.