php 如何在不发送电子邮件的情况下检查电子邮件地址是否存在?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/565504/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-24 23:06:30  来源:igfitidea点击:

How to check if an email address exists without sending an email?

phpemailsmtptelnetemail-validation

提问by php-guy

I have come across this PHP code to check email address using SMTP without sending an email.

我遇到过这个PHP 代码,可以使用 SMTP 检查电子邮件地址,而无需发送电子邮件

Has anyone tried anything similar or does it work for you? Can you tell if an email customer / user enters is correct & exists?

有没有人尝试过类似的东西或者它对你有用吗?您能判断电子邮件客户/用户输入的内容是否正确和存在吗?

采纳答案by Joseph Tary

There are two methods you can sometimesuse to determine if a recipient actually exists:

有时可以使用两种方法来确定收件人是否确实存在:

  1. You can connect to the server, and issue a VRFYcommand. Very few servers support this command, but it is intended for exactly this. If the server responds with a 2.0.0 DSN, the user exists.

    VRFY user
    
  2. You can issue a RCPT, and see if the mail is rejected.

    MAIL FROM:<>
    RCPT TO:<user@domain>
    
  1. 您可以连接到服务器,并发出VRFY命令。很少有服务器支持此命令,但它正是为此而设计的。如果服务器以 2.0.0 DSN 响应,则用户存在。

    VRFY user
    
  2. 您可以发出RCPT, 并查看邮件是否被拒绝。

    MAIL FROM:<>
    RCPT TO:<user@domain>
    

If the user doesn't exist, you'll get a 5.1.1 DSN. However, just because the email is not rejected, does not mean the user exists. Some server will silently discard requests like this to prevent enumeration of their users. Other servers cannot verify the user and have to accept the message regardless.

如果用户不存在,您将获得 5.1.1 DSN。但是,仅仅因为电子邮件没有被拒绝,并不意味着该用户存在。某些服务器会默默地丢弃这样的请求,以防止枚举其用户。其他服务器无法验证用户,无论如何都必须接受消息。

There is also an antispam technique called greylisting, which will cause the server to reject the address initially, expecting a real SMTP server would attempt a re-delivery some time later. This will mess up attempts to validate the address.

还有一种称为灰名单的反垃圾邮件技术,它会导致服务器最初拒绝该地址,期望真正的 SMTP 服务器稍后会尝试重新发送。这将破坏验证地址的尝试。

Honestly, if you're attempting to validate an address the best approach is to use a simple regex to block obviously invalid addresses, and then send an actual email with a link back to your system that will validate the email was received. This also ensures that they user entered their actual email, not a slight typo that happens to belong to somebody else.

老实说,如果您尝试验证地址,最好的方法是使用简单的正则表达式来阻止明显无效的地址,然后将带有链接的实际电子邮件发送回您的系统,以验证电子邮件是否已收到。这也确保了他们的用户输入了他们的实际电子邮件,而不是碰巧属于其他人的轻微错字。

回答by Drew Noakes

Other answers here discuss the various problems with trying to do this. I thought I'd show how you might try this in case you wanted to learn by doing it yourself.

这里的其他答案讨论了尝试这样做的各种问题。我想我会展示你如何尝试这个,以防你想自己动手学习。

You can connect to an mail server via telnet to ask whether an email address exists. Here's an example of testing an email address for stackoverflow.com:

您可以通过 telnet 连接到邮件服务器以询问电子邮件地址是否存在。以下是测试电子邮件地址的示例stackoverflow.com

C:\>nslookup -q=mx stackoverflow.com
Non-authoritative answer:
stackoverflow.com       MX preference = 40, mail exchanger = STACKOVERFLOW.COM.S9B2.PSMTP.com
stackoverflow.com       MX preference = 10, mail exchanger = STACKOVERFLOW.COM.S9A1.PSMTP.com
stackoverflow.com       MX preference = 20, mail exchanger = STACKOVERFLOW.COM.S9A2.PSMTP.com
stackoverflow.com       MX preference = 30, mail exchanger = STACKOVERFLOW.COM.S9B1.PSMTP.com

C:\>telnet STACKOVERFLOW.COM.S9A1.PSMTP.com 25
220 Postini ESMTP 213 y6_35_0c4 ready.  CA Business and Professions Code Section 17538.45 forbids use of this system for unsolicited electronic mail advertisements.

helo hi
250 Postini says hello back

mail from: <[email protected]>
250 Ok

rcpt to: <[email protected]>
550-5.1.1 The email account that you tried to reach does not exist. Please try
550-5.1.1 double-checking the recipient's email address for typos or
550-5.1.1 unnecessary spaces. Learn more at
550 5.1.1 http://mail.google.com/support/bin/answer.py?answer=6596 w41si3198459wfd.71

Lines prefixed with numeric codes are responses from the SMTP server. I added some blank lines to make it more readable.

以数字代码为前缀的行是来自 SMTP 服务器的响应。我添加了一些空行以使其更具可读性。

Many mail servers will not return this information as a means to prevent against email address harvesting by spammers, so you cannot rely on this technique. However you may have some success at cleaning out some obviously bad email addresses by detecting invalid mail servers, or having recipient addresses rejected as above.

许多邮件服务器不会返回此信息作为防止垃圾邮件发送者收集电子邮件地址的手段,因此您不能依赖此技术。但是,通过检测无效的邮件服务器或如上所述拒绝收件人地址,您可能会在清除一些明显错误的电子邮件地址方面取得一些成功。

Note too that mail servers may blacklist you if you make too many requests of them.

另请注意,如果您向邮件服务器发出过多请求,邮件服务器可能会将您列入黑名单。



In PHP I believe you can use fsockopen, fwriteand freadto perform the above steps programmatically:

在 PHP 中,我相信您可以使用fsockopen,fwritefread以编程方式执行上述步骤:

$smtp_server = fsockopen("STACKOVERFLOW.COM.S9A1.PSMTP.com", 25, $errno, $errstr, 30);
fwrite($smtp_server, "helo hi\r\n");
fwrite($smtp_server, "mail from: <[email protected]>\r\n");
fwrite($smtp_server, "rcpt to: <[email protected]>\r\n");

回答by kmkaplan

The general answer is that you can notcheck if an email address exists event if you send an email to it: it could just go into a black hole.

一般的答案是,如果您向其发送电子邮件,则无法检查电子邮件地址是否存在事件:它可能会进入黑洞。

That being said the method described there is quite effective. It is used in production code in ZoneCheckexcept that it uses RSET instead of QUIT.

话虽如此,那里描述的方法非常有效。它用于ZoneCheck 的生产代码中,只是它使用 RSET 而不是 QUIT。

Where user interaction with his mailbox is not overcostly many sites actually test that the mail arrive somewhere by sending a secret number that must be sent back to the emitter (either by going to a secret URL or sending back this secret number by email). Most mailing lists work like that.

在用户与其邮箱交互成本不高的情况下,许多站点实际上通过发送必须发送回发送器的秘密号码来测试邮件是否到达某处(通过访问秘密 URL 或通过电子邮件发送此秘密号码)。大多数邮件列表都是这样工作的。

回答by Piskvor left the building

This will fail (amongst other cases) when the target mailserver uses greylisting.

当目标邮件服务器使用灰名单时,这将失败(在其他情况下)。

Greylisting: SMTP server refuses delivery the first time a previously unknown client connects, allows next time(s); this keeps some percentage of spambots out, while allowing legitimate use - as it is expected that a legitimate mail sender will retry, which is what normal mail transfer agents will do.

灰名单:SMTP 服务器在以前未知的客户端第一次连接时拒绝传送,允许下一次;这可以将一定比例的垃圾邮件机器人拒之门外,同时允许合法使用 -因为预计合法邮件发件人将重试,这是普通邮件传输代理会做的事情。

However, if your code only checks on the server once, a server with greylisting will deny delivery (as your client is connecting for the first time); unless you check again in a little while, you may be incorrectly rejecting valid e-mail addresses.

但是,如果您的代码只在服务器上检查一次,带有灰名单的服务器将拒绝交付(因为您的客户端是第一次连接);除非您稍后再次检查,否则您可能错误地拒绝了有效的电子邮件地址。

回答by l_39217_l

Not really.....Some server may not check the "rcpt to:"

不是真的......某些服务器可能不会检查“rcpt to:”

http://www.freesoft.org/CIE/RFC/1123/92.htm

http://www.freesoft.org/CIE/RFC/1123/92.htm

Doing so is security risk.....

这样做是有安全隐患的......

If the server do, you can write a bot to discovery every address on the server....

如果服务器这样做,您可以编写一个机器人来发现服务器上的每个地址......

回答by Graeme Perrow

Some issues:

一些问题:

  1. I'm sure some SMTP servers will let you know immediately if an address you give them does not exist, but some won't as a privacy measure. They'll just accept whatever addresses you give them and silently ignore the ones that don't exist.
  2. As the article says, if you do this too often with some servers, they will blacklist you.
  3. For some SMTP servers (like gmail), you need to use SSL in order to do anything.This is only true when using gmail's SMTP server to sendemail.
  1. 我敢肯定,如果您提供给它们的地址不存在,某些 SMTP 服务器会立即通知您,但有些不会作为隐私措施。他们只会接受你给他们的任何地址,并默默地忽略不存在的地址。
  2. 正如文章所说,如果您对某些服务器执行此操作过于频繁,他们会将您列入黑名单。
  3. 对于某些 SMTP 服务器(例如 gmail),您需要使用 SSL 才能执行任何操作。这仅适用于使用 gmail 的 SMTP 服务器发送电子邮件时。

回答by Learning

"Can you tell if an email customer / user enters is correct & exists?"

“您能判断电子邮件客户/用户输入的内容是否正确和存在吗?”

Actually these are two separate things. It might existbut might not be correct.

其实这是两个不同的东西。它可能存在,但可能不正确。

Sometimes you have to take the user inputs at the face value. There are many ways to defeat the system otherwise.

有时,您必须按面值接受用户输入。否则有很多方法可以打败系统。

回答by Sachin

function EmailValidation($email)
{
    $email = htmlspecialchars(stripslashes(strip_tags($email))); //parse unnecessary characters to prevent exploits
    if (eregi('[a-z||0-9]@[a-z||0-9].[a-z]', $email)) {
        //checks to make sure the email address is in a valid format
        $domain = explode( "@", $email ); //get the domain name
        if (@fsockopen ($domain[1],80,$errno,$errstr,3)) {
            //if the connection can be established, the email address is probably valid
            echo "Domain Name is valid ";
            return true;
        } else {
            echo "Con not a email domian";
            return false; //if a connection cannot be established return false
        }
        return false; //if email address is an invalid format return false
    }
}

回答by Bryan Rehbein

About all you can do is search DNS and ensure the domain that is in the email address has an MX record, other than that there is no reliable way of dealing with this.

您所能做的就是搜索 DNS 并确保电子邮件地址中的域具有 MX 记录,除此之外没有可靠的方法来处理此问题。

Some servers may work with the rcpt-to method where you talk to the SMTP server, but it depends entirely on the configuration of the server. Another issue may be an overloaded server may return a 550 code saying user is unknown, but this is a temporary error, there is a permanent error (451 i think?) that can be returned. This depends entirelyon the configuration of the server.

某些服务器可能会使用 rcpt-to 方法与 SMTP 服务器通信,但这完全取决于服务器的配置。另一个问题可能是过载的服务器可能会返回一个 550 代码,表示用户未知,但这是一个临时错误,有一个可以返回的永久性错误(我认为是 451?)。这完全取决于服务器的配置。

I personally would check for the DNS MX record, then send an email verification if the MX record exists.

我个人会检查 DNS MX 记录,然后发送电子邮件验证是否存在 MX 记录。

回答by Henkealg

Although this question is a bit old, this service tip might help users searching for a similar solution checking email addresses beyond syntax validation prior to sending.

虽然这个问题有点老,但这个服务提示可能会帮助用户搜索类似的解决方案,在发送之前检查语法验证之外的电子邮件地址。

I have been using this open sourced servicefor a more in depth validating of emails (checking for mx records on the e-mail address domain etc.) for a few projects with good results. It also checks for common typos witch is quite useful. Demo here.

我一直在使用这个开源服务对一些项目进行更深入的电子邮件验证(检查电子邮件地址域上的 mx 记录等),并取得了良好的效果。它还检查常见的错别字女巫非常有用。演示在这里