29

这是我的场景:

我有 2 个电子邮件帐户:admin@domain.com 和bounce@domain.com。

我想用 admin@domain.com 向我的所有用户发送电子邮件,然后“回复”bounce@domain.com(直到这里,我的 PHP 脚本可以处理它)。

当邮件无法发送时,它被发送到bounce@domain.com,错误信息可能是553(不存在的电子邮件......)等。

我的问题是:如何通过处理脚本将所有这些退回电子邮件(无法发送的电子邮件)定向到bounce@domain.com 以检查退回错误代码?

我应该为“处理脚本”使用什么编程语言?

“处理脚本”会是什么样子?能给个样品吗?

换句话说:

我应该遵循哪些程序来处理退回电子邮件?

4

14 回答 14

29

最好的方案是能够对反弹的类型进行分类:软、硬……

我们使用的是BounceStudio。您需要编译它并添加 php 库......一点也不难。您拥有该产品的免费和付费版本

一旦我们检测到退回的类型,我们使用 PEAR::MAIL::MIME 来搜索我们之前添加到电子邮件中的自定义标题,让我们说:

X-user-id: XXXXX
X-campaign-id: YYYYYY 
X-recipient-id: SSSSSSSSS

通过这种方式,我们可以知道我们发送电子邮件的真实收件人。

希望这对你有帮助!所以你可以帮助我达到 500 分:P

于 2009-06-18T14:36:23.613 回答
7

为什么不创建一个bounce@domain.com 并使用php 来阅读这些电子邮件并做任何你想做的事?

在您发表评论后编辑:请检查我的链接,其中有一个 php 脚本,它将教您如何使用 php 打开和电子邮件箱并阅读电子邮件。您可以使用此脚本来检查错误消息。

于 2009-06-18T09:39:41.823 回答
5

让电子邮件退回到真正是电子邮件地址的地址(带有登录详细信息等)。

制作一个每 x 分钟运行一次的 php 脚本(例如使用 cron 作业)。此 php 脚本必须执行以下操作。- 从框中检索所有电子邮件(例如使用Zend Mail) - 检查消息中的错误(例如,通过使用正则表达式搜索它) - 做任何必要的事情。

如果您想具体了解谁被退回,您可以使用用户特定的退回地址。(例如参见本网站

于 2009-06-18T10:58:40.013 回答
4

也许答案有点晚了,但你总是可以尝试一些新的东西。上周我有一个这样的任务,并使用了 Chris Fortune 编写的 BOUNCE HANDLER 类,它将反弹分割成关联数组 - http://www.phpclasses.org/browse/file/11665.html

这将在您使用某些邮件程序连接到 POP3 以从中获取退回邮件后使用,然后将其解析为碎片,如果具有您搜索的状态,请执行必要的操作。

干杯。

于 2010-11-16T11:10:09.203 回答
2

如果您设置了 POP3 邮箱bounce@domain.com,您可以使用 PHP 编写的 POP3 客户端脚本来检索邮件并检查无法投递的邮件。

于 2009-06-18T09:41:19.247 回答
1

您可以使用imap_open从 PHP 访问您的邮件。

此功能也适用于 POP3,但并非每个功能都可以在这里使用。不过我猜 2018 年大多数电子邮件客户端应该支持 IMAP。

此功能也可用于向 POP3 和 NNTP 服务器打开流,但某些功能和特性仅在 IMAP 服务器上可用。

这是一个小例子,如何遍历您的电子邮件:

  /* connect to server */
  $hostname = "{$your-server:$your-port}INBOX";
  $username = 'my-username';
  $password = '123';

  /* try to connect */
  $inbox = imap_open($hostname,$username,$password) or die('Cannot connect to mailbox: ' . imap_last_error());

  /* grab emails */
  $emails = imap_search($inbox,'ALL');

  /* if emails are returned, cycle through each... */
  if($emails) {
    /* for every email... */
    foreach($emails as $email_number) {

        $message = imap_body($inbox,$email_number,2);
        $head    = imap_headerinfo($inbox, $email_number,2);
        // Here you can handle your emails
        // ...
        //  ...
      }
  }

就我而言,我知道我总是从Mailer-Daemon@myserver.com. 所以我可以识别出这样的反弹:

if($head->from[0]->mailbox == 'Mailer-Daemon')
{
  // We have a bounce mail here!
}

你说:

当邮件无法发送时,它被发送到bounce@domain.com,错误信息可能是553(不存在的电子邮件......)等。

因此,如果您的退回电子邮件的主题为“邮件传递失败:错误 553”,那么您可以通过主题来识别它们,如下所示:

if($head->subject == 'Mail delivery failed: Error 553')
{
  // We have a bounce mail here!
}

失败的电子邮件地址不在标头中,因此您需要$message使用一些智能代码从变量中解析它。

于 2018-09-17T11:26:30.287 回答
0

我正在寻找同一个问题的答案。问题的部分更多,选项也更多。

为了处理退回的电子邮件,我找到了一个PHP 类,如果您有一个 PHP 支持的站点,则不需要编译或额外的软件安装。这是非常容易使用。

如果您使用 cPanel 或 InterWorx/SiteWorx,您可以配置一些地址以使用脚本(例如 PHP 脚本)处理接收到的电子邮件,这样您就可以借助上述类编写自己的处理程序。当然,您也可以创建普通的电子邮件帐户,通过 POP3 或 IMAP 检索邮件,然后对其进行解释。我认为第一个更好,因为它是直接的,您不必使用其他渠道,例如 IMAP。当然如果你不能配置你的邮件服务器,或者不知道怎么做,那么前者更适合你。

祝你好运!:)

于 2011-11-16T16:02:25.097 回答
0

您始终可以使用http://cloudmailin.com之类的东西通过 http 将退回的电子邮件转发到您的 php 服务器,但是使用专门用于发送电子邮件并使用其 api 检索退回详细信息的服务可能会更好。

于 2011-03-23T11:36:20.950 回答
0

在 php 邮件命令http://php.net/mail

您使用第五个参数并向其添加“-f”。

因此,您使用“-f mybouncebox@mydomain.com”作为参数

phpList通讯管理器使用它来管理退回邮件。

一旦退回邮件填满邮箱,您就可以将它们弹出并处理它们。这是处理它们的最简单方法,而不是在它们到达时处理它们。

于 2012-02-08T04:10:22.970 回答
0

We are using Procmail to filter these kind of mails. After examining some of the solutions already mentioned here, we ended up with a simple Procmail recipe to detect bounce messages. Depending on the accuracy you need, this might be applicable to your situation.

For details, check this blog entry.

于 2013-12-16T11:19:47.110 回答
0

我在为此寻找 PHP 解决方案时运气不佳,但是我遇到了这个产品,它可以满足我的需要。

它作为本机应用程序 mac/win 运行,但它可以完成这项工作。

http://www.maxprog.com/site/software/internet-marketing/email-bounce-handler_sheet_us.php

于 2011-08-29T00:33:48.147 回答
0

这是使用 IMAP 处理退回邮件的固定解决方案。

我将 Mail 实例的 Return-Path 标头更改为专用的bounce@xxxxxx.us

我认为可行的唯一简单方法是以下方法,它通过 POP3 检查专用收件箱,并可以根据收到的消息处理每封电子邮件。

$inst=pop3_login('mail.xxxxxx.us','110','bounce@xxxxxx.us','pass');
$stat=pop3_stat($inst);
//print_r($stat);
if($stat['Unread']>0){
    echo "begin process<br><br>";
    $list=pop3_list($inst);
    //print_r($list);
    foreach($list as $row){
        if(strpos($row['from'],'MAILER-DAEMON')!==FALSE){
            $msg=imap_fetchbody($inst,$row['msgno'],'1');
            if(strpos($msg,'550')!==FALSE){
                echo "handle hard bounce".$msg."<br><br>";
                //WHATEVER HERE TO PROCESS BOUNCE
            }   
        }
        else{
            $msg=imap_fetchbody($inst,$row['msgno'],'1');
            echo "not from my server. could be spam, etc.".$msg."<br><br>";
            //PROBABLY NO ACTION IS NEEDED
        }   
        //AFTER PROCESSING
        //imap_delete ( resource $imap_stream , int $msg_number [, int $options = 0 ] )
        //commented out because I havent implemented yet. see IMAP documentation
    }   
}   
else{
    echo "no unread messages";  
}


//imap_close ( resource $imap_stream [, int $flag = 0 ] )
//commented out because I havent implemented yet. see IMAP documentation.
//flag: If set to CL_EXPUNGE, the function will silently expunge the mailbox before closing, removing all messages marked for deletion. You can achieve the same thing by using imap_expunge()




function pop3_login($host,$port,$user,$pass,$folder="INBOX",$ssl=false) 
{ 
    $ssl=($ssl==false)?"/novalidate-cert":""; 
    return (imap_open("{"."$host:$port/pop3$ssl"."}$folder",$user,$pass)); 
} 
function pop3_stat($connection)        
{ 
    $check = imap_mailboxmsginfo($connection); 
    return ((array)$check); 
} 
function pop3_list($connection,$message="") 
{ 
    if ($message) 
    { 
        $range=$message; 
    } else { 
        $MC = imap_check($connection); 
        $range = "1:".$MC->Nmsgs; 
    } 
    $response = imap_fetch_overview($connection,$range); 
    foreach ($response as $msg) $result[$msg->msgno]=(array)$msg; 
        return $result; 
} 
function pop3_retr($connection,$message) 
{ 
    return(imap_fetchheader($connection,$message,FT_PREFETCHTEXT)); 
} 
function pop3_dele($connection,$message) 
{ 
    return(imap_delete($connection,$message)); 
} 
于 2012-10-31T06:41:50.670 回答
0

我有同样的问题,确切的情况。默认情况下,我的邮件服务器会将我所有返回的邮件发送到最初发送邮件的同一帐户,并自动发送 msg "Mail delivery failed: returned message to sender"

我真的不想知道它为什么被退回,有这么多邮件交易,我只想删除坏的。没有时间检查特定规则,例如是否存在,不可用等,,,只想标记删除并继续。

退回邮件非常简单,因为您需要处理许多不同的服务器和响应类型。每个反垃圾邮件软件或操作系统方案都可以通过退回的电子邮件发送不同的错误代码。

如果您想设置 IMAP ,我建议您阅读并下载处理退回电子邮件的固定调试版本- 使用来自 KIDMOSES的 PHPMAILER-BMH 和 AUTHSMTP http://www.kidmoses.com/blog-article.php?bid=40并发送您自己的自定义标头,将它们发送到您的bounce@domain.com,然后交叉手指查看脚本是否捕获了您在退回邮件中发送的标头。我试过了,有效。

但是,如果您想按照我的快速简便的解决方案解决我的问题,这里就是秘密。

1 - 从 KIDMOSES 网站或我的网站下载更好的版本,以防 KIDMOSES 想搬到其他地方http://chasqui.market/downloads/KIDMOSES-phpmailer-bmh.zip

2 - 包含返回邮件文本的变量是 $body ,它本身包含错误的返回电子邮件(所以它是一个多维数组)。(还包含您的服务器邮件和其他 DNS 邮件内容,但我们正在寻找 BAD MAIL BOUNCED。

3 - 由于您的 OWN SERVICE 正在向您发送退回的电子邮件,因此它不太可能更改其格式和自己的标题,发送退回的电子邮件,因此您可以安全地选择退回的电子邮件数组返回的顺序。在我的情况下,总是相同的格式模板。(除非您更改系统或提供商)

4 - 我们查看$body并搜索所有电子邮件字符串变量并将它们提取到一个名为 $matches的二维数组中

5 - 我们通过使用print_r(array_values($matches))打印数组来选择数组位置;

6 - 这是您需要修改的代码。它来自class.phpmailer-bmh.php文件的第 500 行左右

  // process bounces by rules
  $result = bmhDSNRules($dsn_msg,$dsn_report,$this->debug_dsn_rule);
} elseif ($type == 'BODY') {
  $structure = imap_fetchstructure($this->_mailbox_link,$pos);
  switch ($structure->type) {
    case 0: // Content-type = text
      $body = imap_fetchbody($this->_mailbox_link,$pos,"1");
      $result = bmhBodyRules($body,$structure,$this->debug_body_rule);

      //MY RULE IT WORKS at least on my return mail system..
      $pattern = '/[a-z0-9_\-\+]+@[a-z0-9\-]+\.([a-z]{2,3})(?:\.[a-z]{2})?/i';
      preg_match_all($pattern, $body, $matches);
        //print_r( array_values( $matches ));     //To select array number of bad returned mail desired, usually is 1st array $matches[0][0]          
        echo "<font color = red>".$matches[0][0]."</font><br>";
      break;

因此,我们忘记了返回的标头并专注于糟糕的电子邮件。你可以超越它们,你可以使用 MySQL,或者处理任何你想做的事情。

重要 注释在示例目录中的 callback_echo.php 中的回声,否则您会在打印之前得到所有垃圾。

function callbackAction ($msgnum, $bounce_type, $email, $subject,      $xheader, $cheader, $remove, $rule_no=false, $rule_cat=false, $rule_msg='', $totalFetched=0) {
  $displayData = prepData($email, $bounce_type, $remove);
  $bounce_type = $displayData['bounce_type'];
  $emailName   = $displayData['emailName'];
  $emailAddy   = $displayData['emailAddy'];
  $remove      = $displayData['remove'];
  //echo "<br>".$msgnum . ': '  . $rule_no . ' | '  . $rule_cat . ' | '  . $bounce_type . ' | '  . $remove . ' | ' . $email . ' | '  . $subject . ' | ';
  //echo 'Custom Header: '  . $cheader . " | ";
  //echo 'Bounce Message: '  . $rule_msg . " | ";
  return true;
}

我的输出

Connected to: mail.chasqui.market (bounce@chasqui.market)
Total: 271 messages 
Running in disable_delete mode, not deleting messages from mailbox

kty2001us@starmedia.com

...

entv@nuevoface.com

Closing mailbox, and purging messages
Read: 271 messages
0 action taken
271 no action taken
0 messages deleted
0 messages moved
于 2015-11-24T17:25:53.180 回答
-1

你应该看看 SwiftMailer。它完全用 PHP 编写,并且支持“退回”电子邮件。 http://swiftmailer.org/

于 2010-06-04T12:59:39.987 回答