WordPress и PHP ядро
is_email()
Функция Source является типичной реализацией WordPress и не полностью работать с тем, что RFC 6531 позволяет. Одной из причин может быть то, что FILTER_VALIDATE_EMAIL
константа PHP по умолчанию для filter_var()
не намного лучше при проверке чего-либо в соответствии с руководящими принципами Internet Engineering Task Force (IETF®) .
стандарты
Дело в том, что RFC 6531 допускает «символы Юникода за пределами диапазона ASCII» . А именно это (для локальной части - до @
):
- Прописные и строчные буквы английского алфавита (a – z, A – Z) (ASCII: 65–90, 97–122)
- Цифры
0
в 9
(ASCII: 48–57)
- Эти специальные символы:
! # $ % & ' * + - / = ? ^ _ ` { | } ~
- Символ
.
(точка, точка, точка остановки) (ASCII: 46) при условии, что он не является первым или последним символом, а также при условии, что он не появляется последовательно (например John..Doe@example.com
, не допускается).
- Специальные символы допускаются с ограничениями. Они есть:
- Космос и
"(),:;<>@[\]
(ASCII: 32, 34, 40, 41, 44, 58, 59, 60, 62, 64, 91–93)
- Ограничения для специальных символов заключаются в том, что они должны использоваться только в том случае, если они заключены в кавычки, и что двум из них (обратный слеш \ и кавычка "(ASCII: 92, 34)) также должен предшествовать обратный слеш
\
(например, "\\"
и "\""
) ,
- Комментарии допускаются с круглыми скобками в любом конце локальной части; Например,
john.smith(comment)@example.com
и (comment)john.smith@example.com
оба эквивалентны "john.smith@example.com"
, но john.(comment)smith@example.com
будут недействительными.
- Международные символы выше
U+007F
, закодированные как UTF-8, разрешены RFC 6531, хотя почтовые системы могут ограничивать какие символы использовать при назначении локальных частей.
и для глобальной / доменной части:
Часть имени домена в адресе электронной почты должна соответствовать строгим правилам: она должна соответствовать требованиям к имени хоста, состоящему из букв, цифр, дефисов и точек. Кроме того, доменная часть может быть литералом IP-адреса, заключенным в квадратные скобки, такие как jsmith@[192.168.2.1]
или jsmith@[IPv6:2001:db8::1]
[…]
Источник: Википедия
Что действительно?
Это может привести к странным, но действительным адресам электронной почты, подобным следующему:
localpart.ending.with.dot.@example.com
(comment)localpart@example.com
"this is v@lid!"@example.com
"much.more unusual"@example.com
postbox@com
admin@mailserver1
"()<>[]:,;\\@\"\\\\!#$%&\'*+-/=?^_`{}| ~.a"@example.org
" "@example.org
Источник: php.net / author gt@kani.hu - пример, исправленный автором этого поста
рамки
Существуют также локальные ограничения и ограничения длины домена:
Формат адресов электронной почты - это local-part@domain
когда локальная часть может иметь длину до 64 символов, а имя домена может содержать не более 253 символов, но максимальная длина 256 символов прямого или обратного пути ограничивает весь адрес электронной почты до быть не более 254 символов . [2] Формальные определения приведены в RFC 5322 (разделы 3.2.3 и 3.4.1) и RFC 5321 - с более читаемой формой, приведенной в информационном RFC 3696 [3] и связанных с ним ошибках. ,
Источник: Википедия
Ограничения WordPress
И вот что проверяет WordPress:
- Проверить на минимальную длину письма можно:
strlen( $email ) < 3
- Проверить наличие символа @ после первой позиции:
strpos( $email, '@', 1 ) === false
- Тест на недопустимые символы:
!preg_match( '/^[a-zA-Z0-9!#$%&\'*+\/=?^_`{|}~\.-]+$/', $local )
- Тест на последовательности периодов:
preg_match( '/\.{2,}/', $domain )
- Тест для ведущих и конечных периодов и пробелов:
trim( $domain, " \t\n\r\0\x0B." ) !== $domain
- Предположим, что в домене будет как минимум две подпрограммы:
$subs = explode( '.', $domain );
и затем
2 > count( $subs )
trim( $sub, " \t\n\r\0\x0B-" ) !== $sub
!preg_match('/^[a-z0-9-]+$/i', $sub )
Источник: WP Core v4.0
Фильтры и пользовательская проверка
Все вышеперечисленные случаи приведут is_email()
к возврату false. Результат может фильтроваться (обратный вызов может быть присоединен), и у фильтра будет три аргумента, где последний аргумент является причиной. Пример:
return apply_filters( 'is_email', false, $email, 'sub_hyphen_limits' );
Это означает, что вы можете переопределить результаты, возвращаемые определенными проверками.
Это позволяет добавлять специальные проверки, например, разрешать использование доменов Umlaut, частей домена только для TLD и т. Д.
Вывод
WordPress безопасен в большинстве случаев, но более ограничен, поскольку почтовые серверы должны соответствовать RFC. Имейте в виду, что не каждый почтовый сервер будет соответствовать рекомендациям RF 6531.
редактировать
Забавный побочный эффект: внутри есть две взаимосвязанные функции ~/wp-includes/formatting
: is_email()
и sanitize_email()
. Они практически одинаковые функции. Я понятия не имею, почему кто-то решил, что было бы неплохо скопировать содержимое функции из одного в другое, вместо того, чтобы просто добавить одно в качестве обратного вызова к фильтрам, которые предоставляет другой. Поскольку v0.71 и v1.5 совпадают, я лично буду использовать позже, когда вы получите очищенную строку. Обратите внимание, что даже говорится, что он не соответствует RFC.is_email()
sanitize_email()
is_email()