zoukankan      html  css  js  c++  java
  • Flask扩展 -- flask-mail

    电子邮件是最常用的通信方式之一。虽然Python标准库中的smtplib包可用在Flask程序中发送电子邮件,但包装了smtplib的Flask-Mail扩展能更好的和Flask集成。

    1.安装Flask-Mail

    1.1使用pip安装

    pip install flask-mail

    1.2 下载源码安装

    git clone https://github.com/mattupstate/flask-mail.git
    cd flask-mail
    python setup.py install

    2.flask-mail初始化

    from flask import Flask
    from flask_mail import Mail, Message
    
    app = Flask(__name__)
    mail = Mail(app)

    3.Flask-Mail 配置

    3.1 Flask-Mail常用配置项

    Flask-Mail通过标准的Flask配置API进行配置,这些常用的配置项如下:

    配置  默认值 说明
    MAIL_SERVER localhost 电子邮件服务器的主机名或IP地址         
    MAIL_PORT 25 电子邮件服务器的端口
    MAIL_USE_TLS False 启用传输层安全(Transport Layer Security,TLS)协议
    MAIL_USE_SSL Flase 启用安全套接层(Secure Sockets Layer,SSL)协议
    MAIL_USERNAME None 邮件账户的用户名
    MAIL_PASSWORD None 邮件账户的密码
    MAIL_DEFAULT_SENDER None 默认发件人,如果Message对象里没指定发件人,就采用默认发件人
    MAIL_MAX_EMAILS None 邮件批量发送个数上限,默认为没有上限
    MAIL_SUPPRESS_SEND app.testing 调用“Mail.send()”方法后,邮件不会真的被发送,在测试环境中使用,默认为False
    MAIL_ASCII_ATTACHMENTS Flase 将附件的文件名强制转换为ASCII字符,避免在某些情况下出现乱码

    3.2 常见的SMTP邮箱服务配置

    (1)配置QQ邮箱服务器

    MAIL_SERVER = 'smtp.qq.com',
    MAIL_PROT = 25,
    MAIL_USE_TLS = True,
    MAIL_USE_SSL = False,
    MAIL_USERNAME = "",
    MAIL_PASSWORD = "",
    

    QQ邮箱的配置方式如下:

     开启了授权之后,就会弹出生成授权码页面:

     注意:

    a.qq邮箱的服务器地址为smtp.qq.com;

    b.邮箱服务的端口为25或者465都可以;

    c.TLS,SSL的选择很多人发不出去邮件的关键之一,这里QQ邮箱选择TLS;

    d.账号和密码需要特别注意,这里的账号是自己的QQ邮箱账号,密码不是QQ邮箱密码,而是生成的授权码

    (2)其他邮箱后续补充

    4. 简单功能实现

    下面举例说明flask-email扩展是如何实现简单邮件发送的:

    from flask import Flask
    from flask_mail import Mail, Message
    app = Flask(__name__) app.config.update( MAIL_SERVER='smtp.qq.com', MAIL_PROT=465, MAIL_USE_TLS=True, MAIL_USE_SSL=False, MAIL_USERNAME="xxxxxxxxxxxxx@qq.com", MAIL_PASSWORD="****************", ) mail = Mail(app) @app.route('/') def index(): # sender 发送方,recipients 邮件接收方列表 msg = Message("Hi!This is a test ",sender='xxxxxxxxxxxxxx@qq.com', recipients=['test@example.com']) # msg.body 邮件正文 msg.body = "This is a first email" mail.send(msg) print("Mail sent") return 'send successfully'
    if __name__ == "__main__": app.run(debug=True)

     如果想发送信息,首先需要创建一个Message实例:

    msg = Message("Hello",sender="from@example.com",recipients=["to@example.com"])

    当然,我们也可以单独添加邮件接收对象:

    msg.recipients = ["you@example.com"]
    msg.add_recipient("somebodyelse@example.com")

    在配置参数的时候,如果我们设置了MAIL_DEFAULT_SENDER参数,在后面创建message实例时不需要清楚指明邮件发送方,此时程序会自动获取默认配置:

    msg = Message("Hello",recipients=["to@example.com"])
    

    5.异步发送邮件

    使用上面的方式发送邮件,会发现页面卡顿了几秒才出现消息,这是因为我们使用了同步的方式。为了避免发送邮件过程中出现的延迟,我们把发送邮件的任务移到后台线程中。代码如下:

    # -*- coding:utf-8 -*-
    
    from flask import Flask
    from flask_mail import Mail, Message
    from threading import Thread
    import os
    
    app = Flask(__name__)
    
    app.config['MAIL_SERVER'] = 'smtp.qq.com'
    app.config['MAIL_PORT'] = 25
    app.config['MAIL_USE_TLS'] = True
    app.config['MAIL_USERNAME'] = os.environ.get('MAIL_USERNAME') or 'xxxxxxxxxx@qq.com'
    app.config['MAIL_PASSWORD'] = os.environ.get('MAIL_PASSWORD') or '*********'
    
    mail = Mail(app)
    
    def send_async_email(app, msg):
        with app.app_context():
            mail.send(msg)
    
    @app.route('/sync')
    def send_email():
        msg = Message('Hi', sender='xxxxxxxx@qq.com', recipients=['test@example.com'])
        msg.html = '<b>send email asynchronously</b>'
    
        thr = Thread(target=send_async_email, args=[app, msg])
        thr.start()
        return 'send successfully'
    
    if __name__ == '__main__':
        app.run(debug=True)

     在上面,我们创建了一个线程,执行的任务是send_async_email,该任务的实现涉及一个问题:

    很多 Flask 扩展都假设已经存在激活的程序上下文和请求上下文。Flask-Mail 中的 send() 函数使用 current_app,因此必须激活程序上下文。不过,在不同线程中执行 mail.send() 函数时,程序上下文要使用 app.app_context()人工创建。

    6.带附件的邮件

    有时候,我们发邮件的时候需要添加附件,比如文档和图片等,这也很简单,代码如下:

    # -*- coding: utf-8 -*-
    
    from flask import Flask
    from flask_mail import Mail, Message
    import os
    
    app = Flask(__name__)
    
    app.config['MAIL_SERVER'] = 'smtp.qq.com'
    app.config['MAIL_PORT'] = 25
    app.config['MAIL_USE_TLS'] = True
    app.config['MAIL_USERNAME'] = os.environ.get('MAIL_USERNAME') or 'xxxxxxxxx@qq.com'
    app.config['MAIL_PASSWORD'] = os.environ.get('MAIL_PASSWORD') or '**********'
    
    mail = Mail(app)
    
    @app.route('/attach')
    def add_attchments():
        msg = Message('A photo', sender='xxxxxxxxx@qq.com', recipients=['ltest@example.com'])
        msg.html = '<b>A beautiful photo!</b>'
    
        with app.open_resource("1111.jpg") as fp:
            msg.attach("photo.jpg", "image/jpeg", fp.read())
    
        mail.send(msg)
        return '<h1>OK!</h1>'
    
    if __name__ == '__main__':
        app.run(debug=True)

    上面的代码中,我们通过 app.open_resource(path_of_attachment) 打开了本机的某张图片,然后通过msg.attach() 方法将附件内容添加到 Message 对象。msg.attach() 方法的第一个参数是附件的文件名,第二个参数是文件内容的 MIME (Multipurpose Internet Mail Extensions) 类型,第三个参数是文件内容。

    7.批量发送

    在某些情况下,我们需要批量发送邮件,比如给网站的所有注册用户发送改密码的邮件,这时为了避免每次发邮件时都要创建和关闭跟服务器的连接,我们的代码需要做一些调整,类似如下:

    with mail.connect() as conn:
        for user in users:
            subject = "hello, %s" % user.name
            msg = Message(recipients=[user.email], body='...', subject=subject)
            conn.send(msg)

    上面的工作方式,使得应用与电子邮件服务器保持连接,一直到所有邮件已经发送完毕。某些邮件服务器会限制一次连接中的发送邮件的上限,这样的话,你可以配置 MAIL_MAX_EMAILS

  • 相关阅读:
    常用正则
    css换行与不换
    数组Array.prototype方法的使用
    你真的知道css三种存在样式(外联样式、内部样式、内联样式)的区别吗?
    js中批量处理样式——cssText的使用
    CSS的定位属性实现text-shadow属性的文本下产生阴影效果
    深入js的面向对象学习篇(继承篇)——温故知新(三)
    深入js的面向对象学习篇(封装是一门技术和艺术)——温故知新(二)
    深入js的面向对象学习篇——温故知新(一)
    【转链接】Handlebars模板引擎以及浅谈模板引擎的实现原理
  • 原文地址:https://www.cnblogs.com/bdhk/p/7571507.html
Copyright © 2011-2022 走看看