Celery异步发送激活邮件
Celery介绍
- 1.Celery介绍
- 点击查看Celery参考文档
- Celery是一个功能完备即插即用的任务队列
- Celery适用异步处理问题,比如发送邮件、文件上传,图像处理等等比较耗时的操作,我们可将其异步执行,这样用户不需要等待很久,提高用户体验
- 2.Celery特点:
- 简单,易于使用和维护,有丰富的文档
- 高效,单个Celery进程每分钟可以处理数百万个任务
- 灵活,Celery中几乎每个部分都可以自定义扩展
- Celery非常易于集成到一些web开发框架中
3.安装Celery
# 进入虚拟环境 pip install celery
4.Celery组成结构
- 任务队列是一种跨线程、跨机器工作的一种机制
- 任务队列中包含任务的工作单元。有专门的工作进程持续不断的监视任务队列,并从中获得新的任务并处理
- Celery通过消息进行通信,通常使用一个叫broker(中间人)来协client(任务的发出者)和worker(任务的处理者)
- client发出消息到队列中,broker将队列中的信息派发给worker来处理
- 一个Celery系统可以包含很多的worker和broker,可增强横向扩展性和高可用性能。
Celery组成结构是生产者消费者模型的一种体现
Celery使用
1.创建Celery异步任务文件
2.创建应用对象/客户端/client
- 应用对象内部封装要异步执行的任务
- Celery():
- 参数1是异步任务路径
- 参数2是指定的broker
- redis://密码@redis的ip:端口/数据库
- redis://192.168.243.191:6379/4
- 返回客户端应用对象app
- send_active_email():内部封装激活邮件内容,并用装饰器@app.task注册
调用python的send_mail()将激活邮件发送出去
from celery import Celery from django.core.mail import send_mail from django.conf import settings # 创建celery应用对象 app = Celery('celery_tasks.tasks', broker='redis://192.168.243.191:6379/4') @app.task def send_active_email(to_email, user_name, token): """发送激活邮件""" subject = "天天生鲜用户激活" # 标题 body = "" # 文本邮件体 sender = settings.EMAIL_FROM # 发件人 receiver = [to_email] # 接收人 html_body = '<h1>尊敬的用户 %s, 感谢您注册天天生鲜!</h1>' \ '<br/><p>请点击此链接激活您的帐号<a href="http://127.0.0.1:8000/users/active/%s">' \ 'http://127.0.0.1:8000/users/active/%s</a></p>' %(user_name, token, token) send_mail(subject, body, sender, receiver, html_message=html_body)
3.中间人broker
- 示例:此处演示Redis数据库作为中间人broker
- Celery需要一种解决消息的发送和接受的方式,我们把这种用来存储消息的的中间装置叫做message broker, 也可叫做消息中间人。
作为中间人,我们有几种方案可选择:
1.RabbitMQ
- RabbitMQ是一个功能完备,稳定的并且易于安装的broker. 它是生产环境中最优的选择。
使用RabbitMQ的细节参照以下链接: http://docs.celeryproject.org/en/latest/getting-started/brokers/rabbitmq.html#broker-rabbitmq
如果使用的是Ubuntu或者Debian发行版的Linux,可以直接通过命令安装RabbitMQ:
sudo apt-get install rabbitmq-server
- 安装完毕之后,RabbitMQ-server服务器就已经在后台运行。
- 如果用的并不是Ubuntu或Debian, 可以在以下网址: http://www.rabbitmq.com/download.html去查找自己所需要的版本软件。
2.Redis
- Redis也是一款功能完备的broker可选项,但是其更可能因意外中断或者电源故障导致数据丢失的情况。
- 关于是由那个Redis作为Broker,可访下面网址: http://docs.celeryproject.org/en/latest/getting-started/brokers/redis.html#broker-redis
4.创建worker
- 示例:此处演示把worker创建到ubuntu虚拟机中,ubuntu作为Celery服务器
Celery服务器创建worker步骤
1.把项目代码拷贝一份到ubuntu虚拟机中
- 并在celery_tasks/tasks.py文件顶部添加以下代码
作用:让Celery的worker能够加载Django配置环境
import os os.environ["DJANGO_SETTINGS_MODULE"] = "dailyfresh.settings" # 放到Celery服务器上时添加的代码 import django django.setup()
2.终端创建worker
celery -A celery_tasks.tasks worker -l info
3.开启redis-server,查看broker
4.测试发邮件
5.查看worker收到的异步任务消息
完整注册逻辑实现代码
class RegisterView(View):
"""类视图:处理注册"""
def get(self, request):
"""处理GET请求,返回注册页面"""
return render(request, 'register.html')
def post(self, request):
"""处理POST请求,实现注册逻辑"""
# 获取注册请求参数
user_name = request.POST.get('user_name')
password = request.POST.get('pwd')
email = request.POST.get('email')
allow = request.POST.get('allow')
# 参数校验:缺少任意一个参数,就不要在继续执行
if not all([user_name, password, email]):
return redirect(reverse('users:register'))
# 判断邮箱
if not re.match(r"^[a-z0-9][\w\.\-]*@[a-z0-9\-]+(\.[a-z]{2,5}){1,2}$", email):
return render(request, 'register.html', {'errmsg':'邮箱格式不正确'})
# 判断是否勾选协
if allow != 'on':
return render(request, 'register.html', {'errmsg': '没有勾选用户协议'})
# 保存数据到数据库
try:
# 隐私信息需要加密,可以直接使用django提供的用户认证系统完成
user = User.objects.create_user(user_name, email, password)
except db.IntegrityError:
return render(request, 'register.html', {'errmsg': '用户已注册'})
# 手动的将用户认证系统默认的激活状态is_active设置成False,默认是True
user.is_active = False
# 保存数据到数据库
user.save()
# 生成激活token
token = user.generate_active_token()
# celery发送激活邮件:异步完成,发送邮件不会阻塞结果的返回
send_active_email.delay(email, user_name, token)
# 返回结果:比如重定向到首页
return redirect(reverse('goods:index'))
#发送邮件的驱动
EMAIL_BACKEND = 'django.core.mail.backends.smtp.EmailBackend'
#邮件服务器
EMAIL_HOST = 'smtp.163.com'
#smtp服务器的端口
EMAIL_PORT = 25
#发送邮件的邮箱
EMAIL_HOST_USER = '[email protected]'
#在邮箱中设置的客户端授权密码
EMAIL_HOST_PASSWORD = 'xxxxxxxxxxx'
#收件人看到的发件人
EMAIL_FROM = '标题<[email protected]>'