PHP从字符串中提取电子邮件地址

时间:2019-01-23 17:52:07

标签: php

我正在使用PHP。

我有一串这样的文字:

mx.google.com;       dkim=pass header.i=@outlook.com header.s=selector1 header.b=OvtBcHsM;       spf=pass (google.com: domain of xxxx@outlook.com designates 12.12.12.12 as permitted sender) smtp.mailfrom=xxxx@outlook.com;       dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=outlook.com

我需要从中提取电子邮件地址(请记住,该电子邮件地址可以是一百万个不同的变体):

smtp.mailfrom=xxxx@outlook.com;

这样我就结束了:

xxxx@outlook.com;

这如何完成?谢谢!

4 个答案:

答案 0 :(得分:4)

使用双重爆炸查找电子邮件。

首先在"smtp.mailfrom="上爆炸,然后使用([1])之后的项目,然后在";"上爆炸,并将数组中的第一项用作$ email。

$str = "mx.google.com;       dkim=pass header.i=@outlook.com header.s=selector1 header.b=OvtBcHsM;       spf=pass (google.com: domain of xxxx@outlook.com designates 12.12.12.12 as permitted sender) smtp.mailfrom=xxxx@outlook.com;       dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=outlook.com";

$mail = explode(";",explode("smtp.mailfrom=", $str)[1])[0];

echo $mail;
//xxxx@outlook.com

https://3v4l.org/KGCVc

答案 1 :(得分:0)

我使您的示例使用以下正则表达式:

<?php

$str = 'mx.google.com;       dkim=pass header.i=@outlook.com header.s=selector1 header.b=OvtBcHsM;       spf=pass (google.com: domain of xxxx@outlook.com designates 12.12.12.12 as permitted sender) smtp.mailfrom=xxxx@outlook.com;       dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=outlook.com';

if (preg_match('/smtp\.mailfrom=(?<email>[a-zA-Z0-9.!#$%&\'*+\\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)+)/', $str, $matches)) {
    var_dump($matches['email']);
}

电子邮件的表达方式非常复杂,但我只是从Symfony的email validator中提取它:https://github.com/symfony/symfony/blob/master/src/Symfony/Component/Validator/Constraints/EmailValidator.php

答案 2 :(得分:0)

我想提供一种有关邮箱名称中带引号字符的算法(请参见RFC822)。

由于preg_是非默认扩展名,因此我使用mbstring函数来支持UTF-8兼容编码。

$str1 = 'mx.google.com;       dkim=pass header.i=@outlook.com header.s=selector1 header.b=OvtBcHsM;       spf=pass (google.com: domain of xxxx@outlook.com designates 12.12.12.12 as permitted sender) smtp.mailfrom=xxxx@outlook.com;       dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=outlook.com';
$str2 = 'mx.google.com;       dkim=pass header.i=@outlook.com header.s=selector1 header.b=OvtBcHsM;       spf=pass (google.com: domain of xx"@"yy";"zz@outlook.com designates 12.12.12.12 as permitted sender) smtp.mailfrom=xx"@"yy";"zz@outlook.com;       dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=outlook.com; xx=yyyy; aa=bb;cc=ddd';

foreach ([$str1, $str2] as $subj)
{
  echo $subj, PHP_EOL;

  // cut off begin of string up to 'smtp.mailfrom='
  $rpl = preg_replace('~^(?:.*?[^\w.-])?smtp.mailfrom=~us', '', $subj);

  // match found / removed?
  if($rpl !== $subj)
  {
    // split on semicolon without remove (lookahead)
    $splitted = preg_split('~(?=;)~us', $rpl);

    $s = '';  // string buffer
    $q = 1 ;  // number of quotes in buffer, mock 1 for 1st iteration

    // while $q is odd (unpaired quotes) and more chunks available, append to string
    while(($q & 1) && !empty($splitted))
    {
      $s .= array_splice($splitted, 0, 1)[0];
      $q = preg_match_all('~"~u', $s);
    }

    echo $s, PHP_EOL;
  }
}

输出:

mx.google.com;       dkim=pass header.i=@outlook.com header.s=selector1 header.b=OvtBcHsM;       spf=pass (google.com: domain of xxxx@outlook.com designates 12.12.12.12 as permitted sender) smtp.mailfrom=xxxx@outlook.com;       dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=outlook.com
xxxx@outlook.com
mx.google.com;       dkim=pass header.i=@outlook.com header.s=selector1 header.b=OvtBcHsM;       spf=pass (google.com: domain of xx"@"yy";"zz@outlook.com designates 12.12.12.12 as permitted sender) smtp.mailfrom=xx"@"yy";"zz@outlook.com;       dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=outlook.com; xx=yyyy; aa=bb;cc=ddd
xx"@"yy";"zz@outlook.com

答案 3 :(得分:-1)

您可以尝试

$string = 'mx.google.com;       dkim=pass header.i=@outlook.com header.s=selector1 header.b=OvtBcHsM;       spf=pass (google.com: domain of xxxx@outlook.com designates 12.12.12.12 as permitted sender) smtp.mailfrom=xxxx@outlook.com;       dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=outlook.com';
$pattern = '/[a-z0-9_\-\+\.]+@[a-z0-9]+\.([a-z]{2,4})(?:\.[a-z]{2})?/i';
preg_match_all($pattern, $string , $matches);
var_dump($matches[0]);