celery
原理图
celery基础使用
安装
pip install celery
包架构封装
project
├── celery_task # celery包
│ ├── __init__.py # 包文件
│ ├── celery.py # celery连接和配置相关文件,且名字必须是celery.py
│ └── tasks.py # 所有任务函数
├── add_task.py # 添加任务
└── get_result.py # 获取结果
启动celery服务
注意
cd 到celery_task所在文件夹下
非windows
命令:celery worker -A celery_task -l info
windows:
pip install eventlet
#注意celery_task这是找的包名字
celery worker -A celery_task -l info -P eventlet
使用
celery.py
from celery import Celery
# broker:任务仓库
broker = 'redis://127.0.0.1:6379/5'
# backend:任务结果仓库
backend = 'redis://127.0.0.1:6379/6'
# include:任务(函数)所在文件,反射
app = Celery(broker=broker, backend=backend, include=['celery_task.tasks'])
tasks.py
from .celery import app
@app.task
def add(n1, n2):
res = n1 + n2
print('n1 + n2 = %s' % res)
return res
@app.task
def low(n1, n2):
res = n1 - n2
print('n1 - n2 = %s' % res)
return res
然后在外部调用tasks的方法就可以向Broker添加任务
add_task.py
# 右键执行该文件,下面环境合理
from celery_task.tasks import add, low
# 往celery的Broker中添加立即任务
add.delay(10, 20)
获取结果
这个是根据控制台的id取值的
get_result.py
# 右键执行该文件,下面环境合理
from celery_task.celery import app
from celery.result import AsyncResult
id = '016d69b1-f066-4817-85de-5b594f65ddc4'
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('任务已经开始被执行')
延迟任务
上面的案例是立即执行的
from celery_task.tasks import add, low
# 添加延迟任务
# args是jump任务需要的参数,没有就设置为空()
# eta是该任务执行的UTC格式的时间
from datetime import datetime, timedelta
#秒
def eta_second(second):
#获取当前时间
ctime = datetime.now()
#当前时间转化为UTC格式的时间
utc_ctime = datetime.utcfromtimestamp(ctime.timestamp())
print(utc_ctime.__class__)
#把秒转化为可以相加的时间
time_delay = timedelta(seconds=second)
print(time_delay.__class__)
#返回执行的时间
return utc_ctime + time_delay
#天
def eta_days(days):
ctime = datetime.now()
utc_ctime = datetime.utcfromtimestamp(ctime.timestamp())
time_delay = timedelta(days=days)
return utc_ctime + time_delay
# apply_async就是添加延迟任务
low.apply_async(args=(200, 50), eta=eta_second(10))
定时任务
注意要开两个窗口,因为需要两个socket
celery启动
celery worker -A celery_task -l info -P eventlet
自动发送任务
上面都是手动发送任务的
celery beat -A celery_task -l info
from celery import Celery
# broker:任务仓库
broker = 'redis://127.0.0.1:6379/5'
# backend:任务结果仓库
backend = 'redis://127.0.0.1:6379/6'
# include:任务(函数)所在文件
app = Celery(broker=broker, backend=backend, include=['celery_task.tasks'])
# 时区
app.conf.timezone = 'Asia/Shanghai'
# 是否使用UTC
app.conf.enable_utc = False
# 自动任务的定时配置,celery自带的
from celery.schedules import crontab
from datetime import timedelta
app.conf.beat_schedule = {
# 定时任务:任务名自定义
'fall_task': {
'task': 'celery_task.tasks.low', # 任务源
'args': (30, 10), # 任务参数s
'schedule': timedelta(seconds=3) # 定时添加任务的时间
# 'schedule': crontab(hour=8, day_of_week=1), # 每周一早八点
}
}
crontab
minute=0 每小时的0分钟
minute=0,hour=12 每天12点
minute=0,hour=12,day_of_week=1 每周一的12点
minute=0,hour=12,day_of_mouth=1 每月一号的12点
minute=0,hour=12,day_of_mouth=1,month_of_year 每年一月一号的12点
总结
结合django使用
django
由于使用了celery,就相当于有个独立的程序帮忙处理一部分请求
celery
独立的socket,不受django影响,
任务发布者
独立的socket,不受django影响
redis
由于数据库使用的是独立的redis,即使django服务关闭,任务依旧接收任务和存储结果
参考链接
https://blog.csdn.net/chenqiuge1984/article/details/80127446