Валидация строк в Vest строится на декларативных правилах, где каждое ограничение задаётся как отдельное утверждение. Такой подход позволяет комбинировать условия и получать детализированные сообщения об ошибках без усложнения логики проверки.
Строковые правила в основном реализуются через механизм
enforce, который предоставляет набор цепочечных методов для
описания ограничений.
Любая строковая проверка в Vest опирается на принцип:
Пример базовой проверки:
import { suite, test, enforce } from 'vest';
const validate = suite((data = {}) => {
test('username', 'Имя пользователя обязательно', () => {
enforce(data.username).isNotEmpty();
});
});
Здесь строка username проверяется на непустое
значение.
Одним из ключевых аспектов строковых правил является различие между
undefined, null и пустой строкой.
Vest рассматривает их как отдельные случаи:
undefined — значение не передано;null — явно отсутствующее значение;"" — строка существует, но не содержит символов.test('email', 'Email обязателен', () => {
enforce(data.email).isNotEmpty();
});
Метод isNotEmpty() учитывает все три состояния и
трактует их как нарушение.
Часто требуется исключить строки, содержащие только пробелы:
test('name', 'Имя не должно быть пустым', () => {
enforce(data.name).trim().isNotEmpty();
});
Метод trim() нормализует строку перед проверкой.
Длина строки — одно из наиболее частых ограничений валидации.
Vest предоставляет явные методы для контроля диапазона длины.
test('password', 'Минимальная длина пароля 8 символов', () => {
enforce(data.password).longerThanOrEquals(8);
});
test('title', 'Слишком длинный заголовок', () => {
enforce(data.title).shorterThanOrEquals(120);
});
Комбинация двух правил:
test('nickname', 'Никнейм должен быть от 3 до 20 символов', () => {
enforce(data.nickname).longerThanOrEquals(3);
enforce(data.nickname).shorterThanOrEquals(20);
});
Регулярные выражения являются основным инструментом проверки формата строки.
test('phone', 'Некорректный номер телефона', () => {
enforce(data.phone).matches(/^\+?[0-9]{10,15}$/);
});
test('email', 'Некорректный email', () => {
enforce(data.email).matches(/^[^\s@]+@[^\s@]+\.[^\s@]+$/);
});
Регулярные выражения позволяют описывать как простые, так и сложные форматы, включая коды, идентификаторы и пользовательские шаблоны.
Помимо формата, часто требуется анализ содержимого строки.
test('bio', 'Описание должно содержать ключевое слово', () => {
enforce(data.bio).contains('javascript');
});
test('code', 'Код должен начинаться с префикса JS-', () => {
enforce(data.code).startsWith('JS-');
});
test('filename', 'Файл должен быть HTML', () => {
enforce(data.filename).endsWith('.html');
});
Эти методы особенно полезны при работе с идентификаторами, путями и метаданными.
Строковые правила часто требуют предварительной очистки данных.
enforce(data.username).trim().isNotEmpty();
Хотя Vest не навязывает конкретную стратегию нормализации, часто используется предварительное преобразование:
const normalized = data.email?.toLowerCase();
test('email', 'Email некорректен', () => {
enforce(normalized).matches(/^[^\s@]+@[^\s@]+\.[^\s@]+$/);
});
Нормализация важна при сравнении строк, чувствительных к регистру.
Сила Vest заключается в возможности объединять правила без усложнения структуры.
test('username', 'Некорректное имя пользователя', () => {
enforce(data.username).isNotEmpty();
enforce(data.username).longerThanOrEquals(3);
enforce(data.username).shorterThanOrEquals(20);
enforce(data.username).matches(/^[a-zA-Z0-9_]+$/);
});
Каждое правило выполняется независимо, что позволяет точно определить причину ошибки.
При необходимости можно описывать собственные проверки.
test('slug', 'Slug должен быть уникальным форматом', () => {
enforce(data.slug).satisfies((value) => {
return /^[a-z0-9-]+$/.test(value);
});
});
Метод satisfies позволяет внедрять произвольную логику,
сохраняя совместимость с системой тестов Vest.
Строковые правила часто зависят от контекста данных.
test('vat', 'VAT обязателен для компаний', () => {
if (data.isCompany) {
enforce(data.vat).isNotEmpty();
}
});
Условная логика позволяет избегать избыточной валидации и адаптировать правила под структуру данных.
enforce(data.name).isNotEmpty();
Строка " " будет считаться валидной, если не
использовать trim().
Ошибкой является проверка длины без учёта нормализации:
enforce(data.input.length).greaterThan(5);
Корректнее использовать встроенные методы строки через
enforce.
Регулярные выражения часто усложняют поддержку кода. В Vest предпочтительнее комбинировать простые правила:
enforce(value).isNotEmpty();
enforce(value).longerThanOrEquals(3);
вместо одного сложного regex, если логика допускает разделение.
При увеличении количества полей важно разделять проверки по смысловым блокам.
suite('UserForm', (data = {}) => {
test('username', () => {
enforce(data.username).isNotEmpty();
});
test('email', () => {
enforce(data.email).matches(/^[^\s@]+@[^\s@]+\.[^\s@]+$/);
});
test('password', () => {
enforce(data.password).longerThanOrEquals(8);
});
});
Такой подход сохраняет читаемость и упрощает сопровождение логики валидации.