• 分布式任务队列Celery 的安装和使用
  • 发布于 2个月前
  • 285 热度
    0 评论
  • 康康
  • 1 粉丝 33 篇博客
  •   
不知道大家有没有这样一种体验,就是我的todolist上有好多任务,但是当前我需要用机器来干别的事情,等忙得昏头转向的时候,又忘记或者错过了一些事情。如何能让他们自动定时的执行呢?
Celery 是一个强大的分布式任务队列 的异步处理框架,它可以让任务的执行完全脱离主程序,甚至可以被分配到其他主机上运行。我们通常使用它来实现异步任务(async task)和定时任务(crontab)。
我们需要一个消息队列来下发我们的任务。首先要有一个消息中间件,此处选择rabbitmq (也可选择 redis 或 Amazon Simple Queue Service(SQS)消息队列服务)。推荐 选择 rabbitmq 。使用RabbitMQ是官方特别推荐的方式,因此我也使用它作为我们的broker。

可以看到,Celery 主要包含以下几个模块:
1.任务模块 Task
包含异步任务和定时任务。其中,异步任务通常在业务逻辑中被触发并发往任务队列,而定时任务由 Celery Beat 进程周期性地将任务发往任务队列。
2.消息中间件 Broker
Broker,即为任务调度队列,接收任务生产者发来的消息(即任务),将任务存入队列。Celery 本身不提供队列服务,官方推荐使用 RabbitMQ 和 Redis等。
3.任务执行单元 Worker
Worker 是执行任务的处理单元,它实时监控消息队列,获取队列中调度的任务,并执行它。
4.任务结果存储 Backend
Backend 用于存储任务的执行结果,以供查询。同消息中间件一样,存储也可使用 RabbitMQ, 和 MongoDB等。

还是不好理解?本人这样理解的:
(任务模块 Task) 产品经理说,我们要做多少功能,这个sprint里面又有多少story. 都在dashbord列出来。
(消息中间件 Broker) 项目经理说,我每个任务都要预估下时间,排入sprint里面。初步指定完成的人。
(任务执行单元 Worker)码农A,拿到task, 就开始编码,实现功能,码农B也是如此。

(任务结果存储 Backend)代码写完后,需要提交存储到github.


让我们跑一个例子,我们使用RabbitMQ作为中间人,Redis作为结果存储。
安装:
$ pip install redis
$ pip install celery
定义任务函数
from celery import Celery
app = Celery('tasks',
             broker='amqp://guest@localhost//',
             backend='redis://localhost:6379/0')
@app.task
def add(x, y):
    return x + y

这里我们创建了一个Celery实例app,名称为’tasks’;中间人用RabbitMQ,URL为’amqp://guest@localhost//’;存储用Redis,URL为’redis://localhost:6379/0’。同时我们定义了一个Celery任务”add”,可以返回两个参数的和。当函数使用”@app.task”修饰后,即为可被Celery调度的任务。


运行celery服务
$ celery worker -A tasks --loglevel=info --concurrency=5
参数”-A”指定了Celery实例的位置,本例是在”tasks.py”中,celery命令会自动在该文件中寻找Celery对象实例。不过我更建议你指定Celery对象名称,如”-A tasks.app”。
参数”loglevel”指定了日志等级,也可以不加,默认为warning。

参数”concurrency”指定最大并发数,默认为CPU核数。


客户应用程序的调用
新建一个 main.py 文件 代码如下:
from tasks import add    
r = add.delay(2, 2)    
r = add.delay(3, 3)    
print r.ready()    
print r.result      
print r.get()
这样,就可以看到程序执行的结果了。
Celery 提供了一个 crontab 的对象,可以对于定时任务进行更为精确的时间设置,而不仅限于多少秒重复一次这种简单的任务。下面用例子的方式来说明一下。
from celery.schedules import crontab
# 每分钟执行一次
c1 = crontab()
# 每天凌晨十二点执行
c2 = crontab(minute=0, hour=0)
# 每十五分钟执行一次
crontab(minute='*/15')
# 每周日的每一分钟执行一次
crontab(minute='*',hour='*', day_of_week='sun')
# 每周三,五的三点,七点和二十二点没十分钟执行一次
crontab(minute='*/10',hour='3,17,22', day_of_week='thu,fri')
当然celery还又许多功能,这里简单入了个门。
用户评论