Celery - запускайте разных воркеров на одном сервере

У меня есть 2 вида задач: Тип 1 - несколько небольших задач с высоким приоритетом. Type2 - много тяжелых задач с более низким приоритетом.

Изначально у меня была простая конфигурация с маршрутизацией по умолчанию, ключи маршрутизации не использовались. Этого было недостаточно - иногда все рабочие были заняты задачами типа 2, поэтому задача 1 откладывалась. Я добавил ключи маршрутизации:

CELERY_DEFAULT_QUEUE = "default"
CELERY_QUEUES = {
    "default": {
        "binding_key": "task.#",
    },
    "highs": {
        "binding_key": "starter.#",
    },
}
CELERY_DEFAULT_EXCHANGE = "tasks"
CELERY_DEFAULT_EXCHANGE_TYPE = "topic"
CELERY_DEFAULT_ROUTING_KEY = "task.default"

CELERY_ROUTES = {
        "search.starter.start": {
            "queue": "highs",
            "routing_key": "starter.starter",
        },
}

Итак, теперь у меня 2 очереди - с задачами с высоким и низким приоритетом.

Проблема - как запустить 2 сельдерея с разными настройками параллелизма?

Ранее сельдерей использовался в режиме демона (согласно к этому), поэтому только начало /etc/init.d/celeryd start было требуется, но теперь мне нужно запустить 2 разных сельдерея с разными очередями и параллелизмом. Как я могу это сделать?


person Andrew    schedule 28.03.2011    source источник


Ответы (4)


Основываясь на приведенном выше ответе, я сформулировал следующий файл / etc / default / celeryd (первоначально на основе конфигурации, описанной в документации здесь: http://ask.github.com/celery/cookbook/daemonizing.html), который работает для запуска двух рабочих сельдерея на одном компьютере, причем каждый рабочий обслуживает отдельную очередь (в в этом случае имена очереди - «по умолчанию» и «важно»).

По сути, этот ответ является просто расширением предыдущего ответа, поскольку он просто показывает, как сделать то же самое, но для сельдерея в режиме демона. Обратите внимание, что здесь мы используем django-celery:

CELERYD_NODES="w1 w2"

# Where to chdir at start.
CELERYD_CHDIR="/home/peedee/projects/myproject/myproject"

# Python interpreter from environment.
#ENV_PYTHON="$CELERYD_CHDIR/env/bin/python"
ENV_PYTHON="/home/peedee/projects/myproject/myproject-env/bin/python"

# How to call "manage.py celeryd_multi"
CELERYD_MULTI="$ENV_PYTHON $CELERYD_CHDIR/manage.py celeryd_multi"

# How to call "manage.py celeryctl"
CELERYCTL="$ENV_PYTHON $CELERYD_CHDIR/manage.py celeryctl"

# Extra arguments to celeryd
# Longest task: 10 hrs (as of writing this, the UpdateQuanitites task takes 5.5 hrs)
CELERYD_OPTS="-Q:w1 default -c:w1 2 -Q:w2 important -c:w2 2 --time-limit=36000 -E"

# Name of the celery config module.
CELERY_CONFIG_MODULE="celeryconfig"

# %n will be replaced with the nodename.
CELERYD_LOG_FILE="/var/log/celery/celeryd.log"
CELERYD_PID_FILE="/var/run/celery/%n.pid"

# Name of the projects settings module.
export DJANGO_SETTINGS_MODULE="settings"

# celerycam configuration
CELERYEV_CAM="djcelery.snapshot.Camera"
CELERYEV="$ENV_PYTHON $CELERYD_CHDIR/manage.py celerycam"
CELERYEV_LOG_FILE="/var/log/celery/celerycam.log"

# Where to chdir at start.
CELERYBEAT_CHDIR="/home/peedee/projects/cottonon/cottonon"

# Path to celerybeat
CELERYBEAT="$ENV_PYTHON $CELERYBEAT_CHDIR/manage.py celerybeat"

# Extra arguments to celerybeat.  This is a file that will get
# created for scheduled tasks.  It's generated automatically
# when Celerybeat starts.
CELERYBEAT_OPTS="--schedule=/var/run/celerybeat-schedule"

# Log level. Can be one of DEBUG, INFO, WARNING, ERROR or CRITICAL.
CELERYBEAT_LOG_LEVEL="INFO"

# Log file locations
CELERYBEAT_LOGFILE="/var/log/celerybeat.log"
CELERYBEAT_PIDFILE="/var/run/celerybeat.pid"
person eedeep    schedule 25.03.2012
comment
Спасибо! Это было очень полезно. - person Jacinda; 04.07.2013
comment
Вы только что спасли мне жизнь, во всей Сети так сложно найти полноценную правильную конфигурацию этого зверя. Вам нужно создать статью в блоге, тысячи будут счастливы! - person holms; 29.01.2015

Кажется, ответ - сельдерей-мульти - в настоящее время плохо документирован.

То, что мне нужно, можно сделать с помощью следующей команды:

celeryd-multi start 2 -Q:1 default -Q:2 starters -c:1 5 -c:2 3 --loglevel=INFO --pidfile=/var/run/celery/${USER}%n.pid --logfile=/var/log/celeryd.${USER}%n.log

Что мы делаем, так это запускаем 2 воркера, которые слушают разные очереди (-Q: 1 по умолчанию, Q: 2 - стартеры) с разным параллелизмом -c: 1 5 -c: 2 3

person Andrew    schedule 29.03.2011

Другой вариант - дать рабочему процессу уникальное имя - с помощью аргумента -n.

У меня есть два приложения Pyramid, работающих на одном физическом оборудовании, каждое со своим собственным экземпляром сельдерея (в пределах своих виртуальных виртуальных машин).

У них обоих есть Supervisor, контролирующий их обоих, причем оба имеют уникальный файл supervisord.conf.

приложение1:

[program:celery]                                            
autorestart=true                                            
command=%(here)s/../bin/celery worker -n ${HOST}.app1--app=app1.queue -l debug
directory=%(here)s     

[2013-12-27 10:36:24,084: WARNING/MainProcess] [email protected] ready.

приложение2:

[program:celery]                                 
autorestart=true                                 
command=%(here)s/../bin/celery worker -n ${HOST}.app2 --app=app2.queue -l debug
directory=%(here)s                               

[2013-12-27 10:35:20,037: WARNING/MainProcess] [email protected] ready.
person maz    schedule 27.12.2013
comment
Я хотел бы сделать что-то подобное, когда у меня есть несколько экземпляров worker. Я пытался прочитать страницу задач маршрутизации, но не совсем понял. Как вы направляете задачи каждому конкретному работнику? - person Raj; 22.01.2014
comment
Задачи автоматически направляются к нужному исполнителю, потому что рабочие для maz находятся в одной виртуальной среде, а рабочие для "Clockworkelves" находятся в другой виртуальной среде. - person maz; 23.01.2014
comment
Я предполагаю, что эта установка может работать, если я хочу, чтобы оба экземпляра извлекались из одной очереди? - person ChrisC; 04.02.2014
comment
Я не уверен. Хотя, если вы посмотрите мой проект на github. Вы можете настроить nginx так, чтобы у него было два виртуальных хоста, и таким образом вы могли узнать наверняка. github.com/mazzaroth/initpyr - person maz; 05.02.2014

Обновление:

В Celery 4.x ниже будет работать правильно:

celery multi start 2 -Q:1 celery -Q:2 starters -A $proj_name

Или, если вы хотите указать имя экземпляра, вы можете:

celery multi start name1 name2 -Q:name1 celery -Q:name2 queue_name -A $proj_name

Тем не менее, я считаю, что если мы будем использовать celery multi, он не будет печатать подробные журналы на экране, поскольку это всего лишь ярлык сценария для загрузки этих экземпляров.

Я полагаю, что это также сработает, если мы запустим эти экземпляры один за другим вручную, давая им разные имена узлов, но -A те же $proj_name, хотя это небольшая трата времени.

Кстати, согласно официальному документу, вы можете убить всех рабочих сельдерея, просто:

ps auxww | grep 'celery worker' | awk '{print $2}' | xargs kill -9

person Alexww    schedule 11.07.2018