【问题标题】:Best approach for PHP mass-mailing routine?PHP群发邮件例程的最佳方法?
【发布时间】:2021-02-28 00:43:26
【问题描述】:

我正在创建一个网站,每天向大约 800 位用户发送新闻电子邮件,他们可以指定时间。我的问题是我的脚本需要很长时间才能运行并且超时,所以我正在寻找一些关于如何更好地解决这个问题的建议。

目前的做法:

用户被放置在一个“邮件队列”数据库表中,其中包含他们的 ID、接收时间和发送标志。

然后我每分钟运行一个 CRON 脚本,它执行以下操作:

  1. 从邮件队列中获取所有“接收时间”小于或等于现在但尚未发送的邮件
  2. 遍历用户,加入偏好表以获取他们选择的类别(每个用户最多约 30 个)。
  3. 对于每个类别,查找最新的 3 篇文章
  4. 使用 PHPMailer 准备包含此内容的 HTML 电子邮件
  5. PHPMailer 正在使用 Mailgun SMTP 来避免我的 SMTP 服务器过载
  6. 向用户发送邮件,在数据库中标记为已发送

我目前的观察结果是:

  1. 在通过在浏览器中运行来测试脚本时,它运行速度非常慢,会持续几分钟然后超时(不发送任何电子邮件)。
  2. 当通过 CRON 每分钟运行一次时,它会在 40 分钟内发送超过电子邮件数量(大约 1400 封),我猜是因为脚本自身重叠并且发送的标志没有可靠地更新。

大多数用户都设置为同时接收他们的电子邮件,所以我在此基础上进行“最坏情况”测试

问题

  1. 我的脚本是否过于繁重,通过查询数据库并为每个用户即时生成 HTML 电子邮件内容?我想知道提前生成内容并将用户存储在邮件队列中是否会更好。
  2. 像 Beanstalkd 这样的队列管理器会有所帮助吗?我已经对其进行了研究,但正在努力了解如何在我的日常工作中实施。

最终,我需要在每个用户期望的时间可靠地发送电子邮件。

非常感谢任何建议!

【问题讨论】:

    标签: php phpmailer mailgun mass-emails


    【解决方案1】:

    可以在 PHP 中执行此操作,但您可能不应该这样做。当有更好的方法可以做到这一点时,您正在尝试构建邮件服务器,主要涉及使用邮件服务器。

    在页面加载期间发送大量电子邮件是不可行的——即使是单个消息也可能很麻烦,但许多人仍在尝试。像这样接近它:

    • 将您的列表存储在数据库中。
    • 当您要发送时,生成一个记录,表示要发送的每条消息(本质上是列表的副本)。
    • 拥有一个以块的形式发送消息的守护进程(一个长时间运行的任务)或 cron 作业。
    • 一次创建一封邮件并将其提交到本地邮件服务器。
    • 使用 DKIM 签名。
    • 在发送每条消息时,在数据库中将它们标记为已发送,但您需要非常清楚数据库事务和锁是如何工作的,这样才能安全地工作并避免重复 - 正确执行此操作,重叠的进程就可以正常工作。
    • 您可以随心所欲地生成邮件,您的邮件服务器将处理排队、转发、重试和退回邮件。
    • 使用VERP addressing,并将退回邮件输入退回处理程序(请注意,编写这些内容并不好玩!),并防止将来发送到退回地址。

    这种方法效果很好——这正是我自己的系统([Smartmessages.net](https://info.smartmessages.net/,内置于 PHP)的工作方式,我可以使用多个并行运行的消息生成器每秒维持超过 200 条消息(数据库事务 FTW!)。

    如果您觉得这一切有点太多(这非常困难),您可能最好使用商业发送服务(如我自己的)或托管 DIY 解决方案,如我的好朋友的Mailcoach在斯派蒂。其中任何一个都可以很好地工作,而且您的列表非常小 - 我经常处理超过 100,000 个的列表。

    【讨论】:

    • 非常感谢您的建议。理想情况下,我想坚持目前的路线,因为我正在重建一个已经实现我想要做的事情的系统,但无法从代码库中确定如何!同意从单个脚本发送注定要失败。也许作业/队列管理器路线会是一个很好的路线。
    猜你喜欢
    • 2010-12-20
    • 2011-10-02
    • 2012-10-06
    • 2011-07-08
    • 1970-01-01
    • 2012-09-20
    • 2010-11-14
    • 2019-02-04
    • 1970-01-01
    相关资源
    最近更新 更多