celery的使用
celery是什么
- celery是一个异步任务框架,用来执行异步任务,执行延迟任务,执行定时任务
- Celery is a project with minimal funding, so we don’t support Microsoft Windows. Please don’t open any issues related to that platform.
- 由于celery没有windows版本,所以在windows平台上使用celery需要注意一些事项
celery的使用
Celery的架构由三部分组成,消息中间件(message broker),任务执行单元(worker)和任务执行结果存储(task result store)组成。
-
消息中间件:Celery本身不提供消息服务,但是可以方便的和第三方提供的消息中间件集成。包括,RabbitMQ, Redis等等。
-
任务执行单元:Worker是Celery提供的任务执行的单元,worker并发的运行在分布式的系统节点中。
-
任务结果存储:Task result store用来存储Worker执行的任务的结果,Celery支持以不同方式存储任务的结果,包括AMQP, redis等。
下载celery
pip install celery
使用前要先配置好redis,这里采用django框架链接redis使用
启动worker命令
linux/Mac中
celery worker -A celery_task -l info
windows系统中
celery worker -A celery_task -l info -P eventlet
eventlet需要下载
pip install eventlet
celery 5.0版本之后启动命令稍有变动
celery -A celery_task worker -l info -P eventlet
把celery写在一个py文件中
from celery import Celery
broker = 'redis://127.0.0.1:6379/1' # broker任务队列
backend = 'redis://127.0.0.1:6379/2' # 结构存储,执行完的结果存在这
# 注册app
app = Celery(__name__, broker=broker, backend=backend)
# 添加任务(使用这个装饰器,@app.task)
@app.task
def add(x, y):
print(x, y)
return x + y
......启动worker.....
'''
启动worker需要把路径切换到celery_task.py所在路径
'''
# 把任务添加到celery的broke中
from celery_task import add
ret=add.delay(5,4) #想broker中添加一个任务
print(ret) # ret 是定时任务的id
查看任务结果
from celery_task import app
from celery.result import AsyncResult
id = '3e397fd7-e0c1-4c5c-999c-2655a96793bb' # 定时任务id
if __name__ == '__main__':
async = AsyncResult(id=id, app=app)
if async.successful():
result = async.get()
print(result)
elif async.failed():
print('任务失败')
elif async.status == 'PENDING':
print('任务等待中被执行')
elif async.status == 'RETRY':
print('任务异常后正在重试')
elif async.status == 'STARTED':
print('任务已经开始被执行')
celery包结构
celery有两种结构,一种是上述把任务和链接celery全部写到一个py文件中基本结构,一种是下述包结构,推荐使用包结构
包结构的使用
1 新建一个包,叫celery_task
2 包下建一个名为celery的py文件 必须加celery
from celery import Celery
broker='redis://127.0.0.1:6379/1' #broker任务队列
backend='redis://127.0.0.1:6379/2'# 结构存储,执行完的结果存在这
app=Celery(__name__,broker=broker,backend=backend,include=['celery_task.task1','celery_task.task2'])
3 把任务分类建在不同的py文件中
task1.py
from .celery import app
@app.task
def add(x, y):
print(x, y)
return x + y
task2.py
from .celery import app
@app.task
def mutile(x, y):
print(x, y)
return x * y
4. 启动worker
需要将路径切换到celery_task包所在路径,命令同上
添加任务(异步任务和延迟任务)
在你需要添加任务的py文件中导入所需任务执行即可
from celery_task.task1 import add
from celery_task.task2 import mutile
# 提交异步任务
ret = add.delay(6, 7)
# 提交延迟任务
from datetime import datetime, timedelta
# 需要utc时间
eta = datetime.utcnow() + timedelta(seconds=10) # 10庙后执行
ret = mutile.apply_async(args=(9, 9), eta=eta)
获取结果方式同上
执行定时任务
- 定时任务直接配置在celery.py中即可
from celery import Celery
broker = 'redis://127.0.0.1:6379/1' # broker任务队列
backend = 'redis://127.0.0.1:6379/2' # 结构存储,执行完的结果存在这
app = Celery(__name__, broker=broker, backend=backend, include=['celery_task.task1', 'celery_task.task2'])
# 执行定时任务
# 调整时区
app.conf.timezone = 'Asia/Shanghai'
app.conf.enable_utc = False
# 任务的定时配置
from datetime import timedelta
from celery.schedules import crontab
app.conf.beat_schedule = {
'add-task': {
'task': 'celery_task.task1.add', # 定时任务的路径
'schedule': crontab(hour=8, day_of_week=1), # 周一早上8点执行
'args': (300, 150) # 参数
}
}
- 需要注意的时,定时任务需要beat来到时间把任务提交到worker
启动worker,启动beat
celery -A celery_task worker -l info -P eventlet
celery -A celery_task beat -l info