Вопрос или проблема
У меня есть событие, отправляемое сервером, которое обрабатывает около 20-30 элементов в секунду. На клиенте у меня есть элемент прогресса и текст статуса, отображающийся в span, который обновляется для каждого обработанного элемента. В настоящее время он “задыхается”, обновляя текст два или три раза в секунду как в браузерах на базе Blink, так и Gecko. Я хотел бы сгладить это, увеличив FPS до более желательного значения, например, 10. Это всего лишь одно соединение с клиентом, поэтому я предполагаю, что это проблема с ограничением PHP на количество вызовов flush()
.
- Сжатие не используется.
- Очень маленькие ответы (обычно 80-500 байт).
- Тестирую Waterfox 128 и Vivaldi 6.5, так что это достаточно современные браузеры.
- Я читал документацию для
flush()
, и большинство комментариев датируются более чем десятилетней давностью. - Я попробовал рекомендацию из этого комментария, но никаких заметных улучшений не было.
Навскидку я не уверен, что еще можно сделать. Я предполагаю, что это, вероятно, проблема с ограничением PHP на количество вызовов flush()
в секунду, хотя, возможно, это связано с ограничениями браузера.
Как я могу улучшить способность либо PHP, либо браузера flush()
подключение более чем два-три раза в секунду?
.
Ответ или решение
Когда возникает задача увеличения частоты обновления данных в сервер-сент эвентах (SSE) с использованием PHP, ключевым аспектом является оптимизация скорости выполнения функции flush()
. Проблема, которую вы описываете — это необходимость повысить частоту обновления с 2-3 раз в секунду до более частого, например, 10 раз в секунду. Рассмотрим несколько шагов по улучшению производительности.
-
Оптимизация кода на стороне сервера:
- Убедитесь, что ваш PHP-код максимально оптимизирован. Если вы обрабатываете большое количество данных в цикле, возможно, стоит пересмотреть алгоритмы, чтобы минимизировать задержки на стороне сервера.
- Убедитесь, что все операции, которые могут задерживать выполнение (например, обращения к базе данных), оптимизированы.
-
Конфигурация сервера:
- Проверьте настройки Apache или Nginx. Убедитесь, что буферизация отключена или минимальна. Например, в конфигурации Apache убедитесь, что директива
OutputBuffering
отключена или установлена в небольшое значение. - Если используется Nginx, убедитесь, что директивы
proxy_buffering
иfastcgi_keep_conn
настроены корректно для работы с SSE.
- Проверьте настройки Apache или Nginx. Убедитесь, что буферизация отключена или минимальна. Например, в конфигурации Apache убедитесь, что директива
-
Настройка PHP:
- Посмотрите на директиву
output_buffering
вphp.ini
— она должна быть установлена в0
или быть отключена. - Используйте функции
ob_flush()
иflush()
вместе, чтобы убедиться, что данные проталкиваются из буфера PHP в веб-сервер.
- Посмотрите на директиву
-
Кэширование и сжатие:
- Хотя у вас сжатие не используется, удостоверьтесь, что оно не включено ни на каком уровне — например, на уровне сервера веб-страницы или в PHP.
-
Учет ограничений браузера:
- Современные браузеры, как Waterfox и Vivaldi, вполне должны справляться с высокой частотой обновлений через SSE. Однако, если у клиента есть ограничения, например, использование расширений, которые могут влиять на производительность, их стоит учитывать.
-
Альтернативные подходы:
- Рассмотрите использование других методов отправки данных, таких как WebSockets, если данные должны передаваться еще быстрее и более отзывчиво.
Включив оптимизацию на всех уровнях — от кода PHP до настроек сервера и учет возможных ограничений браузера — вы сможете увеличить частоту спусковых обновлений и улучшить общее восприятие прогресса на клиентской стороне.