使用PHPMailer批量发送队列邮件时触发ERR_TOO_MANY_REDIRECTS错误如何解决
报错核心原因
当前脚本采用每批50封发送完成后,通过header('Location: 脚本自身路径')触发浏览器302重定向,反复请求自身遍历全队列的设计。该机制存在必然触发报错的硬伤:
- Chrome对同一地址的连续重定向有固定次数上限(约20次),当队列总规模超过1000封(20次*50封/批),必然弹出
ERR_TOO_MANY_REDIRECTS错误 - 脚本在执行跳转逻辑前,会通过
echo输出发送日志、队列统计值,这些提前输出的内容会导致PHP无法正常发送302重定向头,进一步加剧循环报错 - 队列计数的SQL查询未过滤
do_not_send_before条件,只要存在未到发送时间的queued状态记录,就会出现「当前批次无有效可发邮件,但计数显示仍有队列」的异常,形成无意义的反复重定向
修复方案
- 从根源替换浏览器重定向循环的实现逻辑:将发送脚本改为后台CLI运行模式,通过服务器定时任务每1-2分钟调用一次脚本,每次跑完当前批次直接退出执行,完全不触发页面跳转,从设计上消除重定向报错的可能
- 若受服务器权限限制无法配置定时任务,可对原有逻辑做最小成本改造:
- 移除所有基于
header()的302重定向,批次处理完成后输出一段自动触发下一次脚本请求的前端JS,同时在跳转链接中追加已处理批次的计数参数,达到预设最大跳转次数后直接跳转到完成页,不再继续请求发送脚本 - 调整代码执行顺序,将所有
echo输出内容放到header()跳转命令之后,避免提前输出的内容干扰HTTP头正常发送 - 修正队列计数的SQL语句,补充
do_not_send_before < 当前时间戳的过滤条件,避免无效循环触发 - 发送流程因单封邮件发送失败触发
break中断时,直接终止后续的队列查询、跳转逻辑,避免中断后仍反复触发脚本请求
- 移除所有基于
内容的提问来源于stack exchange,提问作者Samuel Parrino
相关产品推荐
相关产品推荐

