Regex for an email address doesn't work

萝らか妹 提交于 2019-12-03 00:50:22
Craig Trader

You cannot correctly validate an email address with regular expressions alone. A simple search will show you many articles discussing this. The problem lies with the nature of DNS: there are too many possible domain names (including non-english and Unicode domains), you cannot correctly validate them using a regex. Don't try.

The only correct way to determine if an email address is valid is to send a message to the address with a unique URL that identifies the account associated with the email, for the user to click. Anything else will annoy your end-user.

This is the regular expression used by the iOS Mail application to validate an email address:

^[[:alnum:]!#$%&’*+/=?^_`{|}~-]+((\.?)[[:alnum:]!#$%&’*+/=?^_`{|}~-]+)*@[[:alnum:]-]+(\.[[:alnum:]-]+)*(\.[[:alpha:]]+)+$

And here is a copy/paste ready function using this regular expression to validate an email address in Objective-C:

BOOL IsValidEmail(NSString *email)
{
    // Regexp from -[NSString(NSEmailAddressString) mf_isLegalEmailAddress] in /System/Library/PrivateFrameworks/MIME.framework
    NSString *emailRegex = @"^[[:alnum:]!#$%&'*+/=?^_`{|}~-]+((\\.?)[[:alnum:]!#$%&'*+/=?^_`{|}~-]+)*@[[:alnum:]-]+(\\.[[:alnum:]-]+)*(\\.[[:alpha:]]+)+$";
    NSPredicate *emailPredicate = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", emailRegex];
    return [emailPredicate evaluateWithObject:email];
}

Here's a working example, with a slightly more appropriate pattern (although it's not perfect, as others have mentioned):

NSString* pattern = @"[A-Z0-9a-z._%+-]+@[A-Za-z0-9.-]+\\.[A-Za-z]{2,4}";
NSPredicate* predicate = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", pattern];
if ([predicate evaluateWithObject:@"johndoe@example.com"] == YES) {
  // Match
} else {
  // No Match
}

I guess it should be \\., since \ itself should be escaped as well.

This page has a good explanation of using regular expressions to validate email, as well as some regexes:

http://www.regular-expressions.info/email.html

Their expression:

[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*@(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?

Seems to be the best tradeoff between thoroughness and correctness.

try putting double slash instead of one slash. that's what might the Unknown escape sequence mean.

here is a website that can help you understand how to use regex: http://www.wellho.net/regex/java.html

or just find the appropriate regex for email address here: http://regexlib.com/DisplayPatterns.aspx?cattabindex=0&categoryId=1

I think youre looking for this. Its a quite comprehensive listing of different regexps and a list of mail addresses for each, stating if the regexp was successful or not.

Copy paste solution (I added capital letters for the first example):

We get a more practical implementation of RFC 5322 if we omit the syntax using double quotes and square brackets. It will still match 99.99% of all email addresses in actual use today. Source

[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*@(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?
  NSString * derivedStandard = @"[A-Za-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\\.[A-Za-z0-9!#$%&'*+/=?^_`{|}~-]+)*@(?:[A-Za-z0-9](?:[A-Za-z0-9-]*[A-Za-z0-9])?\\.)+[A-Za-z0-9](?:[A-Za-z0-9-]*[A-Za-z0-9])?";
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", derivedStandard];
  BOOL isValid = [predicate evaluateWithObject:emailAddress];

//doesn't fail on ;)
@"asdkfjaskdjfakljsdfasdkfjaskdjfakljsdfasdkfjaskdjfakljsdfasdkfjaskdjfakljsdf"

For those who want to implement full RFC5322

The official standard is known as RFC 5322. It describes the syntax that valid email addresses must adhere to. You can (but you shouldn't--read on) implement it with this regular expression:

(?:[a-z0-9!#$%\&'*+/=?\^_`{|}~-]+(?:\.[a-z0-9!#$%\&'*+/=?\^_`{|}~-]+)*|"(?:[\x01-\x08\x0b\x0c\x0e-\x1f\x21\x23-\x5b\x5d-\x7f]|\\[\x01-\x09\x0b\x0c\x0e-\x7f])*")@(?:(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?|\[(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?|[a-z0-9-]*[a-z0-9]:(?:[\x01-\x08\x0b\x0c\x0e-\x1f\x21-\x5a\x53-\x7f]|\\[\x01-\x09\x0b\x0c\x0e-\x7f])+)\])
  NSString *rfc5322 = @"(?:[a-z0-9!#$%\\&'*+/=?\\^_`{|}~-]+(?:\\.[a-z0-9!#$%\\&'*+/=?\\^_`{|}~-]+)*|\"(?:[\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x21\\x23-\\x5b\\x5d-\\x7f]|\\\\[\\x01-\\x09\\x0b\\x0c\\x0e-\\x7f])*\")@(?:(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?|\\[(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?|[a-z0-9-]*[a-z0-9]:(?:[\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x21-\\x5a\\x53-\\x7f]|\\\\[\\x01-\\x09\\x0b\\x0c\\x0e-\\x7f])+)\\])";
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", rfc5322];
  BOOL isValid = [predicate evaluateWithObject:emailAddress];

Above regexps you can test using online regular expression tester

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!