060. 编写一个函数,实现简单的SMTP邮件发送功能

在 Python 中,可以使用 smtplib 模块来实现简单的 SMTP 邮件发送功能。以下是一个示例代码,展示如何编写一个函数来发送邮件。

示例代码

import smtplib
from email.mime.text import MIMEText
from email.mime.multipart import MIMEMultipart
from email.header import Header

def send_email(smtp_server, port, sender_email, sender_password, recipient_email, subject, body):
    """
    发送邮件的函数

    :param smtp_server: SMTP 服务器地址
    :param port: SMTP 服务器端口(通常为 587 或 465)
    :param sender_email: 发件人邮箱地址
    :param sender_password: 发件人邮箱密码
    :param recipient_email: 收件人邮箱地址
    :param subject: 邮件主题
    :param body: 邮件正文
    """
    # 创建 MIMEText 对象,_text 是邮件内容,_subtype 是主内容类型,_charset 是编码
    message = MIMEText(body, 'plain', 'utf-8')
    message['From'] = Header(sender_email, 'utf-8')  # 显示的发件人
    message['To'] = Header(recipient_email, 'utf-8')  # 显示的收件人
    message['Subject'] = Header(subject, 'utf-8')  # 显示的邮件主题

    try:
        # 根据端口号选择连接方式
        if port == 465:
            # 使用 SSL 连接
            server = smtplib.SMTP_SSL(smtp_server, port)
        else:
            # 使用普通连接
            server = smtplib.SMTP(smtp_server, port)
            server.starttls()  # 启用安全传输模式

        # 登录 SMTP 服务器
        server.login(sender_email, sender_password)

        # 发送邮件
        server.sendmail(sender_email, [recipient_email], message.as_string())

        print("邮件发送成功!")
    except smtplib.SMTPException as e:
        print(f"邮件发送失败:{e}")
    finally:
        # 关闭连接
        server.quit()

# 示例用法
if __name__ == "__main__":
    smtp_server = "smtp.example.com"  # 替换为你的 SMTP 服务器地址
    port = 587  # 替换为你的 SMTP 服务器端口
    sender_email = "your_email@example.com"  # 替换为你的邮箱地址
    sender_password = "your_password"  # 替换为你的邮箱密码
    recipient_email = "recipient@example.com"  # 替换为收件人邮箱地址
    subject = "测试邮件"
    body = "这是一封测试邮件,由 Python 发送。"

    send_email(smtp_server, port, sender_email, sender_password, recipient_email, subject, body)

代码说明

邮件内容

  • 使用 email.mime.text.MIMEText 创建邮件正文。

  • 使用 email.mime.multipart.MIMEMultipart 可以创建包含附件的邮件(如果需要)。

  • 使用 email.header.Header 设置邮件主题和发件人、收件人信息,确保邮件主题和地址可以正确显示中文。

SMTP 连接

  • 根据端口号选择连接方式:

  • 使用 smtplib.SMTP_SSL 连接到 465 端口(SSL 连接)。

  • 使用 smtplib.SMTP 连接到其他端口(如 587),并通过 starttls() 启用安全传输模式。

  • 使用 server.login() 登录 SMTP 服务器。

  • 使用 server.sendmail() 发送邮件。

异常处理:使用 try-except 捕获 smtplib.SMTPException,处理邮件发送过程中可能出现的异常。

关闭连接:使用 server.quit() 关闭 SMTP 连接。

注意事项

SMTP 服务器和端口

  • 不同的邮箱服务提供商有不同的 SMTP 服务器地址和端口。例如:

  • Gmailsmtp.gmail.com,端口 587 或 465。

  • Outlooksmtp.office365.com,端口 587。

  • QQ 邮箱smtp.qq.com,端口 465 或 587。

  • 确保你已经开启了邮箱的 SMTP 功能,并获取了正确的授权码(某些邮箱需要单独设置)。

安全性:在实际应用中,建议不要在代码中直接写明邮箱密码,可以使用环境变量或配置文件来存储敏感信息。

邮件内容:如果需要发送 HTML 格式的邮件,可以将 MIMEText_subtype 参数设置为 'html'

附件:如果需要发送带附件的邮件,可以使用 email.mime.multipart.MIMEMultipartemail.mime.application.MIMEApplication 来添加附件。

示例:发送带附件的邮件

如果需要发送带附件的邮件,可以参考以下代码:

from email.mime.application import MIMEApplication

def send_email_with_attachment(smtp_server, port, sender_email, sender_password, recipient_email, subject, body, attachment_path):
    """
    发送带附件的邮件
    """
    # 创建 MIMEMultipart 对象
    message = MIMEMultipart()
    message['From'] = Header(sender_email, 'utf-8')
    message['To'] = Header(recipient_email, 'utf-8')
    message['Subject'] = Header(subject, 'utf-8')

    # 添加邮件正文
    message.attach(MIMEText(body, 'plain', 'utf-8'))

    # 添加附件
    with open(attachment_path, 'rb') as f:
        attachment = MIMEApplication(f.read(), Name=attachment_path.split('/')[-1])
        attachment['Content-Disposition'] = f'attachment; filename="{attachment_path.split("/")[-1]}"'
        message.attach(attachment)

    try:
        if port == 465:
            server = smtplib.SMTP_SSL(smtp_server, port)
        else:
            server = smtplib.SMTP(smtp_server, port)
            server.starttls()

        server.login(sender_email, sender_password)
        server.sendmail(sender_email, [recipient_email], message.as_string())
        print("带附件的邮件发送成功!")
    except smtplib.SMTPException as e:
        print(f"邮件发送失败:{e}")
    finally:
        server.quit()

# 示例用法
if __name__ == "__main__":
    smtp_server = "smtp.example.com"
    port = 587
    sender_email = "your_email@example.com"
    sender_password = "your_password"
    recipient_email = "recipient@example.com"
    subject = "测试邮件(带附件)"
    body = "这是一封带附件的测试邮件。"
    attachment_path = "example.txt"  # 替换为附件路径

    send_email_with_attachment(smtp_server, port, sender_email, sender_password, recipient_email, subject, body, attachment_path)

视频讲解

BiliBili: 视睿网络-哔哩哔哩视频 (bilibili.com)