Сейчас в тренде писать об использовании gearman-job-server в качестве системы, которая позволяет в фоне выполнять ресурсоёмкие задачи и горизонтально масштабироваться. Подробнее можно почитать http://gearman.org/use_cases.
Упрощённо систему можно представить как дополнительный уровень абстракции “планировщик”, куда можно поставить в очередь задачу, а потом [с другой машины] законнектиться и, забрав её из очереди, выполнить. Подробно описывать принцип работы системы я не буду, так каб об этом можно почитать как на официальном сайте gearmand, так и много ещё где. Но сразу отмечу, что спавнить воркеры по событию (добавление задания в очередь) гиармэн не умеет. Так что поднимать “демон” воркера и следить за его состоянием придётся своими силами, например с помощью supervisor.
Итак, поскольку в debian stable (который сейчас wheezy) пакет gearman-job-server имеет старую версию 0.33, а в backports нет свежего пакета, то мы будем устанавливать его из testing репозитория debian jessie, для чего переведём систему в смешанный режим, со stable дистрибьютивом по-умолчанию.
# переводим систему в смешанный режим, где wheezy основной дистрибьютив echo 'APT::Default-Release "wheezy";' >> /etc/apt/apt.conf apt-get update apt-get install -t jessie gearman-job-server libgearman-dev # устанавливаем PEAR, чтобы собрать расширение php gearman самим из PECL apt-get install php-pear php5-dev mount -o remount,exec /tmp/ # ибо иначе получим shtool at '/tmp/pear/temp/gearman/build/shtool' does not exist or is not executable # на момент написания статьи это самая свежая версия доступная тут http://pecl.php.net/package/gearman pecl install channel://pecl.php.net/gearman-1.1.2 mount -o remount,noexec /tmp/ # дописываем расширение в конфиг пхп echo "extension=gearman.so" >> /etc/php5/conf.d/gearman.ini # если у вас FastCGI, то загружаем новый конфиг так /etc/init.d/php5-fpm reload |
Теперь Gearman работает, что можно простестить из php, выполнив нижеприведённый код и получив “1.0.6”
<?php print gearman_version() . "\n"; ?> |
Теперь установим супервизор, который позволит нам демонизировать php-воркеры и перезапускать их после того как они умрут
apt-get install supervisor vi /etc/supervisor/conf.d/test.conf [program:test] command=php /home/user/gearman/worker.php user=user process_name=%(process_num)s stdout_logfile=/var/log/supervisor-test.log stderr_logfile=/var/log/supervisor-test.log redirect_stderr=true autostart=true autorestart=true startsecs=5 numprocs=1 supervisorctl update |
,где /home/user/gearman/worker.php наш тестовый воркер
<?php $worker= new GearmanWorker(); $worker->addServer(); $worker->addFunction("reverse", "my_reverse_function"); while ($worker->work()); function my_reverse_function($job) { return strrev($job->workload()); } ?> |
Не забываем обязательно указать в конфиге существующего пользователя, а то супервизор будет крутить службы от root.
Cоздаём клиент client.php и запускаем его. Вывод должен показать нам “!dlroW olleH”
<?php $client= new GearmanClient(); $client->addServer(); print $client->do("reverse", "Hello World!"); ?> |
Теперь, чтобы обновить пакеты, установленные из jessie необходимо будет выполнять:
apt-get update && apt-get install `apt-show-versions -u -b | grep jessie | cut -d ' ' -f 1` |
Позже, я постараюсь написать о недостатках гиармэна (таких, как возможность потерять задание, в случае неожиданной смерти воркера) и способов минимизировать их возможные последствия (без перенесения в приложение всей логики по контролю всех этих вещей)
в wheezy нужно устанавливать пакет php-pear – пакета php5-pear нет
действительно, спасибо – поправил
с локальными воркерами все пашет ок, но при использовании разных(удаленных) серверов получаю ошибку
ErrorException [ 2 ]: GearmanClient::runTasks(): send_packet(GEARMAN_COULD_NOT_CONNECT) Failed to send server-options packet -> libgearman/connection.cc:433
в иптейблс доступ разрешен
Чтобы не потерять задачи из Gearman надо для него настроить сохранение очереди в Mysql