Django触发500错误时未向管理员发送邮件问题排查
首先,你提到通过Python shell调用send_mail()能正常发邮件,说明你的邮件基础配置是没问题的。核心问题出在日志配置上——你的当前LOGGING设置里只配置了文件日志handler,完全没有设置用于发送管理员邮件的AdminEmailHandler,所以Django不会在触发500错误时自动发送告警邮件。
修正日志配置
你需要在LOGGING的handlers里添加AdminEmailHandler,并把它关联到对应的logger上。修改后的配置大概是这样:
import os from django.conf import settings LOGGING = { 'version': 1, 'disable_existing_loggers': False, 'handlers': { 'file': { 'level': 'WARNING', 'class': 'logging.FileHandler', 'filename': os.path.join(settings.BASE_DIR, 'debug.log'), }, # 添加邮件handler 'mail_admins': { 'level': 'ERROR', 'class': 'django.utils.log.AdminEmailHandler', # 可选:开启后会发送包含栈追踪的HTML格式邮件 'include_html': True, }, }, 'loggers': { 'django': { 'handlers': ['file', 'mail_admins'], # 关联邮件handler到全局django logger 'level': 'WARNING', 'propagate': True, }, # 单独针对请求相关错误配置,确保500错误被精准捕获 'django.request': { 'handlers': ['mail_admins'], 'level': 'ERROR', 'propagate': False, }, }, }
这里重点说明:
django.request这个logger专门负责处理请求生命周期内的错误(包括500服务器错误),单独给它配置mail_adminshandler,能确保这类错误被优先捕获并发送邮件。AdminEmailHandler的默认级别是ERROR,刚好匹配500错误的日志级别,不需要额外调整。
关于ADMINS设置的几个疑问解答
1. ADMINS里的“全名”是否来自默认User模型?
完全不是!ADMINS是独立于User模型的配置项,它只是一个元组列表,每个元组的格式是(显示名称, 邮箱地址)——这里的“全名”只是邮件收件人看到的发件人显示名称,比如你设置('运维管理员', 'admin@example.com'),对方收到邮件时就会显示这个名称,和数据库里的User模型字段没有任何关联。
2. 如果“全名”字段为空会有什么影响?
如果你写成('', 'myemail@gmail.com')或者(None, 'myemail@gmail.com'),邮件依然能正常发送,只是收件人看到的发件人名称会是空,或者自动显示为你的DEFAULT_FROM_EMAIL对应的邮箱名称,完全不会影响邮件的投递功能。
3. 存在同名管理员会有问题吗?
完全没问题!ADMINS里的名称仅用于显示,Django不会对这个字段做唯一性校验或者逻辑判断。哪怕你添加多个('管理员', 'admin1@example.com')和('管理员', 'admin2@example.com'),这两个邮箱都会正常收到告警邮件,彼此之间没有任何冲突。
最后提醒:修改完日志配置后,记得重启你的Django服务确保配置生效。你可以手动触发一个500错误(比如在视图里写raise Exception('测试500错误')),测试是否能收到邮件。
内容的提问来源于stack exchange,提问作者Chiefir




