返回介绍

异步电子邮件

发布于 2025-01-02 21:53:53 字数 1590 浏览 0 评论 0 收藏 0

如果你正在使用 Python 提供的模拟电子邮件服务器,可能没有注意到这一点,那就是发送电子邮件会大大减慢应用的速度,原因是发送电子邮件时所发生的和电子邮件服务器的网络交互。通常需要几秒钟的时间才能收到电子邮件,如果收件人的电子邮件服务器速度较慢,或者收件人有多个,则可能会更久。

我真正想要的 send_email() 函数是 异步的 。 那是什么意思? 这意味着当这个函数被调用时,发送邮件的任务被安排在后台进行,释放 send_email() 函数以立即返回,以便应用可以在发送邮件的同时继续运行。

Python 实际上有多种方式支持运行异步任务, threadingmultiprocessing 模块都可以做到这一点。 为发送电子邮件启动一个后台线程,比开始一个全新的进程需要的资源少得多,所以我打算采用这种方法:

from threading import Thread
# ...

def send_async_email(app, msg):
    with app.app_context():
        mail.send(msg)

def send_email(subject, sender, recipients, text_body, html_body):
    msg = Message(subject, sender=sender, recipients=recipients)
    msg.body = text_body
    msg.html = html_body
    Thread(target=send_async_email, args=(app, msg)).start()

send_async_email 函数现在运行在后台线程中,它通过 send_email() 的最后一行中的 Thread() 类来调用。 有了这个改变,电子邮件的发送将在线程中运行,并且当进程完成时,线程将结束并自行清理。 如果你已经配置了一个真正的电子邮件服务器,当你按下密码重置请求表单上的提交按钮时,肯定会注意到访问速度的提升。

你可能预期只有 msg 参数会被发送到线程,但正如你在代码中所看到的那样,我也传入了应用实例。 使用线程时,需要牢记 Flask 的一个重要设计方面。 Flask 使用 上下文 来避免必须跨函数传递参数。 我不打算详细讨论这个问题,但是需要知道的是,有两种类型的上下文,即 应用上下文 和 请求上下文 。 在大多数情况下,这些上下文由框架自动管理,但是当应用启动自定义线程时,可能需要手动创建这些线程的上下文。

许多 Flask 插件需要应用上下文才能工作,因为这使得他们可以在不传递参数的情况下找到 Flask 应用实例。这些插件需要知道应用实例的原因是因为它们的配置存储在 app.config 对象中,这正是 Flask-Mail 的情况。 mail.send() 方法需要访问电子邮件服务器的配置值,而这必须通过访问应用属性的方式来实现。 使用 with app.app_context() 调用创建的应用上下文使得应用实例可以通过来自 Flask 的 current_app 变量来进行访问。

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文