Асинхронная валидация в Class-validator становится необходимой тогда, когда проверка значения не может быть выполнена в рамках локальной синхронной логики и требует обращения к внешним источникам данных или операциям, зависящим от задержек ввода-вывода. В отличие от синхронных правил, работающих исключительно с уже доступными значениями объекта, асинхронные проверки расширяют область валидации за пределы текущего контекста выполнения.
Одним из наиболее частых сценариев выступает проверка уникальности значений. Например, при регистрации пользователя требуется убедиться, что электронная почта или логин отсутствуют в базе данных.
Такая проверка невозможна без обращения к хранилищу данных:
Подобные операции являются асинхронными по своей природе и требуют ожидания результата запроса. Синхронная валидация здесь теряет смысл, так как не обладает актуальной информацией о состоянии системы.
Асинхронная валидация применяется при необходимости обращения к сторонним сервисам:
Такие запросы зависят от сетевых задержек и недетерминированного времени ответа, что делает их несовместимыми с синхронной моделью выполнения.
Некоторые правила валидации зависят от состояния системы, которое может изменяться независимо от текущего объекта:
В этих случаях данные нельзя считать локальными, поскольку их актуальность определяется внешним источником, который требует асинхронного запроса.
Асинхронная валидация часто используется при работе с токенами и криптографическими операциями:
Несмотря на то что часть криптографических операций может выполняться синхронно, сценарии с удалённой проверкой неизбежно требуют асинхронного подхода.
В микросервисной архитектуре данные часто распределены между несколькими сервисами. Проверка уникальности или согласованности может требовать:
Асинхронная валидация становится единственным способом обеспечить консистентность проверки в таких условиях.
Class-validator поддерживает асинхронные проверки через
пользовательские валидаторы, возвращающие
Promise<boolean>. Это позволяет интегрировать любые
операции, связанные с I/O.
Базовая структура асинхронного валидатора строится на
ValidatorConstraint:
import {
ValidatorConstraint,
ValidatorConstraintInterface,
ValidationArguments,
} from 'class-validator';
@ValidatorConstraint({ async: true })
class IsEmailAlreadyUsed implements ValidatorConstraintInterface {
async validate(email: string, args: ValidationArguments): Promise<boolean> {
const user = await database.users.findOne({ email });
return !user;
}
defaultMessage(args: ValidationArguments): string {
return 'Email уже используется';
}
}
Ключевым моментом является флаг async: true, который
определяет, что валидатор работает в асинхронном режиме. В этом случае
метод validate может возвращать Promise, а
выполнение всей цепочки валидации становится асинхронным.
Асинхронная модель в Class-validator влияет на поведение всей системы:
PromisevalidateSync игнорирует асинхронные
проверкиvalidate()Это означает, что при наличии хотя бы одного асинхронного правила весь процесс валидации становится асинхронным.
В реальных приложениях часто используется смешанный подход. Например:
Class-validator объединяет такие правила в единую цепочку, где синхронные проверки выполняются первыми, а асинхронные подключаются при необходимости обращения к внешним ресурсам.
Асинхронная валидация оказывает влияние на производительность за счёт увеличения количества I/O операций. Основные факторы:
Для снижения нагрузки часто применяются:
Синхронная валидация остаётся эффективной только в пределах локального контекста объекта. Как только правило выходит за границы текущих данных, возникает необходимость асинхронного подхода. Попытка реализовать такие проверки синхронно приводит к:
Асинхронная модель устраняет эти ограничения за счёт неблокирующего выполнения и возможности интеграции с внешними системами.
В типичных сценариях использования Class-validator асинхронные проверки привязываются к DTO-классам:
import { Validate } from 'class-validator';
class CreateUserDto {
@Validate(IsEmailAlreadyUsed)
email: string;
}
Такая интеграция позволяет декларативно описывать бизнес-правила, сохраняя отделение логики валидации от структуры данных.
Асинхронные валидаторы получают доступ к контексту через
ValidationArguments, что позволяет учитывать дополнительные
параметры:
Это даёт возможность строить сложные проверки, зависящие от нескольких полей или внешних условий, требующих запроса к сервисам или базам данных.