Skip to main content

Отладка с помощью xdebug

Отладка сервиса на базе Swoole

Настройка отладки конкретного сервиса

Действия из этого раздела каждый разработчик должен повторить для каждого сервиса на своей машине.

Добавляем в .env следующие переменные:

DEBUG_HOST=host.docker.internal
DEBUG_PORT=9101
MAX_EXECUTION_TIME=3600

Переменная DEBUG_PORT должна иметь уникальное значение в пределах проекта.

Далее идём в настройки PhpStorm, В раздел PHP > Debug и указываем там порт отладки для текущего сервиса. Screenshot

В разделе PHP > Servers настраиваем маппинг путей. Важно заполнить значения как показано на скриншоте, потому что такие значения указаны в конфигах запуска сервера. Screenshot

Запуск отладки

Если файл .env был только что отредактирован, то нужно перезапустить сервис

elc restart

Включаем прослушивание порта отладки в PhpStorm

Screenshot

FPM

При использовании FPM, вы можете поставить брейкпоинт в IDE и добавить к HTTP запросу GET параметр XDEBUG_SESSION=1.

Swoole

Способ установки брейкпоинтов для swoole немного отличается от привычного. Нельзя добавлять/убирать брейкпоинты во время работы приложения. Устанавливать брейкпоинты можно только когда приложение уже остановлено брейкпоинтом. Самый первый брейкпоинт нужно установить вызвав функцию xdebug_break прямо в коде.

public function search(PageBuilderFactory $pageBuilderFactory, BannersQuery $query)
{
xdebug_break(); // <<< останавливаем работу приложения
return BannersResource::collectPage(
$pageBuilderFactory->fromQuery($query)->build()
);
}

Пока приложение остановлено можно добавлять и убирать брейкпоинты обычным способом - кликая рядом с номерами строк.

tip

Иногда брейкпоинт поставленный вызовом xdebug_break промахивается и останавливается на одну-две строки ниже чем надо. Если это повторяется, можно добавить лишних операций

xdebug_break();
$a = 1;
$b = 2;
Swoole

Когда вы хотите остановить отладку swoole, вам необходимо нажимать не на стоп, а на продолжение работы.

Screenshot

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

Перезапускать сервис при добавлении/убирании функцйии xdebug_break не нужно, здесь отработает обычный способ подгрузки кода.

Для отладки консольных команд, запускать их нужно находясь внутри контейнера, а не через elc php artisan. Заходить в контейнер нужно обязательно запуская bash, а не sh, это необходимо для того чтобы процесс получил необходимые env переменные из контейнерного .bashrc.

elc bash
php artisan import:products

Ставить первый брейкпоинт здесь нужно тоже с помощью функции xdebug_break.

Подготовка воркспейса

Всё что описано в этом разделе делается один раз на старте проекта и доставляется на машины разработчиков при клонировании воркспейса/севрисов.

В энтрипоинте контейнера (<workspace>/templates/swoole-8.2/php/enstrypoint) настраиваем запуск сервера в режиме отладки при наличии в .env переменной DEBUG_HOST.

DEBUG_HOST=$(sed "s/^#.*//" .env | grep -oE 'DEBUG_HOST=.*' | sed -r 's/DEBUG_HOST=(.*)/\1/')
DEBUG_PORT=$(sed "s/^#.*//" .env | grep -oE 'DEBUG_PORT=.*' | sed -r 's/DEBUG_PORT=(.*)/\1/')

if [ "${DEBUG_HOST}" != "" ]; then
{
echo ""
echo "xdebug.mode=develop,debug"
echo "xdebug.client_host=${DEBUG_HOST}"
echo "xdebug.client_port=${DEBUG_PORT}"
echo "max_execution_time=3600"
echo ""
} >> /usr/local/etc/php/conf.d/docker-php-ext-xdebug.ini
sed 's/request_terminate_timeout =.*/request_terminate_timeout = 3600s/' -i /usr/local/etc/php-fpm.d/www.conf
fi

PHP_IDE_CONFIG=serverName=local \
OCTANE_SHOW_FATAL_ERROR=true \
php artisan octane:swoole --watch --host=0.0.0.0 --workers=1 --task-workers=1 || sleep 3600
FPM

Для fpm в последней строчке будет

PHP_IDE_CONFIG=serverName=local \
php-fpm -R

В контейнероном .bashrc (<workspace>/home/.bashrc) должна быть экспортирована переменая

export PHP_IDE_CONFIG=serverName=local

В конфиге nginx'a сервиса должен быть увеличен лимит на длительность запроса. В файле <workspace>/templates/swoole-8.2/nginx/default.conf.template должны присутствовать следующие строки:

proxy_connect_timeout 3600s;
proxy_send_timeout 3600s;
proxy_read_timeout 3600s;

Аналогичные настройки должны быть и в сервисе proxy. Обычно они находятся в файле <workspace>/services/proxy/conf/proxy.conf.

Swoole

Для Swoole таймаут обработки запроса нужно увеличить в коде каждого сервиса.

Задаётся это в файле config/octane.php:

'max_execution_time' => env('MAX_EXECUTION_TIME', 30),

Не забываем добавить переменную в .env и .env.example, потому что для отладки нужен существенно больший таймаут.

MAX_EXECUTION_TIME=3600