Как оптимизировать производительность PHP?

Как оптимизировать производительность PHP?

@drbrain4web
Photo by Felix M. Dorn on Unsplash

Производительность приложения - не только техническая проблема. Именно производительность делает бизнес успешным или ведет к разорению. Поэтому, если Вы думаете что задержка в несколько миллисекунд не является проблемой, подумайте еще раз.

Почему так важна производительность?

Необходимость создания производительного приложения определяют три основных причины:

  1. Отношение пользователей,
  2. Конверсия,
  3. Масштабируемость.

Отношение пользователей

Чем дольше загружается приложение, тем выше риск того, что Ваш потенциальный клиент уйдет к более успешным конкурентам или оставит негативный отзыв, который не лучшим образом повлияет на развитие Вашего бизнеса.

Конверсия

Конверсию можно определить, например, как количество пользователей, которые совершили покупку или скачали электронную книгу с помощью Вашего приложения. В целом, это пользователи, оплатившие, предоставляемые Вами товары или услуги.

Масштабируемость

Чем больше запросов обрабатывает Ваше приложение за секунду, тем выше его пропускная способность. Например, приложение обрабатывает 1 запрос за 100 миллисекунд, что означает 10 запросов в секунду. Если Вы сможете уменьшить время обработки такого запроса вполовину, пропускная способность увеличится в 2 раза.

Примеры

Firefox: сокращение времени загрузки страницы на 2,2 секунды, позволило достигнуть более 10 миллионов скачиваний.

Shopzilla: ускорение загрузки сайта в среднем на 5 секунд привело к увеличению конверсии на 7-12%.

Bing: увеличение времени работы поисковой системы Microsoft на 1 секунду вызвало снижение доходов сервиса на 2,8%.

Yahoo!: так же как и Bing, замедление на 0,4 секунды привело к уменьшению трафика на 5-9%.

Выводы: каким бы бизнесом Вы не занимались, чем быстрее приложение, тем выше доход.

Как оптимизировать производительность?

Выбор версии

Это очевидный факт, особенно после выхода PHP7, который демонстрирует лучшую производительность в сравнении с предыдущими релизами. В данной статье я не буду делать подробное сравнение версий PHP, потому что этой теме уже посвящено множество статей и обсуждений. Достаточно посмотреть на нижеприведенную таблицу, сравнивающую производительность нескольких версий PHP для разных CMS:

Микрооптимизация

Микрооптимизация - это минорные изменения кода, ведущие к улучшению производительности приложения. Например, если вы используете цикл for, всегда лучше заранее знать его длину. Следующее изображение демонстрирует результат выполнения цикла for, содержащего 1000 однобайтовых значений. Ускорение очевидно:

Этот пример, далеко не все возможности микрооптимизации. Вы сможете лучше разобраться в этой теме с помощью ресурса phpbench.com

XHProf: профилирование PHP кода

После того как мы ознакомились с ограниченными возможностями микрооптимизации PHP, настало время точного обнаружения фрагмента кода, ведущего к снижению производительности, без необходимости угадывания, с помощью профилирующего приложения, которое называется XHProf. После установки и настройки на Вашем сервере (руководство по установке есть на youtube) XHProf добавит header и footer ко всем скриптам PHP и создаст отчет, в который будут внесены все выполненные функции, время их выполнения и количество вызовов каждой из них.

Следующее изображение - результат профилирования карточки товара, созданной с помощью фреймворка laravel. Из отчета видно, что getProductData() была вызвана 40 раз с общим временем выполнения более 5 секунд.

Итак, здесь можно ожидать проблему "N+1", исправление которой приведет к уменьшению времени загрузки карточки товара на 5 секунд.


Проблема "N+1" появляется, когда Вы обращаетесь к базе данных, чтобы получить информацию из двух разных таблиц. Например, Вы запрашиваете Name и Id для всех товаров, а затем обращаетесь к другой таблице, чтобы получить такие детали, как доступные цвета или остатки на складах для каждого полученного товара. Обычно, эта проблема решается изменением запроса, таким образом, чтобы необходимые данные можно было получить посредством одного (максимум двух) обращения к базе данных. Но это уже проблема оптимизации базы данных.

Кэширование

Использование кэширования должно влиять на частоту и время обращения к базе данных и уменьшать время вывода наиболее востребованных данных. Как Memcache, так и Redis широко используются для кэширования. Тем не менее Redis имеет некоторые конкурентные преимущества, такие как синхронизация данных в памяти и на диске, что позволяет сохранять информацию после перезагрузки сервера. Так же Redis имеет встроенную репликацию master/slave, поэтому масштабировать кластер Redis по мере роста приложения достаточно легко.

Report Page