You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

Django邮件发送失败:报错smtplib.SMTPServerDisconnected连接意外关闭

解决Django+SendGrid发送邮件报SMTP连接意外关闭的问题

我之前在配置Django+SendGrid发邮件时也碰到过一模一样的报错,给你几个实测有效的排查和解决方向:

  • 修正身份验证配置(最常见的坑)
    SendGrid的SMTP服务现在要求用API密钥进行验证,而不是你的账号用户名。你当前的EMAIL_HOST_USER = 'myusername'是错误的,必须改成:

    EMAIL_HOST_USER = 'apikey'  # 固定值,不要修改
    EMAIL_HOST_PASSWORD = '你的SendGrid完整API密钥'  # 不是账号登录密码,是后台生成的专属API密钥
    

    另外要确保这个API密钥在SendGrid后台创建时,勾选了Mail Send的权限,没有对应权限也会被服务器拒绝连接。

  • 调整端口与加密方式
    虽然465+SSL是合法配置,但部分服务器或防火墙会拦截这个端口的连接。可以尝试切换到兼容性更好的587端口+TLS加密,修改settings.py:

    EMAIL_PORT = 587
    EMAIL_USE_TLS = True
    EMAIL_USE_SSL = False
    
  • 验证发件人邮箱/域名
    SendGrid要求发件人邮箱必须是已验证的(要么验证整个域名,要么验证单个邮箱地址)。你测试时用的send_mail第三个参数是'email@email.com',但你的DEFAULT_FROM_EMAIL'admin@mysite.com',如果前者没在SendGrid后台验证过,就会触发连接拦截。建议改成使用已验证的发件人:

    from django.conf import settings
    send_mail('test','test', settings.DEFAULT_FROM_EMAIL, ['to@email.com'])
    
  • 排查网络连通性
    可能是本地/服务器的防火墙、代理拦截了SMTP端口。可以用telnet命令测试连通性:

    # 测试465端口
    telnet smtp.sendgrid.net 465
    # 测试587端口
    telnet smtp.sendgrid.net 587
    

    如果连接失败,需要联系运维开放对应端口,或者考虑改用SendGrid API后端。

  • 改用SendGrid API后端(可选)
    如果你不想折腾SMTP的连接问题,可以直接用SendGrid提供的Django后端,绕过SMTP协议:

    1. 安装依赖包:pip install django-sendgrid-v5
    2. 修改settings.py:
      EMAIL_BACKEND = 'sendgrid_backend.SendgridBackend'
      SENDGRID_API_KEY = '你的SendGrid API密钥'
      DEFAULT_FROM_EMAIL = 'admin@mysite.com'
      

    这种方式更稳定,还能直接使用SendGrid的高级邮件功能。

内容的提问来源于stack exchange,提问作者Zorgan

火山引擎 最新活动