不知道有没有人把 Celery 和 Signal 搞混,我之前也是有点含糊,两者原理都是去触发一些任务,那么这两者有什么区别呢?
下面使用 Celery 和 Signal 分别做一个发送短信的示例。
Celery 是开一个线程异步去执行这个任务,具体耗时多久都在这个线程中去处理这些逻辑,不会影响下面的操作,比如发送短信、邮件等。
发送短信示例:
celery 基础配置:
# project/celery.py
import os
from celery import Celery
from django.conf import settings
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'nsproject.settings')
app = Celery('nsproject')
app.config_from_object('django.conf:settings', namespace='CELERY')
app.autodiscover_tasks(settings.INSTALLED_APPS)
任务:app/task.py
from django.conf import settings
from lib.tengxunyun.sms import SmsSender
from nsproject.celery import app
@app.task
def sed_sms(identity, sms_code):
try:
import time
time.sleep(10) # 测试延时10秒
sms = SmsSender()
sms.send(identity, settings.SMS_TEMPLATE_ID['login'], sms_code)
except KeyError:
raise Exception('短信模板 id 不存在')
return True
调用任务:app/views.py
def send_sms_code(request):
user_sms.send(sender=None, sms_code=sms_code)
return HttpResponse('ok')
访问 app/urls.py:
path('api/otp/send_code',auth.send_sms_code),
结果很快就出来了,并没有感觉到10秒延时,可以具体测试一下,这里就不截图了。
自定义一个信号:
app/siganal.py
from django.dispatch import Signal
# 当发送验证码时,发送该信号
user_sms = Signal(providing_args=['sms_code'])
接收信号:
app/signal_handlers.py
from django.dispatch import receiver
from gongyequ.signals import user_sms
@receiver(user_sms)
def user_sms_handler(sms_code, **kwargs):
import time
time.sleep(10) # 模拟延时
print(sms_code)
注册信号:
app/apps.py
from django.apps import AppConfig
class xxConfig(AppConfig):
name = 'xx'
def ready(self):
import xx.signal_handlers # noqa: F401
触发信号:
app/views.py
def send_sms_code(request):
user_sms.send(sender=None, sms_code=sms_code)
结果:会发现很慢,要等十秒钟。
send() 和 send_robust():
send_robust() 捕获从 Python的 Exception 类派生的所有错误,并确保所有接收器都收到信号通知。如果发生错误,将在引发错误的接收器的元组对中返回错误实例。
send() 不 捕获接收器引起的任何异常;它只是允许错误传播。因此,并非所有的接收器都会在出现错误时被通知信号。
工作方式的不同:
celery(异步):通过消息机制进行通信,单独开一个线程去执行任务,不影响下面程序的执行,应用场景主要是一些耗时任务,如发送短信,邮件等。
signal(同步):当某事件发生时,触发相关的反应动作,如果发生错误程序将会阻塞,应用场景如:进入课程详情页时将浏览量加一,或者时注册成功之后给用户发送邮件、短信等。
Signal翻译过来中文就是信号- 当然, 本身他就是Linux系统编程中非常重要的概念, 信号机制是进程之间传递消息的一种机制,其全称为软中断信号:作用是通知进程发生了异步事件。进程之间可以调用系统来传递信号, 本身内核也可以发送信号给进程, 告诉该进程发生了某个事件.
架构的不同:
celery:task(任务)-broker(消息队列)-worker(任务处理者)
signal:signals(信号)-senders(寄件人)-receivers(接收者)
Celery 使用:https://blog.csdn.net/qq_39253370/article/details/116377577
Signal:https://docs.djangoproject.com/zh-hans/3.2/topics/signals/