Регулярные выражения для проверки данных пользователей

Регулярные выражения — мощный инструмент для поиска, сопоставления и простого парсинга текста. Их удобно использовать для быстрой валидации полей формы и базовых правил на стороне клиента и сервера. Правильно составленные шаблоны помогут отсекать недопустимые значения и уменьшат количество ошибок и уязвимостей.
Ниже приведены практические шаблоны и рекомендации для распространённых типов данных. Код-образцы даны на Python и JavaScript — их можно адаптировать под другие языки и инструменты.
Содержание
- Проверка имени пользователя
- Проверка email
- Оценка силы пароля
- Валидация даты в формате mm/dd/yyyy
- Проверка пустой строки
- Проверка ZIP-кода (США)
- Когда regex не подходит
- Альтернативные подходы
- Методология тестирования и чеклисты
- Краткое резюме и ключевые выводы
Проверка имени пользователя
Условие для валидного имени пользователя в примере:
- Длина: от 5 до 15 символов (можно изменить диапазон в regex).
- Строка содержит только буквы, цифры и/или символ подчёркивания (_).
- Первый символ — буква (латинская).
Шаблон (подходит для латинских символов):
^[A-Za-z]\w{4,14}$Пояснение: ^ и $ ограничивают начало и конец строки; [A-Za-z] требует букву первым символом; \w означает [A-Za-z0-9_]; {4,14} добавляет от 4 до 14 символов после первой буквы, суммарно 5–15.
Пример на Python:
import re
def checkUsername(username):
regex = "^[A-Za-z]\\w{4,14}$"
r = re.compile(regex)
if (re.search(r, username)):
print("Valid")
else:
print("Not Valid")
username1 = "yuvraj_chandra"
checkUsername(username1)
username2 = "ja7&^%87"
checkUsername(username2)Результат: первый пример валиден, второй — нет.
Пример на JavaScript:
function checkUsername(user) {
if(/^[A-Za-z][A-Za-z0-9_]{4,14}$/.test(user)) {
console.log('Valid');
} else {
console.log('Not Valid');
}
}
checkUsername('yuvraj_chandra');
checkUsername('ja7&^%87');Важно: если вы поддерживаете локализованные имена (не только латиницу), замените класс символов на соответствующий Unicode-диапазон или используйте флаги/модули, поддерживающие Unicode.
Проверка email
Общая оговорка: универсального «идеального» regex для email не существует — многое зависит от вашей политики допустимых форматов. Ниже — практичный шаблон, который покрывает большинство обычных адресов.
Условия примера:
- Локальная часть (до @) содержит буквы, цифры, подчёркивания, дефисы и точки.
- Один символ @ обязателен.
- Доменная часть содержит один или несколько уровней домена, разделённых точками.
- Расширение домена (последняя часть) — 2–4 символа.
Шаблон:
^[\w.-]+@([\w-]+\.)+[\w-]{2,4}$Пример на Python:
import re
def checkEmailId(email):
regex = "^[\\w.-]+@([\\w-]+\\.)+[\\w-]{2,4}$"
r = re.compile(regex)
if (re.search(r, email)):
print("Valid")
else:
print("Not Valid")
email1 = "abc@gmail.com"
checkEmailId(email1)
email2 = "abc@def@gmail.kahscg"
checkEmailId(email2)Результат: первый email валиден, второй — нет.
Пример на JavaScript:
function checkEmailId(email) {
if (/^[\w.-]+@([\w-]+\.)+[\w-]{2,4}$/.test(email)) {
console.log('Valid');
} else {
console.log('Not Valid');
}
}
checkEmailId("abc@gmail.com");
checkEmailId("abc@def@gmail.kahscg");Замечания:
- Этот шаблон не покроет все валидные в RFC адреса (например, адреса с кавычками в локальной части или более длинными TLD).
- Если необходима строгая проверка по стандарту RFC5322, лучше комбинировать regex с библиотечными валидаторами и/или проверкой MX-записи DNS.
Оценка силы пароля
Для безопасности часто требуют, чтобы пароль содержал минимум набор классов символов.
Условия примера:
- Минимум 8 символов.
- Как минимум одна цифра.
- Как минимум одна заглавная буква.
- Как минимум одна строчная буква.
- Как минимум один специальный символ (не буква и не цифра).
Шаблон:
(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[^A-Za-z0-9])(?=.{8,})Пример на Python:
import re
def checkPasswordStrength(password):
regex = "(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[^A-Za-z0-9])(?=.{8,})"
r = re.compile(regex)
if (re.search(r, password)):
print("Strong Password")
else:
print("Weak Password")
password1 = "Hiuahd$5jawd"
checkPasswordStrength(password1)
password2 = "my_password"
checkPasswordStrength(password2)Пример на JavaScript:
function checkPasswordStrength(password) {
if (/(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[^A-Za-z0-9])(?=.{8,})/.test(password)) {
console.log('Strong Password');
} else {
console.log('Weak Password');
}
}
checkPasswordStrength('Hiuahd$5jawd');
checkPasswordStrength('my_password');Важно: даже сильный по метрике regex пароль может быть слабым (например, популярные фразы с требуемыми символами). Рекомендуется дополнять проверки блок-листами популярных паролей и использовать оценщики энтропии.
Валидация даты в формате mm/dd/yyyy
Шаблон для быстрой проверки формата (не проверяет реальную корректность всех календарных дат):
^(0[1-9]|1[012])[- /.](0[1-9]|[12][0-9]|3[01])[- /.](19|20)\d\d$Пояснение: шаблон проверяет корректность месяца (01–12) и дня (01–31) и год в 1900–2099.
Пример на Python:
import re
def checkDateFormat(date):
regex = "^(0[1-9]|1[012])[- /.](0[1-9]|[12][0-9]|3[01])[- /.](19|20)\\d\\d$"
r = re.compile(regex)
if(re.search(r, date)):
print("Valid")
else:
print("Not Valid")
date1 = "03/21/2002"
checkDateFormat(date1)
date2 = "15/21/2002"
checkDateFormat(date2)Ограничение: шаблон не отсекает невозможные даты вроде 02/30 или 04/31. Для точной валидации используйте парсинг с календарными функциями (например, datetime в Python или Date в JavaScript) и обработкой исключений.
Пример на JavaScript:
function checkDateFormat(date) {
if(/^(0[1-9]|1[012])[- /.](0[1-9]|[12][0-9]|3[01])[- /.](19|20)\d\d$/.test(date)) {
console.log('Valid');
} else {
console.log('Not Valid');
}
}
checkDateFormat('03/21/2002');
checkDateFormat('15/21/2002');Проверка пустой строки
Шаблон для точного определения пустой строки:
^$Пример на Python:
import re
def checkEmptyString(str):
regex = "^$"
r = re.compile(regex)
if (re.search(r, str)):
print("The given string is empty")
else:
print("The given string is not empty")
str1 = ""
checkEmptyString(str1)
str2 = "This is not an empty string"
checkEmptyString(str2)Пример на JavaScript:
function checkEmptyString(str) {
if (/^$/.test(str)) {
console.log('The given string is empty');
} else {
console.log('The given string is not empty');
}
}
checkEmptyString('');
checkEmptyString('This is not an empty string');Примечание: часто нужно также отсекать строки, содержащие только пробелы — для этого используйте проверку вида /^\s*$/ или предварительно trim().
Проверка ZIP-кода (США)
Шаблон, поддерживающий пять цифр и формат ZIP+4:
^[0-9]{5}(?:-[0-9]{4})?$Пример на Python:
import re
def validateZIPCode(code):
regex = "^[0-9]{5}(?:-[0-9]{4})?$"
r = re.compile(regex)
if (re.search(r, code)):
print("Valid")
else:
print("Not Valid")
code1 = "76309"
validateZIPCode(code1)
code2 = "83468-2348"
validateZIPCode(code2)
code3 = "234445"
validateZIPCode(code3)Результат: первые две строки валидны, третья — нет.
Пример на JavaScript:
function validateZIPCode(code) {
if (/^[0-9]{5}(?:-[0-9]{4})?$/.test(code)) {
console.log('Valid');
} else {
console.log('Not Valid');
}
}
validateZIPCode('76309');
validateZIPCode('83468-2348');
validateZIPCode('234445');Когда регулярные выражения не подходят
- Проверка сложных требований формата email (полный RFC): regex слишком громоздкий и ошибкоопасен.
- Валидация календарных дат с проверкой вискосных годов и числа дней в месяце — лучше использовать парсер даты.
- Сложная бизнес-логика (например, взаимосвязанные поля формы) — реализуйте в коде, а не одной строкой regex.
- Нужен международный ввод (имена с диакритикой, многобайтовые символы) — используйте Unicode-aware regex и/или специализированные библиотеки.
Альтернативные подходы и рекомендации
- Используйте библиотечные валидаторы (например, email-validator, validator.js) для надёжной валидации.
- Для паролей комбинируйте regex с оценкой по словарю популярных паролей и вычислением энтропии.
- Для дат и времени применяйте парсеры (datetime, moment, date-fns) и проверяйте логические отношения (например, дата окончания позже даты начала).
- Для адресов и почтовых индексов используйте API или библиотеки, учитывающие локальные форматы и правила.
Методология тестирования и чеклист
Мини-методология (быстрый набор шагов для QA и разработчиков):
- Определите требования формата и границы допустимых значений.
- Составьте позитивные и негативные тест-кейсы (см. ниже).
- Автоматизируйте тесты (юнит-тесты и интеграционные тесты).
- Проверяйте перекрёстно: client-side + server-side.
- Регулярно обновляйте тесты при изменении требований.
Чеклист для разработчика:
- Regex читаем и документирован.
- Есть примеры валидных и невалидных значений.
- Добавлены юнит-тесты.
- Защита от ReDoS (см. раздел «Риски»).
- Client-side/Server-side проверки согласованы.
Чеклист для QA:
- Позитивные тесты (валидные примеры).
- Негативные тесты (невалидные варианты).
- Граничные значения (минимальная/максимальная длина).
- Тесты на пользовательский ввод с пробелами и Unicode.
Примеры тест-кейсов (скорые тестовые строки):
- Имя пользователя: “Anna_01” (валидное), “1Anna” (невалидное), “abcd” (слишком короткое), строка из 16 латинских символов (слишком длинная).
- Email: “user.name+tag@example.co” (в зависимости от политики может быть валидным), “user@@example.com” (невалидный).
- Пароль: “P@ssw0rd” (валидный), “password” (недостаточно классов символов).
- Дата: “02/29/2020” (валидная — високосный год), “02/29/2019” (невалидная).
Риски и рекомендации по безопасности
- ReDoS (Regular Expression Denial of Service): некоторые сложные регулярные выражения с бэктреккингом уязвимы к экспоненциальному времени обработки. Тестируйте производительность на длинных строках и используйте упрощённые шаблоны.
- Не полагайтесь только на client-side валидацию — проверяйте ввод и на сервере.
- Для персональных данных учитывайте требования локального законодательства (например, в Европе — GDPR) при логировании и хранении входных данных.
Важно: валидатор не должен сохранять приватные данные в логах. Логи должны анонимизировать чувствительные поля.
Дерево принятия решения — когда использовать regex
flowchart TD
A[Начало: нужно валидировать поле?] --> B{Это формат-ориентированное правило?}
B -- Да --> C[Используйте regex + юнит-тесты]
B -- Нет --> D[Реализуйте валидацию в коде/бизнес-логике]
C --> E{Нужна точная календарная проверка?}
E -- Да --> D
E -- Нет --> F[Добавьте тесты на производительность и ReDoS]
F --> G[Client + Server проверки]
D --> GКраткая терминология
- Regex: регулярное выражение — строка-шаблон для поиска/сопоставления текста.
- Локальная часть email: часть до символа @.
- TLD: домен верхнего уровня (например, com, org).
Роль‑ориентированные рекомендации
- Для фронтенда: применяйте простые и быстрые шаблоны, показывайте понятные сообщения пользователю, синхронизируйте правила с бэкендом.
- Для бэкенда: критичные проверки, защита от ReDoS, дополнительные проверки на сервере.
- Для QA: автоматизируйте тесты, проверяйте границы, Unicode и длинные строки.
Когда regex не справится — примеры и контрпримеры
- Контрпример: валидация email для всех случаев RFC5322 потребует чрезмерно сложного regex — лучше использовать специализированную библиотеку.
- Контрпример: проверка, что дата является рабочим днём — это бизнес-логика, регулярные выражения не подойдут.
Социальные подсказки
OG-заголовок и описание для превью: используйте краткое описание формата проверки и упоминание примеров на Python/JS.
Резюме
- Регулярные выражения удобны для базовой и быстрой валидации формата данных.
- Для критичных или сложных проверок комбинируйте regex с библиотеками и логикой на сервере.
- Всегда покрывайте валидаторы тестами и учитывайте риски ReDoS.
Ключевые выводы:
- Regex хорош для формата, но не для полной логики.
- Синхронизируйте правила между клиентом и сервером.
- Тестируйте и защищайтесь от экспоненциальных затрат на обработку.
Похожие материалы
Приостановить Family Bell в Google Assistant
Исправить SMBus Controller в Диспетчере устройств
Как отменить root на Android быстро
Отключить автозагрузку фото в WhatsApp
Переслать изображение WhatsApp с подписью