На протяжении многих лет я медленно разрабатывал регулярное выражение, которое корректно проверяет адреса электронной почты MOST, предполагая, что они не используют IP-адрес в качестве серверной части.
Я использую его в нескольких программах PHP, и он работает большую часть времени. Однако время от времени со мной связывается кто-то, у кого проблемы с сайтом, который его использует, и мне приходится вносить некоторые коррективы (совсем недавно я понял, что не разрешаю 4-символьные TLD).
Какое лучшее регулярное выражение вы видели или видели для проверки писем?
Я видел несколько решений, в которых используются функции, использующие несколько более коротких выражений, но я бы предпочел иметь одно длинное сложное выражение в простой функции вместо нескольких коротких выражений в более сложной функции.
Ответы:
Совместимое регулярное выражение полностью RFC 822 является неэффективным и неясным из - за его длиной. К счастью, RFC 822 был заменен дважды, и текущая спецификация адресов электронной почты - RFC 5322 . RFC 5322 приводит к регулярному выражению, которое можно понять, если изучить его в течение нескольких минут, и достаточно эффективно для реального использования.
Одно регулярное выражение, совместимое с RFC 5322, можно найти в верхней части страницы по адресу http://emailregex.com/, но в нем используется шаблон IP-адреса, распространяющийся по Интернету, с ошибкой, которая допускает
00
любое из десятичных значений байтов без знака в Адрес, разделенный точками, что недопустимо. Остальная часть, похоже, соответствует грамматике RFC 5322 и проходит несколько тестов с использованиемgrep -Po
доменных имен, IP-адресов, неверных и учетных записей с кавычками и без них.Исправляя
00
ошибку в шаблоне IP, мы получаем работающее и довольно быстрое регулярное выражение. (Очистите отрендеренную версию, а не уценку, для реального кода.)или:
Вот диаграмма , из конечного автомата для регулярного выражения выше , которое является более ясным , чем само регулярное выражение
Более сложные шаблоны в Perl и PCRE (библиотека регулярных выражений, используемая, например, в PHP) могут безошибочно анализировать RFC 5322 . Python и C # тоже могут это делать, но они используют синтаксис, отличный от первых двух. Однако, если вы вынуждены использовать один из многих менее мощных языков сопоставления с образцом, то лучше использовать настоящий парсер.
Также важно понимать, что проверка его в соответствии с RFC абсолютно ничего не говорит вам о том, действительно ли этот адрес существует в предоставленном домене, или является ли лицо, вводящее адрес, его истинным владельцем. Люди постоянно подписывают других на списки рассылки. Исправление, которое требует более причудливого вида проверки, который включает отправку на этот адрес сообщения, содержащего токен подтверждения, который должен быть введен на той же веб-странице, что и адрес.
Жетоны подтверждения - это единственный способ узнать, что вы получили адрес человека, который его вводит. Вот почему большинство списков рассылки теперь используют этот механизм для подтверждения регистрации. В конце концов, любой может отрицать
president@whitehouse.gov
, и это даже будет восприниматься как законное, но вряд ли это будет человек на другом конце.Для PHP вы не должны использовать шаблон, приведенный в разделе Проверка адреса электронной почты с PHP, правильный путь, из которого я цитирую:
Это не лучше, чем все другие не RFC шаблоны. Он даже не настолько умен, чтобы справиться даже с RFC 822 , не говоря уже о RFC 5322. Этот , однако, таков .
Если вы хотите стать модным и педантичным, внедрите полный двигатель состояния . Регулярное выражение может действовать только как элементарный фильтр. Проблема с регулярными выражениями заключается в том, что говорить кому-то, что их совершенно действительный адрес электронной почты недействителен (ложный положительный результат), потому что ваше регулярное выражение не может его обработать, просто грубо и невежливо с точки зрения пользователя. Механизм состояний для этой цели может проверять и даже корректировать адреса электронной почты, которые в противном случае считались бы недействительными, поскольку он разбирает адрес электронной почты в соответствии с каждым RFC. Это позволяет получить потенциально более приятный опыт, как
См. Также Проверка адресов электронной почты , включая комментарии. Или сравнение адреса электронной почты с проверкой правильности регулярных выражений .
Debuggex Demo
источник
Вы не должны использовать регулярные выражения для проверки адресов электронной почты.
Вместо этого используйте класс MailAddress , например:
MailAddress
Класс использует анализатор BNF для проверки адреса в полном соответствии с RFC822.Если вы планируете использовать
MailAddress
для проверки адреса электронной почты, имейте в виду, что этот подход также принимает часть отображаемого имени адреса электронной почты, и это может быть не совсем тем, чего вы хотите достичь. Например, он принимает эти строки в качестве действительных адресов электронной почты:В некоторых из этих случаев только последняя часть строк обрабатывается как адрес; остальное до этого - отображаемое имя. Чтобы получить простой адрес электронной почты без отображаемого имени, вы можете сравнить нормализованный адрес с исходной строкой.
Кроме того,
user@company.
MailAddress также принимает адрес, имеющий точку в конце, например .Если вы действительно хотите использовать регулярное выражение, вот оно :
источник
fake@not-a-real-domain.name
. Вы не должны полагаться на проверку электронной почты, чтобы предотвратить XSS.Этот вопрос задают много, но я думаю, что вы должны отступить и спросить себя, почему вы хотите проверять адреса электронной почты синтаксически? Какая выгода на самом деле?
Если вы хотите проверить правильность электронного письма, у вас нет другого выбора, кроме как отправить электронное письмо с подтверждением и получить ответ от пользователя. Во многих случаях вам все равно придется отправлять письмо-подтверждение по соображениям безопасности или по этическим причинам (например, вы не можете, например, подписать кого-либо на службу против их воли).
источник
me@hotmail
, он, очевидно, не получит ваше электронное письмо с подтверждением, и тогда где они? Их больше нет на вашем сайте, и они задаются вопросом, почему они не могут зарегистрироваться. На самом деле нет, они не совсем - они совсем забыли о вас. Однако, если вы можете просто выполнить базовую проверку работоспособности с помощью регулярных выражений, пока они еще с вами, тогда они сразу же поймут эту ошибку, и вы получите счастливого пользователя.president@whitehouse.gov
адреса указывают на очень занятого главнокомандующего. :)Все зависит от того, насколько точно вы хотите быть. Для моих целей, где я просто пытаюсь не пускать такие вещи, как
bob @ aol.com
(пробелы в электронных письмах) илиsteve
(без домена) илиmary@aolcom
(без периода до .com), я используюКонечно, это будет соответствовать вещам, которые не являются действительными адресами электронной почты, но это вопрос получения простых простых ошибок.
В это регулярное выражение можно внести любое количество изменений (и некоторые в комментариях к этому ответу), но это просто и легко понять, и это хорошая первая попытка.
источник
.
входит в\S
.mary@aolcom
я, полный мусор . YMMV.@
знаками:/^[^\s@]+@[^\s@]+\.[^\s@]{2,}$/
jsfiddle.net/b9chris/mXB96Это зависит от того, что вы подразумеваете под лучшим: если вы говорите о перехвате каждого действующего адреса электронной почты, используйте следующее:
( http://www.ex-parrot.com/~pdw/Mail-RFC822-Address.html ) Если вы ищете что-то более простое, но которое поймает большинство действительных адресов электронной почты, попробуйте что-то вроде:
РЕДАКТИРОВАТЬ: Из ссылки:
источник
email address
которые ошибочно проходят через второй, но попадают в более длинное регулярное выражение?[ОБНОВЛЕНО] Я собрал все, что я знаю о проверке адреса электронной почты, здесь: http://isemail.info , который теперь не только проверяет, но и диагностирует проблемы с адресами электронной почты. Я согласен со многими комментариями здесь, что валидация является лишь частью ответа; см. мое эссе на http://isemail.info/about .
Насколько я знаю, is_email () остается единственным валидатором, который определенно скажет вам, является ли данная строка действительным адресом электронной почты или нет. Я загрузил новую версию на http://isemail.info/
Я сопоставил контрольные примеры от Кэла Хендерсона, Дейва Чайлда, Фила Хаака, Дуга Ловелла, RFC5322 и RFC 3696. Всего 275 тестовых адресов. Я провел все эти тесты со всеми бесплатными валидаторами, которые смог найти.
Я постараюсь обновлять эту страницу по мере того, как люди улучшат свои валидаторы. Спасибо Кэлу, Майклу, Дейву, Полу и Филу за их помощь и сотрудничество в составлении этих тестов и конструктивную критику моего собственного валидатора .
Люди должны знать об ошибках в RFC 3696 в частности. Три из канонических примеров на самом деле являются недействительными адресами. И максимальная длина адреса составляет 254 или 256 символов, а не 320.
источник
name@xn--4ca9at.at
так как этот код о проверке, а не интерпретации. Если вы хотите добавить переводчик punycode, тогда я с радостью приму запрос на размещение по адресу github.com/dominicsayers/isemailСогласно спецификации W3C HTML5 :
Контекст:
источник
john.doe@localhost
действителен. Конечно, в реальном приложении (то есть в сообществе) я бы хотел, чтобы вы предложили заменить * на +"test...."@gmail.com
полностью действителен в соответствии с RFC и семантически эквивалентенtest....@gmail.com
.Это легко в Perl 5.10 или новее:
источник
addrspec
части действительно имеет отношение к вопросу. Принятие чего-то большего и переадресация, хотя какая-то другая часть системы, которая не готова принять полные адреса RFC5822, похожа на стрельбу - ваша собственная нога.я использую
Который используется в ASP.NET RegularExpressionValidator.
источник
!@mydomain.net
отклонен.^\\w+([-+.']\\w+)*@\\w+([-.]\\w+)*\\.\\w{2,}([-.]\\w+)*$
simon-@hotmail.com
который действительно действителен (у нашего клиента был похожий адрес) `Не знаю, что лучше, но этот, по крайней мере, правильный, если на адресах есть комментарии и они заменены пробелами.
Шутки в сторону. Вы должны использовать уже написанную библиотеку для проверки писем. Лучше всего, вероятно, просто отправить электронное письмо с подтверждением на этот адрес.
источник
Адреса электронной почты, которые я хочу проверить, будут использоваться веб-приложением ASP.NET с использованием пространства имен System.Net.Mail для отправки писем списку людей. Поэтому вместо того, чтобы использовать какое-то очень сложное регулярное выражение, я просто пытаюсь создать экземпляр MailAddress по адресу. Построитель MailAddress сгенерирует исключение, если адрес сформирован неправильно. Таким образом, я знаю, что могу, по крайней мере, получить электронное письмо от двери. Конечно, это проверка на стороне сервера, но как минимум она вам нужна.
источник
args.Value
вместо ссылки полеtxtEmail.Text
жестко закодированным. Последний будет привязывать ваш валидатор к одному экземпляру элемента управления, что может быть в порядке, если у вас есть одно поле электронной почты, но в противном случае это не рекомендуется.Быстрый ответ
Используйте следующее регулярное выражение для проверки ввода:
([-!#-'*+/-9=?A-Z^-~]+(\.[-!#-'*+/-9=?A-Z^-~]+)*|"([]!#-[^-~ \t]|(\\[\t -~]))+")@[0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?(\.[0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?)+
Адреса, соответствующие этому регулярному выражению:
Второе ограничение - это ограничение по RFC 5321/5322.
Подробный ответ
Использование регулярного выражения, которое распознает адреса электронной почты, может быть полезно в различных ситуациях: например, для поиска адресов электронной почты в документе, для проверки ввода пользователя или в качестве ограничения целостности хранилища данных.
Однако следует отметить, что если вы хотите узнать, действительно ли адрес относится к существующему почтовому ящику, ничто не заменит отправку сообщения на этот адрес. Если вы хотите только проверить, является ли адрес грамматически правильным, то вы можете использовать регулярное выражение, но обратите внимание, что
""@[]
это грамматически правильный адрес электронной почты, который, безусловно, не ссылается на существующий почтовый ящик.Синтаксис адресов электронной почты был определен в различных RFC , особенно в RFC 822 и RFC 5322 . RFC 822 следует рассматривать как «оригинальный» стандарт, а RFC 5322 - как последний стандарт. Синтаксис, определенный в RFC 822, является наиболее мягким, и последующие стандарты ограничивают синтаксис все дальше и дальше, когда более новые системы или службы должны распознавать устаревший синтаксис, но никогда не создавать его.
В этом ответе я буду использовать «адрес электронной почты»,
addr-spec
как определено в RFC (то естьjdoe@example.org
, но не"John Doe"<jdoe@example.org>
, ниsome-group:jdoe@example.org,mrx@exampel.org;
).Существует одна проблема с переводом синтаксисов RFC в регулярные выражения: синтаксис не является регулярным! Это объясняется тем, что они допускают необязательные комментарии в адресах электронной почты, которые могут быть бесконечно вложенными, в то время как бесконечная вложенность не может быть описана регулярным выражением. Для сканирования или проверки адресов, содержащих комментарии, вам нужен анализатор или более мощные выражения. (Обратите внимание, что такие языки, как Perl, имеют конструкции для описания контекстно-свободных грамматик в форме регулярных выражений.) В этом ответе я проигнорирую комментарии и рассмотрю только правильные регулярные выражения.
RFC определяют синтаксис для сообщений электронной почты, а не для адресов электронной почты как таковых. Адреса могут появляться в различных полях заголовка, и именно здесь они в основном определены. Когда они появляются в полях заголовка, адреса могут содержать (между лексическими токенами) пробелы, комментарии и даже разрывы строк. Семантически это не имеет значения, однако. Удаляя этот пробел и т. Д. Из адреса, вы получаете семантически эквивалентное каноническое представление . Таким образом, каноническое представление
first. last (comment) @ [3.5.7.9]
естьfirst.last@[3.5.7.9]
.Различные синтаксисы должны использоваться для разных целей. Если вы хотите сканировать адреса электронной почты в (возможно, очень старом) документе, возможно, будет хорошей идеей использовать синтаксис, определенный в RFC 822. С другой стороны, если вы хотите проверить ввод пользователя, вы можете использовать синтаксис, определенный в RFC 5322, возможно, принимает только канонические представления. Вы должны решить, какой синтаксис применяется в вашем конкретном случае.
В этом ответе я использую «расширенные» регулярные выражения POSIX, предполагая набор символов, совместимый с ASCII.
RFC 822
Я пришел к следующему регулярному выражению. Я приглашаю всех попробовать и сломать это. Если вы найдете какие-либо ложные срабатывания или ложные отрицания, пожалуйста, оставьте их в комментарии, и я постараюсь исправить выражение как можно скорее.
([^][()<>@,;:\\". \x00-\x1F\x7F]+|"(\n|(\\\r)*([^"\\\r\n]|\\[^\r]))*(\\\r)*")(\.([^][()<>@,;:\\". \x00-\x1F\x7F]+|"(\n|(\\\r)*([^"\\\r\n]|\\[^\r]))*(\\\r)*"))*@([^][()<>@,;:\\". \x00-\x1F\x7F]+|\[(\n|(\\\r)*([^][\\\r\n]|\\[^\r]))*(\\\r)*])(\.([^][()<>@,;:\\". \x00-\x1F\x7F]+|\[(\n|(\\\r)*([^][\\\r\n]|\\[^\r]))*(\\\r)*]))*
Я считаю, что он полностью соответствует RFC 822, включая ошибки . Он распознает только адреса электронной почты в их канонической форме. Для регулярного выражения, которое распознает (сворачивание) пробелы, смотрите вывод ниже.
Вывод показывает, как я пришел к выражению. Я перечисляю все соответствующие грамматические правила из RFC в том виде, в котором они отображаются, а затем соответствующее регулярное выражение. Там, где опечатка была опубликована, я даю отдельное выражение для исправленного правила грамматики (помеченное «erratum») и использую обновленную версию как подвыражение в последующих регулярных выражениях.
Как указано в пункте 3.1.4. RFC 822 необязательный линейный пробел может быть вставлен между лексическими токенами. Там, где это применимо, я расширил выражения для соответствия этому правилу и пометил результат как «opt-lwsp».
RFC 5322
Я пришел к следующему регулярному выражению. Я приглашаю всех попробовать и сломать это. Если вы найдете какие-либо ложные срабатывания или ложные отрицания, пожалуйста, оставьте их в комментарии, и я постараюсь исправить выражение как можно скорее.
([-!#-'*+/-9=?A-Z^-~]+(\.[-!#-'*+/-9=?A-Z^-~]+)*|"([]!#-[^-~ \t]|(\\[\t -~]))+")@([-!#-'*+/-9=?A-Z^-~]+(\.[-!#-'*+/-9=?A-Z^-~]+)*|\[[\t -Z^-~]*])
Я считаю, что он полностью соответствует RFC 5322, включая ошибки . Он распознает только адреса электронной почты в их канонической форме. Для регулярного выражения, которое распознает (сворачивание) пробелы, смотрите вывод ниже.
Вывод показывает, как я пришел к выражению. Я перечисляю все соответствующие грамматические правила из RFC в том виде, в котором они отображаются, а затем соответствующее регулярное выражение. Для правил, которые включают семантически нерелевантные (складывающиеся) пробелы, я даю отдельное регулярное выражение с пометкой «(нормализовано)», которое не принимает этот пробел.
Я проигнорировал все "обс-" правила из RFC. Это означает, что регулярные выражения соответствуют только адресам электронной почты, которые строго соответствуют RFC 5322. Если вам нужно сопоставить «старые» адреса (как делает более свободная грамматика, включая правила «obs-»), вы можете использовать одно из регулярных выражений RFC 822 из предыдущего абзаца.
Обратите внимание, что некоторые источники (в частности, w3c ) утверждают, что RFC 5322 является слишком строгим в локальной части (то есть в части, предшествующей знаку @). Это потому что "..", "a..b" и "a." не являются действительными точечными атомами, в то время как они могут использоваться как имена почтовых ящиков. RFC, однако, это позволит местным частям , как это, за исключением того, что они должны быть заключены в кавычки. Поэтому вместо
a..b@example.net
вас следует написать"a..b"@example.net
, что семантически эквивалентно.Дальнейшие ограничения
SMTP (как определено в RFC 5321 ) дополнительно ограничивает набор действительных адресов электронной почты (или фактически: имена почтовых ящиков). Представляется разумным навязать эту более строгую грамматику, чтобы сопоставленный адрес электронной почты мог фактически использоваться для отправки электронного письма.
RFC 5321, в основном, оставляет в стороне "локальную" часть (то есть часть до @ -знака), но является более строгой в доменной части (т.е. часть после @ -знака). Он допускает только имена хостов вместо точечных атомов и адресные литералы вместо доменных литералов.
Грамматика, представленная в RFC 5321, слишком мягкая, когда речь идет об именах хостов и IP-адресах. Я позволил себе «исправить» эти правила, используя этот проект и RFC 1034 в качестве руководства. Вот результирующее регулярное выражение.
([-!#-'*+/-9=?A-Z^-~]+(\.[-!#-'*+/-9=?A-Z^-~]+)*|"([]!#-[^-~ \t]|(\\[\t -~]))+")@([0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?(\.[0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?)*|\[((25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])){3}|IPv6:((((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){6}|::((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){5}|[0-9A-Fa-f]{0,4}::((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){4}|(((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):)?(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}))?::((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){3}|(((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){0,2}(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}))?::((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){2}|(((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){0,3}(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}))?::(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):|(((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){0,4}(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}))?::)((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3})|(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])){3})|(((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){0,5}(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}))?::(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3})|(((0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}):){0,6}(0|[1-9A-Fa-f][0-9A-Fa-f]{0,3}))?::)|(?!IPv6:)[0-9A-Za-z-]*[0-9A-Za-z]:[!-Z^-~]+)])
Обратите внимание, что в зависимости от варианта использования вы можете не использовать «General-address-literal» в своем регулярном выражении. Также обратите внимание, что
(?!IPv6:)
в последнем регулярном выражении я использовал отрицательный прогноз, чтобы часть «General-address-literal» не соответствовала искаженным адресам IPv6. Некоторые процессоры регулярных выражений не поддерживают негативную перспективу. Удалите подстроку|(?!IPv6:)[0-9A-Za-z-]*[0-9A-Za-z]:[!-Z^-~]+
из регулярного выражения, если вы хотите убрать всю часть "General-address-literal".Вот вывод:
Проверка ввода пользователя
Распространенным вариантом использования является проверка ввода пользователя, например, в форме HTML. В этом случае обычно разумно исключать адресные литералы и требовать по крайней мере две метки в имени хоста. Взяв за основу улучшенное регулярное выражение RFC 5321 из предыдущего раздела, получим следующее выражение:
([-!#-'*+/-9=?A-Z^-~]+(\.[-!#-'*+/-9=?A-Z^-~]+)*|"([]!#-[^-~ \t]|(\\[\t -~]))+")@[0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?(\.[0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?)+
Я не рекомендую ограничивать локальную часть, например, путем исключения строк в кавычках, поскольку мы не знаем, какие имена почтовых ящиков допускают некоторые хосты (например,
"a..b"@example.net
или даже"a b"@example.net
).Я также не рекомендую явно проверять список литеральных доменов верхнего уровня или даже устанавливать ограничения длины (помните, как «.museum» аннулирован
[a-z]{2,4}
), но если вы должны:([-!#-'*+/-9=?A-Z^-~]+(\.[-!#-'*+/-9=?A-Z^-~]+)*|"([]!#-[^-~ \t]|(\\[\t -~]))+")@([0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?\.)*(net|org|com|info|
так далее...)
Убедитесь, что вы регулярно обновляете свое регулярное выражение, если решите пойти по пути явной проверки домена верхнего уровня.
Дальнейшие соображения
Когда принимаются только имена хостов в доменной части (после знака @), приведенные выше регулярные выражения принимают только метки, содержащие не более 63 символов, как они должны. Однако они не приводят в исполнение тот факт, что полное имя хоста должно быть длиной не более 253 символов (включая точки). Хотя это ограничение, строго говоря, все еще остается регулярным, сделать регулярное выражение, включающее это правило, не представляется возможным.
Еще одним соображением, особенно при использовании регулярных выражений для проверки ввода, является обратная связь с пользователем. Если пользователь вводит неправильный адрес, было бы неплохо дать немного больше отзывов, чем простой «синтаксически неправильный адрес». С "ванильными" регулярными выражениями это невозможно.
Эти два соображения могут быть решены путем анализа адреса. В некоторых случаях ограничение дополнительной длины для имен хостов также может быть устранено с помощью дополнительного регулярного выражения, которое проверяет его, и сопоставляя адрес с обоими выражениями.
Ни одно из регулярных выражений в этом ответе не оптимизировано для производительности. Если производительность является проблемой, вы должны посмотреть, можно ли (и каким образом) регулярное выражение по вашему выбору.
источник
arbitrary-long-email-address-should-be-invalid-arbitrary-long-email-address-should-be-invalid.and-the-second-group-also-should-not-be-so-long-and-the-second-group-also-should-not-be-so-long@example.com
не следует проверять. Я предлагаю изменить знаки «+» в первой группе (имя перед необязательной точкой) и во второй группе (имя после следующих точек) на{1,64}
$emailRegex = '/^([-!#-\'*+\/-9=?A-Z^-~]{1,64}(\.[-!#-\'*+\/-9=?A-Z^-~]{1,64})*|"([]!#-[^-~ \t]|(\\[\t -~]))+")@[0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?(\.[0-9A-Za-z]([0-9A-Za-z-]{0,61}[0-9A-Za-z])?)+$/';
Есть множество примеров этого в сети (и я думаю, что даже тот, который полностью проверяет RFC - но это десятки / сотни строк, если память служит). Люди склонны увлекаться проверкой подобных вещей. Почему бы просто не проверить, есть ли у него @ и хотя бы один. и встречает некоторую простую минимальную длину. Вводить фальшивое электронное письмо и в любом случае сопоставлять любое действительное регулярное выражение просто. Я предполагаю, что ложные срабатывания лучше, чем ложные.
источник
Решая, какие символы разрешены, пожалуйста, помните своих друзей-апострофов и переносов. Я не могу контролировать тот факт, что моя компания генерирует мой адрес электронной почты, используя мое имя из системы управления персоналом. Это включает в себя апостроф в моей фамилии. Я не могу сказать вам, сколько раз я был заблокирован от взаимодействия с веб-сайтом из-за того, что мой адрес электронной почты "недействителен".
источник
Это регулярное выражение из библиотеки Perl Email :: Valid . Я считаю, что он самый точный, он соответствует всем 822. И он основан на регулярном выражении в книге О'Рейли:
источник
Когда вы пишете на PHP, я бы посоветовал вам использовать встроенную проверку PHP для электронной почты.
Если вы используете php-версию ниже 5.3.6, пожалуйста, учтите эту проблему: https://bugs.php.net/bug.php?id=53091
Если вам нужна дополнительная информация о том, как работает эта встроенная проверка, см. Здесь: Работает ли PHP filter_var FILTER_VALIDATE_EMAIL на самом деле?
источник
Кэл Хендерсон (Flickr) написал статью под названием « Парсинг адресов электронной почты в PHP» и показывает, как правильно выполнять синтаксический анализ адресов электронной почты , соответствующих RFC (2) 822. Вы также можете получить исходный код в php , python и ruby, который лицензирован cc .
источник
a@b
это действительноa@b
что допустимо ... в данном случаеb
это домен верхнего уровня.Я никогда не удосужился создавать свои собственные регулярные выражения, потому что есть вероятность, что кто-то другой уже придумал лучшую версию. Я всегда использую regexlib, чтобы найти тот, который мне по вкусу.
источник
Нет такого, который действительно пригоден для использования.
Я обсуждаю некоторые вопросы в своем ответе на вопрос: есть ли библиотека php для проверки адреса электронной почты? , это также обсуждается в Regexp распознавание адреса электронной почты трудно?
Короче говоря, не ожидайте, что одно, пригодное для использования регулярное выражение выполнит правильную работу. И наилучшее регулярное выражение будет проверять синтаксис, а не действительность электронного письма (jhohn@example.com верно, но оно, вероятно, отскочит ...).
источник
Одно простое регулярное выражение, которое, по крайней мере, не будет отклонять какой-либо действительный адрес электронной почты, будет проверять что-то, за которым следует знак @, а затем что-то, за которым следует точка и как минимум 2 символа. Он не будет ничего отклонять, но после просмотра спецификации я не смог найти ни одного письма, которое было бы действительным и отклонено.
электронная почта = ~
/.+@[^@]+\.[^@]{2,}$/
источник
/^[^@]+@[^@]+\.[^@]{2}[^@]*$/
на самом деле проверяет на 1 знак @. Ваше регулярное выражение пропустит множественное число из-за. * В конце./^[^@]+@[^@]+\.[^@]{2,4}$/
удостовериться, что оно заканчивается от 2 до 4 не @ символов. Как указал @Josh, теперь в конце можно добавить лишний @. Но вы также можете изменить это на:/^[^@]+@[^@]+\.[^a-z-A-Z]{2,4}$/
все домены верхнего уровня являются символами aZ. вы можете заменить4
с5
или более позволяя доменов верхнего уровня имена , чтобы быть больше в будущем.Вы можете использовать тот, который используется плагином jQuery Validation:
источник
a-b'c_d.e@f-g.h
но смог поймать несоответствующие изменения, такие какa-b'c_d.@f-g.h
иa-b'c_d.e@f-.h
Для наиболее полной оценки лучшего регулярного выражения для проверки адреса электронной почты, пожалуйста, перейдите по этой ссылке; « Сравнение адреса электронной почты, проверяющего регулярные выражения »
Вот текущее верхнее выражение для справочных целей:
источник
Не говоря уже о том, что нелатинские (китайский, арабский, греческий, иврит, кириллица и т. Д.) Доменные имена должны быть разрешены в ближайшем будущем . Каждый должен изменить используемое регулярное выражение электронной почты, потому что эти символы наверняка не будут охвачены
[a-z]/i
ни тем, ни другим\w
. Они все потерпят неудачу.В конце концов, лучший способ проверить адрес электронной почты по-прежнему состоит в том, чтобы фактически отправить электронное письмо на указанный адрес для подтверждения адреса. Если адрес электронной почты является частью аутентификации пользователя (регистрация / логин / и т. Д.), То вы можете идеально сочетать его с системой активации пользователя. Т.е. отправьте электронное письмо со ссылкой с уникальным ключом активации на указанный адрес электронной почты и разрешите вход в систему только тогда, когда пользователь активировал вновь созданную учетную запись, используя ссылку в электронном письме.
Если целью регулярного выражения является просто быстрое информирование пользователя в пользовательском интерфейсе о том, что указанный адрес электронной почты не выглядит в правильном формате, лучше всего проверить, соответствует ли он в основном следующему регулярному выражению:
Просто как тот. С какой стати вы заботитесь о символах, используемых в имени и домене? Ответственность за ввод действительного адреса электронной почты лежит на клиенте, а не на сервере. Даже когда клиент вводит синтаксически действительный адрес электронной почты, например
aa@bb.cc
, это не гарантирует, что это допустимый адрес электронной почты. Ни одно регулярное выражение не может покрыть это.источник
spaces
после,@.
например.test@test.ca com net
считается правильным адресом электронной почты, используя приведенное выше регулярное выражение, где, как это должно быть, возвращается недействительнымСпецификация HTML5 предлагает простое регулярное выражение для проверки адресов электронной почты:
Это намеренно не соответствует RFC 5322 .
Общая длина также может быть ограничена 254 символами, согласно RFC 3696 опечаток 1690 .
источник
invalid@emailaddress
. Я призываю к осторожности и много испытаний, прежде чем использовать его!Для яркой демонстрации следующий монстр довольно хорош, но все еще не может правильно распознать все синтаксически допустимые адреса электронной почты: он распознает вложенные комментарии глубиной до четырех уровней.
Это задание для синтаксического анализатора, но даже если адрес синтаксически допустим, он все равно может не быть доставленным. Иногда вам приходится прибегать к простому методу: «Эй, вы все, смотрите нас!»
источник
Согласно официальному стандарту RFC 2822 действительное регулярное выражение электронной почты
если вы хотите использовать его в Java, это действительно очень легко
источник
(?:[A-Za-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[A-Za-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])+)\])
Вот PHP, который я использую. Я выбрал это решение в духе «ложные срабатывания лучше, чем ложные отрицания», как было объявлено другим комментатором здесь И в отношении сохранения времени отклика и нагрузки на сервер ... на самом деле нет необходимости тратить ресурсы сервера на регулярное выражение, когда это отсеет самую простую ошибку пользователя. Вы всегда можете выполнить это, отправив тестовое электронное письмо, если хотите.
источник
Стандарт RFC 5322:
Позволяет использовать локальную часть точечного атома, локальную часть в кавычках, устаревшую (смешанная точка и строка в кавычках) локальную часть, домен доменных имен, литеральный домен домена (IPv4, IPv6 и сопоставленный с IPv4 адрес IPv6), и (вложенные) CFWS.
Стандарт RFC 5321:
Разрешает локальную часть локальной точки, локальную часть в кавычках, домен доменного имени и буквенный домен (IPv4, IPv6 и IPv4-сопоставленный адрес IPv6).
Основные:
Разрешает использование локальной точки и домена доменных имен с точечным атомом (требуются как минимум две метки доменного имени с ДВУ, ограниченным 2-6 буквенными символами).
источник
/D
флаг, а вы его цитируете одинарными кавычками, но также использовали косую черту для разделения шаблона? Это не Perl, и это не может быть PCRE. Поэтому это PHP? Я считаю, что это единственные три, которые допускают рекурсию(?1)
.Странно, что вы «не можете» разрешить 4-х символьные TLD. Вы запрещаете людям доступ к .info и .name , и ограничение длины останавливается .travel и .museum , но да, они встречаются реже, чем 2-символьные TLD и 3-символьные TLD.
Вы должны разрешить прописные алфавиты тоже. Системы электронной почты нормализуют локальную часть и часть домена.
Для вашего регулярного выражения доменной части доменное имя не может начинаться с «-» и не может заканчиваться «-». Тире может оставаться только между
Если вы использовали библиотеку PEAR, проверьте их почтовую функцию (забыл точное имя / библиотеку). Вы можете проверить адрес электронной почты, вызвав одну функцию, и он подтвердит адрес электронной почты в соответствии с определением в RFC822.
источник
источник