我正在使用django 1.4,芹菜3.0,rabbitmq
为了描述这个问题,我在系统中有很多内容网络,我想要一个队列来处理与这些网络相关的任务。
然而,当系统处于活动状态时,内容会立即创建,因此我需要动态创建队列并让现有工作人员开始接收它们。
我尝试按以下方式安排任务(内容是django模型实例):
queue_name = 'content.{}'.format(content.pk)
# E.g. queue_name = content.0c3a92a4-3472-47b8-8258-2d6c8a71e3ba
add_content.apply_async(args=[content], queue=queue_name)
这将创建一个名为content.0c3a92a4-3472-47b8-8258-2d6c8a71e3ba
的队列,创建一个名为content.0c3a92a4-3472-47b8-8258-2d6c8a71e3ba
的新交换和路由密钥content.0c3a92a4-3472-47b8-8258-2d6c8a71e3ba
,并将任务发送到该队列。
但是我从未看到工作人员接受这些任务。我当前设置的工作人员没有收听任何特定的队列(没有使用队列名称初始化)并接收发送给他们的任务。默认队列就好了。我的芹菜设置是:
BROKER_URL = "amqp://test:password@localhost:5672/vhost"
CELERY_TIMEZONE = 'UTC'
CELERY_ALWAYS_EAGER = False
from kombu import Exchange, Queue
CELERY_DEFAULT_QUEUE = 'default'
CELERY_DEFAULT_EXCHANGE = 'default'
CELERY_DEFAULT_EXCHANGE_TYPE = 'direct'
CELERY_DEFAULT_ROUTING_KEY = 'default'
CELERY_QUEUES = (
Queue(CELERY_DEFAULT_QUEUE, Exchange(CELERY_DEFAULT_EXCHANGE),
routing_key=CELERY_DEFAULT_ROUTING_KEY),
)
CELERY_CREATE_MISSING_QUEUES = True
CELERYD_PREFETCH_MULTIPLIER = 1
知道如何让工作人员接收发送到这个新创建的队列的任务吗?
答案 0 :(得分:7)
您需要告诉工作人员开始使用新队列。相关文档为here。
从命令行:
$ celery control add_consumer content.0c3a92a4-3472-47b8-8258-2d6c8a71e3ba
或者在python中:
>>> app.control.add_consumer('content.0c3a92a4-3472-47b8-8258-2d6c8a71e3ba', reply=True)
两个表单都接受目标参数,因此如果需要,您只能告诉单个工作人员新的队列。
答案 1 :(得分:0)
我们可以动态添加队列并将工作人员附加到他们身上。
from celery import current_app as app
from task import celeryconfig #your celeryconfig module
动态定义任务并将其路由到队列
from task import process_data
process_data.apply_async(args,kwargs={}, queue='queue-name')
reply = app.control.add_consumer('queue_name', destination = ('your-worker-name',), reply = True)
您必须将队列名称保存在持久数据存储中,例如redis,以便在重新启动时记住它。
redis.sadd('CELERY_QUEUES','queue_name')
celeryconfig.py也使用相同的方法来记住队列名称
CELERY_QUEUES = {
'celery-1': {
'binding_key': 'celery-1'
},
'gateway-1': {
'binding_key': 'gateway-1'
},
'gateway-2': {
'binding_key': 'gateway-2'
}
}
for queue in redis.smembers('CELERY_QUEUES'):
CELERY_QUEUES[queue] = dict(binding_key=queue)