Regex для валидации email: паттерны, которые действительно работают
Валидация email — один из самых распространённых случаев использования regex и один из самых непонятых. Спецификация RFC 5321 для email-адресов удивительно сложна, и ни одно регулярное выражение не может полностью её валидировать. Однако практические паттерны, покрывающие 99.9% реальных email-адресов, вполне достижимы и полезны.
Простой паттерн (достаточно хороший)
Для большинства приложений этот паттерн работает хорошо:
^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$
Что совпадает: один или более допустимых символов, за которыми следует @, затем домен с хотя бы одной точкой и доменом верхнего уровня из 2+ букв.
JavaScript:
const emailRegex = /^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$/;
emailRegex.test('user@example.com'); // true
emailRegex.test('user@.com'); // false
Протестируйте этот паттерн с помощью нашего Тестера regex.
Почему идеальная regex-валидация невозможна
Спецификация email (RFC 5321/5322) допускает структуры, которые формально валидны, но практически никогда не используются:
"john..doe"@example.com // Quoted local part with consecutive dots
user@[192.168.1.1] // IP address as domain
"very.(),:;<>[]".VERY."very@\ "very".unusual"@strange.example.com
Regex, обрабатывающий все RFC-валидные адреса, занимает тысячи символов и всё равно может не покрыть каждый граничный случай. Практичный подход: используйте простой regex для базовой проверки формата, а затем подтвердите существование email, отправив письмо с подтверждением.
Разбор паттерна
Локальная часть (до @)
[a-zA-Z0-9._%+-]+
- Буквы (верхний и нижний регистр)
- Цифры
- Точки, подчёркивания, проценты, плюсы, дефисы
- Один или более символов
Типичные ошибки:
- Допускаются точки в начале или конце (формально недопустимо)
- Допускаются последовательные точки (формально недопустимо без кавычек)
- Излишняя строгость (блокировка допустимых символов, таких как
+, используемый в Gmail-алиасах)
Доменная часть (после @)
[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}
- Буквенно-цифровые символы, точки, дефисы
- Минимум одна точка
- Домен верхнего уровня из 2+ буквенных символов
Типичные ошибки:
- Ограничение длины домена верхнего уровня до 3-4 символов (
.museum,.photographyсуществуют) - Запрет дефисов в доменных именах
- Неправильная обработка поддоменов (
user@mail.example.co.uk)
Улучшенные паттерны
Стандарт HTML5
Спецификация HTML5 определяет этот паттерн для <input type="email">:
^[a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$
Он более разрешительный в локальной части и более строгий в отношении длины доменных меток.
Рекомендуемый практический паттерн
^[^\s@]+@[^\s@]+\.[^\s@]{2,}$
Этот минимальный паттерн просто проверяет: нет пробелов, один @, хотя бы одна точка после @, домен верхнего уровня из 2+ символов. Он намеренно разрешителен — отсеивает очевидно ошибочный ввод, не отклоняя необычные, но валидные адреса.
Реализация на разных языках
JavaScript
function isValidEmail(email) {
// Basic regex check
const regex = /^[^\s@]+@[^\s@]+\.[^\s@]{2,}$/;
if (!regex.test(email)) return false;
// Additional checks
if (email.length > 254) return false; // RFC 5321 limit
const [local] = email.split('@');
if (local.length > 64) return false; // RFC 5321 limit
return true;
}
Python
import re
def is_valid_email(email: str) -> bool:
pattern = r'^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$'
if not re.match(pattern, email):
return False
if len(email) > 254:
return False
local, domain = email.rsplit('@', 1)
if len(local) > 64:
return False
return True
За пределами regex: правильная валидация email
Regex — это лишь первая линия обороны. Полная стратегия валидации:
- Проверка формата (regex): отклонение очевидно невалидных форматов
- Проверка длины: локальная часть ≤ 64 символа, общая ≤ 254 символа
- Проверка DNS: верификация наличия MX-записей у домена
- Обнаружение одноразовых email: блокировка временных почтовых сервисов при необходимости
- Письмо подтверждения: единственный способ по-настоящему проверить email — отправить сообщение и подтвердить, что пользователь его получил
// DNS MX record check (Node.js)
const dns = require('dns');
const [, domain] = email.split('@');
dns.resolveMx(domain, (err, addresses) => {
if (err || !addresses.length) {
console.log('Domain has no email server');
}
});
Типичные ошибки, которых следует избегать
- Излишне строгие паттерны: блокировка
user+tag@gmail.com(адресация с плюсом) илиuser@subdomain.example.com - Чувствительность к регистру: локальные части email могут быть регистрозависимыми по RFC, но на практике следует обрабатывать их как регистронезависимые
- Обрезка пробелов: всегда обрезайте пробелы перед валидацией —
" user@example.com "должен пройти проверку - Интернациональные домены:
.münchenи用户@例え.jpвалидны в интернационализированной электронной почте
Больше regex-паттернов в нашей Шпаргалке по regex.
FAQ
Нужно ли валидировать email с помощью regex на клиенте или на сервере?
На обоих. Клиентская валидация обеспечивает мгновенную обратную связь (лучший UX). Серверная валидация обязательна для безопасности (клиентские проверки можно обойти). Никогда не полагайтесь только на клиентскую валидацию.
Почему некоторые сайты отклоняют мой валидный email-адрес?
Причина обычно в чрезмерно строгих regex-паттернах. Адреса с + (Gmail-алиасы), длинными доменами верхнего уровня (.technology) или поддоменами часто отклоняются плохой валидацией. Если вы поддерживаете сайт, используйте разрешительный regex и верифицируйте с помощью письма подтверждения.
Связанные ресурсы
- Тестер regex — Тестируйте паттерны валидации email в реальном времени
- Шпаргалка по regex — Полный справочник по regex-паттернам
- Руководство по JSON Schema валидации — Валидация email-полей в JSON с format: email