Laravel с Octane: Быстрее, Чем Когда-либо

Команда Laravel объявила о выпуске Laravel Octane в 2021 году, целью которого является повышение скорости и производительности приложений Laravel за счет сокращения времени запроса/ответа за счет кэширования экземпляра контейнера зависимостей Laravel в оперативной памяти. Этот процесс выполняется с помощью инструментов Swoole и RoadRunner.

В этом посте мы представим краткое руководство по оптимизации ваших приложений Laravel с помощью Octane, принимая во внимание анализ производительности, чтобы продемонстрировать различия в производительности между RoadRunner, Swoole и Nginx.

Объяснение инструментов

  • Swoole : Swoole — это расширение PHP, которое помогает использовать низкоуровневые или традиционные модели без сохранения состояния, такие как циклы событий и асинхронность, для повышения производительности PHP. Swoole имеет тенденцию быть популярным из-за того, что это расширение PHP по сравнению с roadrunner, созданным на Go.
  • RoadRunner : RoadRunner — это высокопроизводительный PHP-сервер приложений, балансировщик нагрузки и диспетчер процессов, написанный на Go — это двоичное приложение, которое необходимо установить перед использованием.
  • AutoCannon : AutoCannon — это инструмент для сравнительного анализа HTTP, написанный на Node.js. Он используется для оценки производительности веб-приложений.

Почему Laravel Octane?

Laravel Octane — это пакет, который обслуживает приложения Laravel с помощью Swoole или RoadRunner, помогая повысить производительность.

Обычные приложения Laravel обслуживаются с таких веб-серверов, как Apache, Nginx и Lighttpd, которые при каждом запросе порождают исполнитель PHP-FPM. Этот подход приводит к дополнительным затратам на создание процессов и загрузку приложений Laravel при каждом запросе, что называется подходом без сохранения состояния, поскольку ни один из процессов PHP не используется повторно при каждом запросе.

Хотя Swoole и RoadRunner по-прежнему используют рабочие процессы для всех запросов, они обслуживают только первый запрос на загрузку платформы (контейнеры зависимостей), а все остальные — из загрузочной версии платформы.

Плюсы Octane

  • Это повышает производительность ваших приложений Laravel.
  • Он экономит ресурсы по сравнению с обычными приложениями Laravel.

Проблемы Octane

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

Настройка приложения Laravel Octane

Теперь, когда мы подробно рассмотрели, что включает в себя Octane и что он делает, давайте начнем применять его на практике.

Вот как начать:

composer create-project laravel/laravel laravel-octane
composer require laravel/octane
php artisan octane:install

 Which application server you would like to use?:
  [0] roadrunner
  [1] swoole
 > 0

Установка серверов приложений

RoadRunner или Swoole необходимы для обслуживания вашего приложения, поскольку оба они являются внешними пакетами, но в большинстве случаев RoadRunner будет установлен после выбора сервера приложений. Если это не так, используйте команду ниже, чтобы установить ее вручную:

composer require spiral/roadrunner

Установка Swoole может немного отличаться, поскольку это расширение PHP, а не пакет, и требует нескольких процедур. Следующая команда используется для его установки и начала процедур установки:

pecl install swoole

Запустите приложение с помощью следующей команды, затем перейдите в браузер.

 php artisan octane:start

   INFO  Server running…

  Local: http://127.0.0.1:8000

Вы также можете указать, какую технологию/сервер использовать и сколько потоков запускать в зависимости от потоков ЦП вашей среды, как показано ниже.

php artisan Octane:start --workers=4 --server=roadrunner

Бенчмаркинг серверов приложений с помощью AutoCannon

Проект, использованный в этом посте, представляет собой простую страницу с небольшим количеством заполненных данных. Мы будем менять сервер приложений (RoadRunner, Swoole и Nginx) на каждом этапе теста, чтобы оценить и сравнить производительность каждого сервера с помощью AutoCannon.

Этот процесс поможет вам принять решение о том, какой сервер приложений наиболее подходит для вашего проекта.

AutoCannon способен генерировать большой объем трафика даже при работе на одном многоядерном процессоре; мы будем запускать тест в течение 10 секунд со 100 одновременными соединениями, 10 конвейерными соединениями и 3 рабочими потоками для обработки запросов.

Swoole

❯ autocannon http://127.0.0.1:8000 -d 10 -w 3 -c 100 -p 10
Running 10s test @ http://127.0.0.1:8000
100 connections with 10 pipelining factor
3 workers

/
┌─────────┬────────┬─────────┬─────────┬─────────┬────────────┬───────────┬─────────┐
│ Stat    │ 2.5%   │ 50%     │ 97.5%   │ 99%     │ Avg        │ Stdev     │ Max     │
├─────────┼────────┼─────────┼─────────┼─────────┼────────────┼───────────┼─────────┤
│ Latency │ 201 ms │ 1773 ms │ 3175 ms │ 3304 ms │ 1854.07 ms │ 657.15 ms │ 4201 ms │
└─────────┴────────┴─────────┴─────────┴─────────┴────────────┴───────────┴─────────┘
┌───────────┬─────┬──────┬─────────┬─────────┬─────────┬─────────┬─────────┐
│ Stat      │ 1%  │ 2.5% │ 50%     │ 97.5%   │ Avg     │ Stdev   │ Min     │
├───────────┼─────┼──────┼─────────┼─────────┼─────────┼─────────┼─────────┤
│ Req/Sec   │ 0   │ 0    │ 503     │ 576     │ 475.3   │ 166.71  │ 440     │
├───────────┼─────┼──────┼─────────┼─────────┼─────────┼─────────┼─────────┤
│ Bytes/Sec │ 0 B │ 0 B  │ 4.13 MB │ 4.73 MB │ 3.91 MB │ 1.37 MB │ 3.62 MB │
└───────────┴─────┴──────┴─────────┴─────────┴─────────┴─────────┴─────────┘

Req/Bytes counts sampled once per second.
# of samples: 30

6k requests in 10.02s, 39.1 MB read

Roadrunner

❯ autocannon http://127.0.0.1:8000 -d 10 -w 3 -c 100 -p 10
Running 10s test @ http://127.0.0.1:8000
100 connections with 10 pipelining factor
3 workers

-
┌─────────┬────────┬─────────┬─────────┬─────────┬────────────┬───────────┬─────────┐
│ Stat    │ 2.5%   │ 50%     │ 97.5%   │ 99%     │ Avg        │ Stdev     │ Max     │
├─────────┼────────┼─────────┼─────────┼─────────┼────────────┼───────────┼─────────┤
│ Latency │ 119 ms │ 1692 ms │ 2314 ms │ 2587 ms │ 1617.82 ms │ 574.62 ms │ 3153 ms │
└─────────┴────────┴─────────┴─────────┴─────────┴────────────┴───────────┴─────────┘
┌───────────┬─────────┬─────────┬─────────┬─────────┬─────────┬─────────┬─────────┐
│ Stat      │ 1%      │ 2.5%    │ 50%     │ 97.5%   │ Avg     │ Stdev   │ Min     │
├───────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤
│ Req/Sec   │ 366     │ 366     │ 544     │ 861     │ 546.3   │ 124.68  │ 366     │
├───────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤
│ Bytes/Sec │ 3.01 MB │ 3.01 MB │ 4.47 MB │ 7.08 MB │ 4.49 MB │ 1.02 MB │ 3.01 MB │
└───────────┴─────────┴─────────┴─────────┴─────────┴─────────┴─────────┴─────────┘

Req/Bytes counts sampled once per second.
# of samples: 30

6k requests in 10.02s, 44.9 MB read

Чтобы протестировать приложение через Nginx, нам нужно настроить Laravel Valet , а затем приступить к выполнению той же команды; но в данном случае мы используем 127.0.0.1, потому что он работает на порту 80.

❯ autocannon http://127.0.0.1 -d 10 -w 3 -c 100 -p 10
Running 10s test @ http://127.0.0.1
100 connections with 10 pipelining factor
3 workers

/
┌─────────┬────────┬────────┬────────┬────────┬───────────┬─────────┬────────┐
│ Stat    │ 2.5%   │ 50%    │ 97.5%  │ 99%    │ Avg       │ Stdev   │ Max    │
├─────────┼────────┼────────┼────────┼────────┼───────────┼─────────┼────────┤
│ Latency │ 111 ms │ 169 ms │ 202 ms │ 235 ms │ 166.22 ms │ 23.1 ms │ 290 ms │
└─────────┴────────┴────────┴────────┴────────┴───────────┴─────────┴────────┘
┌───────────┬─────────┬─────────┬─────────┬─────────┬─────────┬────────┬─────────┐
│ Stat      │ 1%      │ 2.5%    │ 50%     │ 97.5%   │ Avg     │ Stdev  │ Min     │
├───────────┼─────────┼─────────┼─────────┼─────────┼─────────┼────────┼─────────┤
│ Req/Sec   │ 4551    │ 4551    │ 5691    │ 6343    │ 5718.8  │ 464.3  │ 4548    │
├───────────┼─────────┼─────────┼─────────┼─────────┼─────────┼────────┼─────────┤
│ Bytes/Sec │ 2.13 MB │ 2.13 MB │ 2.67 MB │ 2.98 MB │ 2.68 MB │ 218 kB │ 2.13 MB │
└───────────┴─────────┴─────────┴─────────┴─────────┴─────────┴────────┴─────────┘

Req/Bytes counts sampled once per second.
# of samples: 32

0 2xx responses, 62950 non 2xx responses
64k requests in 10.01s, 29.5 MB read

Заключение

Согласно эталонному анализу, вы заметите, что Nginx выполнил общее количество запросов 64 тыс. , что намного больше, чем запросы, сделанные как Swoole, так и RoadRunner, которые составляют около 12 тыс. , или по 6 тыс. каждый.