关于python:如何检查有效的电子邮件地址?

How to check for valid email address?

本问题已经有最佳答案,请猛点这里访问。

有没有一个好的方法来检查使用regex的表单输入,以确保它是一个正确的样式的电子邮件地址?从昨晚开始搜索,所有回答过人们关于这个主题的问题的人,如果是子域电子邮件地址,似乎也有问题。


没有意义。即使您可以验证电子邮件地址在语法上是有效的,您仍然需要检查它是否输入错误,以及它是否确实是发送给您认为正确的人。唯一的方法就是给他们发一封电子邮件,让他们点击一个链接来验证。

因此,最基本的检查(例如,他们没有意外地输入他们的街道地址)通常就足够了。比如:它只有一个@符号,在@之后至少有一个.

1
[^@]+@[^@]+\.[^@]+

您可能还想禁止使用空格--可能有有效的电子邮件地址中含有空格,但我从未见过,所以这可能是一个用户错误。

如果你想要完整的检查,看看这个问题。

更新:以下是使用任何此类regex的方法:

1
2
3
4
import re

if not re.match(r"... regex here ...", email):
  # whatever

python≥3.4有re.fullmatch,优于re.match

注意绳子前面的r;这样,你就不需要两次逃避。

如果要检查大量的regex,则首先编译regex可能会更快:

1
2
3
4
5
6
import re

EMAIL_REGEX = re.compile(r"... regex here ...")

if not EMAIL_REGEX.match(email):
  # whatever

另一种选择是使用validate_email包,该包实际上与SMTP服务器联系以验证地址是否存在。但这仍然不能保证它属于正确的人。


python标准库附带了一个电子邮件解析函数:email.utils.parseaddr()

它返回两个元组,其中包含电子邮件的实名和实际地址部分:

1
2
3
4
5
6
7
8
9
>>> from email.utils import parseaddr
>>> parseaddr('[email protected]')
('', '[email protected]')

>>> parseaddr('Full Name <[email protected]>')
('Full Name', '[email protected]')

>>> parseaddr('"Full Name with quotes and <[email protected]>" <[email protected]>')
('Full Name with quotes and <[email protected]>', '[email protected]')

如果解析失败,则返回两个空字符串组成的元组:

1
2
>>> parseaddr('[invalid!email]')
('', '')

这个解析器的一个问题是它接受任何被认为是RFC-822和朋友的有效电子邮件地址的东西,包括许多在广域互联网上显然不可寻址的东西:

1
2
3
4
5
>>> parseaddr('invalid@example,com') # notice the comma
('', 'invalid@example')

>>> parseaddr('invalid-email')
('', 'invalid-email')

因此,正如@tokenmacguy所说,检查电子邮件地址的唯一确定方法是将电子邮件发送到预期的地址,并等待用户对消息中的信息采取行动。

但是,您可能希望至少检查第二个tuple元素上是否存在@符号,正如@bvukelic建议的那样:

1
2
>>> '@' in parseaddr("invalid-email")[1]
False

如果您想更进一步,可以安装dnspython项目并解析电子邮件域的邮件服务器(位于"@"之后的部分),只在实际存在MX服务器时尝试发送电子邮件:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
>>> from dns.resolver import query
>>> domain = 'foo@[email protected]'.rsplit('@', 1)[-1]
>>> bool(query(domain, 'MX'))
True
>>> query('example.com', 'MX')
Traceback (most recent call last):
  File"<stdin>", line 1, in <module>
  [...]
dns.resolver.NoAnswer
>>> query('not-a-domain', 'MX')
Traceback (most recent call last):
  File"<stdin>", line 1, in <module>
  [...]
dns.resolver.NXDOMAIN

你可以通过捕获dns.exception.DNSException来同时捕获NoAnswerNXDOMAIN

是的,foo@[email protected]是一个语法上有效的地址。只有最后一个@才可以用来检测域部分的起始位置。


我还没有在这里的自定义regex答案中看到答案,但是…

存在一个名为validate_email的python库,它有三个级别的电子邮件验证,包括询问有效的SMTP服务器电子邮件地址是否有效(不发送电子邮件)。

检查电子邮件字符串的有效格式:

1
2
from validate_email import validate_email
is_valid = validate_email('[email protected]')

检查主机是否有SMTP服务器:

1
is_valid = validate_email('[email protected]',check_mx=True)

检查主机是否有SMTP服务器,电子邮件是否确实存在:

1
is_valid = validate_email('[email protected]',verify=True)

对于那些对肮脏细节感兴趣的人,validate_email.py(source)的目标是忠实于RFC2822。

All we are really doing is comparing the input string to one
gigantic regular expression. But building that regexp, and
ensuring its correctness, is made much easier by assembling it
from the"tokens" defined by the RFC. Each of these tokens is
tested in the accompanying unit test file.

用PIP安装

1
pip install validate_email

您将需要pydns模块来检查SMTP服务器

1
pip install pyDNS

或者来自Ubuntu

1
apt-get python3-dns


电子邮件地址并不像看上去那么简单!例如,bob_o'[email protected]是有效的电子邮件地址。

我对lepl包(http://www.acooke.org/lepl/)有些运气。它可以验证RFC3696中所示的电子邮件地址:http://www.faqs.org/rfcs/rfc3696.html

找到一些旧代码:

1
2
3
4
import lepl.apps.rfc3696
email_validator = lepl.apps.rfc3696.Email()
if not email_validator("[email protected]"):
    print"Invalid email"


我找到了一个很好的(并且经过测试的)方法来检查有效的电子邮件地址。我把我的代码粘贴在这里:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
# here i import the module that implements regular expressions
import re
# here is my function to check for valid email address
def test_email(your_pattern):
pattern = re.compile(your_pattern)
# here is an example list of email to check it at the end
emails = ["[email protected]","[email protected]","wha.t.`1an?ug{}[email protected]"]
for email in emails:
    if not re.match(pattern, email):
        print"You failed to match %s" % (email)
    elif not your_pattern:
        print"Forgot to enter a pattern!"
    else:
        print"Pass"
# my pattern that is passed as argument in my function is here!
pattern = r""?([-a-zA-Z0-9.`?{}]+@\w+\.\w+)"?"  
# here i test my function passing my pattern
test_email(pattern)


我在这里看到了很多复杂的答案。其中一些人不知道简单的、真实的电子邮件地址,或者有假阳性。下面是测试字符串是否为有效电子邮件的最简单方法。它对2和3个字母的TLD进行测试。既然技术上可以有更大的TLD,那么您可能希望将3增加到4、5甚至10。

1
2
3
import re
def valid_email(email):
  return bool(re.search(r"^[\w\.\+\-]+\@[\w]+\.[a-z]{2,3}$", email))


这通常是用regex解决的。然而,有许多不同的解决方案。取决于您需要多么严格,以及您是否有验证的自定义要求,或者是否接受任何有效的电子邮件地址。

请参阅本页以获取参考:http://www.regular-expressions.info/email.html


电子邮件地址复杂得令人难以置信。这是一个匹配每个RCF822有效地址的正则表达式示例:HTTP://www-Ex-PARTRO.COM/PDW/MAIL RCF822-Advest.HTML

你会注意到它可能比你的程序长。甚至还有Perl的整个模块,用于验证电子邮件地址。因此,你可能不会得到任何100%完美作为正则表达式,同时也是可读的。下面是一个递归递归分析器:http://cpansearch.perl.org/src/abigail/rfc-rfc822-address-2009110702/lib/rfc/rfc822/address.pm

但您需要决定是需要完美的解析还是简单的代码。


1
2
3
4
5
6
import validator
is_valid = validate_email('[email protected]',verify=True)
if (is_valid==True):
    return 1
else:
    return 0

请参见验证电子邮件文档。


如果要从长字符串或文件中取出邮件,请尝试此操作。

1
([^@|\s]+@[^@]+\.[^@|\s]+)

注意,当您的电子邮件地址前后有一个空格时,这将起作用。如果你没有空间或者没有一些特殊字符,你可以尝试修改它。

工作示例:

1
2
3
string="Hello ABCD, here is my mail id [email protected]"
res = re.search("([^@|\s]+@[^@]+\.[^@|\s]+)",string,re.I)
res.group(1)

这将从此字符串中删除[email protected]

另外,请注意,这可能不是正确的答案。但我把它贴在这里是为了帮助像我这样有特殊要求的人


1
2
3
4
5
6
7
8
9
10
11
import re
def email():
    email = raw_input("enter the mail address::")
     match = re.search(r'[\w.-]+@[\w.-]+.\w+', email)

    if match:
        print"valid email :::", match.group()
    else:
        print"not valid:::"

email()


在电子邮件输入中使用此筛选器掩码:电子邮件掩码:/[\w.\-@'"!#$%&'*+/=?^_~]/i`


查找电子邮件ID:finding IP screenshot

1
2
3
4
5
6
7
8
9
10
11
12
import re
a=open("aa.txt","r")
#c=a.readlines()
b=a.read()
c=b.split("
"
)
print(c)
  for d in c:
    obj=re.search(r'[\w.]+\@[\w.]+',d)
    if obj:
      print(obj.group())  
#for more calcification click on image above..


使用电子邮件验证程序检查电子邮件

1
2
3
4
5
6
7
8
9
10
11
12
from email_validator import validate_email, EmailNotValidError

def check_email(email):
    try:
        v = validate_email(email)  # validate and get info
        email = v["email"]  # replace with normalized form
        print("True")
    except EmailNotValidError as e:
        # email is not valid, exception message is human-readable
        print(str(e))

check_email("test@gmailcom")

发现这是一个实际的实现:

1
[^@\s]+@[^@\s]+\.[^@\s]+

1
"^[\w\.\+\-]+\@[\w]+\.[a-z]{2,3}$"


电子邮件验证

1
2
3
4
5
6
7
import re
def validate(email):
    match=re.search(r"(^[a-zA-Z0-9_.+-]+@[a-zA-Z0-9]+\.[a-zA-Z0-9.]*\.*[com|org|edu]{3}$)",email)
    if match:
        return 'Valid email.'
    else:
        return 'Invalid email.'

区分真实有效的电子邮件地址和无效电子邮件地址的唯一真正准确的方法是向其发送邮件。算作电子邮件的内容令人惊讶地复杂("John Doe" "实际上是一个有效的电子邮件地址),而且您很可能希望电子邮件地址在以后实际发送给它。当它通过一些基本的健全性检查后(如在托马斯的回答中,在@之后有一个@和至少一个.之后,您可能只需向地址发送一封电子邮件验证信,并等待用户按照消息中嵌入的链接确认电子邮件有效。