Обзор библиотеки FluentValidation. Часть 5. Условия
Вы можете задавать условия через методы расширения When
и Unless
для определения, должны ли выполняться все предыдущие валидаторы (до вызова метода расширения) либо конкретный валидатор в правиле RuleFor
. Применение метода расширения When
:
// Модель клиента
public class Customer
{
// Имя
public string? Forename { get; set; }
// Фамилия
public string? Surname { get; set; }
}
// Валидатор для модели клиента
public class CustomerValidator : AbstractValidator
{
public CustomerValidator()
{
// Оба свойства (Surname, Forename) должны быть заполнены, если заполнено одно из них
RuleFor(customer => customer.Surname)
.NotNull()
.When(customer => customer.Forename is not null);
RuleFor(customer => customer.Forename)
.NotNull()
.When(customer => customer.Surname is not null);
}
}
Метод расширения Unless
противоположность методу расширения When
, следующий пример кода вернёт тот же результат, что из примера выше, т. к. условие инвертировано:
// Модель клиента
public class Customer { ... }
// Валидатор для модели клиента
public class CustomerValidator : AbstractValidator
{
public CustomerValidator()
{
// Оба свойства (Surname, Forename) должны быть заполнены, если заполнено одно из них
RuleFor(customer => customer.Surname)
.NotNull()
.Unless(customer => customer.Forename is null);
RuleFor(customer => customer.Forename)
.NotNull()
.Unless(customer => customer.Surname is null);
}
}
По умолчанию FluentValidaton применяет условие When
, Unless
для всех предыдущих валидаторов в правиле RuleFor
. Если возникла необходимость указать условие к валидатору, который непосредственно предшествует методу расширения When
, Unless
нужно это явно указать через значение перечисления ApplyConditionTo.CurrentValidator
, которое передаётся вторым аргументом в метод расширения When
, Unless
, пример использования с методом расширения When
:
// Модель клиента
public class Customer
{
// Название организации
public string? OrgName { get; set; }
// Имя
public string? Forename { get; set; }
// Фамилия
public string? Surname { get; set; }
}
// Валидатор для модели клиента
public class CustomerValidator : AbstractValidator
{
public CustomerValidator()
{
// Должны быть заполнены поля Surname, Forename (одновременно) либо OrgName
RuleFor(customer => customer.Surname)
.NotNull()
.When(customer => customer.OrgName is null && customer.Forename is not null, ApplyConditionTo.CurrentValidator)
.Null()
.When(customer => customer.OrgName is not null && customer.Forename is null, ApplyConditionTo.CurrentValidator);
RuleFor(customer => customer.Forename)
.NotNull()
.When(customer => customer.OrgName is null && customer.Surname is not null, ApplyConditionTo.CurrentValidator)
.Null()
.When(customer => customer.OrgName is not null && customer.Surname is null, ApplyConditionTo.CurrentValidator);
RuleFor(customer => customer.OrgName)
.NotNull()
.When(customer => customer.Surname is null && customer.Forename is null, ApplyConditionTo.CurrentValidator)
.Null()
.When(customer => customer.Surname is not null && customer.Forename is not null, ApplyConditionTo.CurrentValidator);
}
}
Обратите внимание, что я выделил дополнительной табуляцией вызов метода расширения When
, т. к. указан аргумент ApplyConditionTo.CurrentValidator
, чтобы подчеркнуть принадлежность метода расширения When
только к предыдущему валидатору.
Если второй параметр ApplyConditionTo
явно не указан, он примет значение ApplyConditionTo.AllValidators
по умолчанию, которое означает, что условие применяется для всех предыдущих валидаторов в правиле RuleFor
.
Если возникла необходимость указать общее условие для группы правил RuleFor
, можно использовать метод When
«верхнего уровня» (из базового класса AbstractValidator
) вместо метода расширения When
, который крепится в конце правила либо валидатора:
// Модель клиента
public class Customer { ... }
// Валидатор для модели клиента
public class CustomerValidator : AbstractValidator
{
public CustomerValidator()
{
// Должны быть заполнены поля Surname, Forename (одновременно) либо OrgName.
// Если OrgName не заполнен, то
When(customer => customer.OrgName is null, () =>
{
// Surname должен быть заполнен
RuleFor(customer => customer.Surname)
.NotNull();
// Forename должен быть заполнен
RuleFor(customer => customer.Forename)
.NotNull();
// OrgName должен быть не заполнен
RuleFor(customer => customer.OrgName)
.Null();
})
// Otherwise выполняется в случае, если условие When не удовлетворено (false)
.Otherwise(() =>
{
// Surname должен быть не заполнен
RuleFor(customer => customer.Surname)
.Null();
// Forename должен быть не заполнен
RuleFor(customer => customer.Forename)
.Null();
// OrgName должен быть заполнен
RuleFor(customer => customer.OrgName)
.NotNull();
});
}
}
Вызов метода Otherwise
опционален, его можно вызывать непосредственно после вызова When
«верхнего уровня». Выполняется в случае, если условие When
не удовлетворено (false
).
← Предыдущая часть