Celery 异步队列
1、Celery简介
Celery是一个专注于实时处理
和任务调度
的分布式任务队列
。所谓任务就是消息,消息中的有效载荷中包含要执行任务需要的全部数据。
使用Celery的常见场景如下:
- Web应用:当用户触发的一个操作需要较长时间才能执行完成时,可以把它作为任务交给Celery去异步执行,执行完再返回给用户。这段时间用户不需要等待,提高了网站的整体吞吐量和响应时间。
- 定时任务:生产环境经常会跑一些定时任务。假如你有上千台的服务器、上千种任务,定时任务的管理很困难,Celery可以帮助我们快速在不同的机器设定不同种任务。
- 同步完成的附加工作都可以异步完成。比如发送短信/邮件、推送消息、清理/设置缓存等
Celery架构图:
Celery包含如下组件:
- Celery Beat:任务调度器,Beat进程会读取配置文件的内容,周期性地将配置中到期需要执行的任务发送给任务队列。
- Celery Worker:执行任务的消费者,通常会在多台服务器运行多个消费者来提高执行效率。
- Broker:消息代理,或者叫作消息中间件,接受任务生产者发送过来的任务消息,存进队列再按序分发给任务消费方(通常是消息队列或者数据库)。
- Producer:调用了Celery提供的API、函数或者装饰器而产生任务并交给任务队列处理的都是任务生产者。
- Result Backend:任务处理完后保存状态信息和结果,以供查询。Celery默认已支持Redis、RabbitMQ、MongoDB、Django ORM、SQLAlchemy等方式。
2、简单Celery实现
一般来说我们会专门规定创建一个名为tasks
的目录来存放所有关于异步任务的代码
以及Celery的启动文件
,所有异步代码为以包的形式存在
例如:主项目/tasks/xxx
1.proj/tasks/app.py(celery启动主入口)
# 将Celery独立成目录
from celery import Celery
# 定义celery对象。第一个参数为celery别名
celery_app = Celery("web")
# 引入celery配置信息
# 方式一:直接字符串形式写配置文件路径
# celery_app.config_from_object("web.tasks.config")
# 方式二:将配置文件导入
from proj.tasks import config
celery_app.config_from_object(config)
# 让celery自动搜索任务,
# 一个包:python的一个目录,每个包中必须是以tasks.py命名的任务文件
# 列表中可以指定多个包的路径
celery_app.autodiscover_tasks(['proj.tasks.mail'])
2.proj/tasks/config.py(celery配置文件)
# celery配置文件
BROKER_URL = "redis://127.0.0.1:6379/1" # 指定 Broker
CELERY_RESULT_BACKEND = "redis://127.0.0.1:6379/2" # 指定 backend
CELERY_TIMEZONE='Asia/Shanghai' # 指定时区,默认是 UTC
3.proj/tasks/mail/tasks.py(创建一个任务)
from proj.tasks.app import celery_app
import time
@celery_app.task
def send_mail(mail):
time.sleep(10)
return 'successful'
4.proj/executor.py(执行任务)
from proj.tasks.mail.tasks import send_mail
def mail(mail):
print('1、开始发送邮件')
# 使用异步任务被celery装饰后的方法delay,实现异步任务推送
send_mail.delay(mail)
print('2、邮件发送成功')
mail('jasonminghao@163.com')
5.启动异步任务,即启动proj/tasks/app.py这个文件
celery -A proj.tasks.app worker -l info
启动proj/executor.py文件,将邮件任务推送到异步队列中
一点发送邮件,则将发送邮件的任务,推送给队列,然后立即返回结果,我们可以看看Celery异步队列的日志信息