FluentValidation 验证框架
验证
// 创建验证器
var validator = new CustomerValidator();
// 进行验证
var result = await validator.ValidateAsync(customer).ConfigureAwait(false);
this.SendLog($@"验证结果:{result.IsValid}");
// 能验证流程传递一些参数
var context = new ValidationContext<Customer>(customer) { RootContextData = { [@"data"] = new object() } };
var validationResult = await validator.ValidateAsync(context).ConfigureAwait(false);
// 进行验证,如果有错误,直接抛出异常
await validator.ValidateAndThrowAsync(customer).ConfigureAwait(false);
// 指定 options 参数,比如指定只验证指定的规则集
await validator.ValidateAsync(customer, options => options.IncludeRuleSets(@"sales").ThrowOnFailures())
.ConfigureAwait(false);
验证规则
public class CustomerValidator : AbstractValidator<Customer>
{
public CustomerValidator()
{
// 可以设置只有一项不符合规则就停止验证, 也可以只设置至某条规则
this.CascadeMode = CascadeMode.Stop;
// 一般的验证规则
this.RuleFor(x => x.Surname).NotEmpty().WithMessage(@"{PropertyName}, 值为 {PropertyValue} 不能为空");
this.RuleFor(x => x.Forename).NotEmpty().WithMessage(@"姓不能为空");
this.RuleFor(x => x.Address).NotEmpty().WithMessage(@"地址不能为空");
this.RuleFor(x => x.Products).NotEmpty().WithMessage(@"未设置产品");
// 针对数组内容,设置验证规则 , 并且可以使用 where 进行条件判断
this.RuleForEach(x => x.Products).Where(it => it.Name == "skip").NotNull().WithMessage(@"无效的产品信息");
// 设置复杂对象的验证器
var productValidator = new ProductValidator(); // 比如 ProductValidator : AbstractValidator<Product>
this.RuleForEach(x => x.Products).NotNull().SetValidator(productValidator);
// 设置规则集, 可以只验证指定规则集的规则。验证时使用 options.IncludeRuleSets 指定规则集
this.RuleSet(
"sales",
() => { this.RuleFor(x => x.Discount).LessThanOrEqualTo(0).WithMessage(@"折扣不能小于0"); });
// 设置达到指定条件时才验证,使用 when 进行指定
this.When(
x => x.Discount > 10,
() => { this.RuleFor(x => x.Products).Must(it => it.Count >= 10).WithMessage(@"产品数据必须大于 10"); });
// 使用 DependentRules 指定前置验证条件,只有前置验证通过后,才进行此条规则验证
this.RuleFor(it => it.Surname).MinimumLength(10)
.WithMessage(@"名称长度必须大于 10, 当前 {PropertyValue} 长度 {TotalLength}")
.DependentRules(() => this.RuleFor(it => it.Address));
// 获取通过 ValidationContext 中的 RootContextData 传入的一些参数
this.RuleFor(it => it.Surname).Custom(
(it, context) =>
{
var data = context.ParentContext.RootContextData[@"data"];
});
// 设置并调用扩展规则
public static IRuleBuilderOptions<T, IList<TElement>> ListMustContainFewerThan<T, TElement>(this IRuleBuilder<T, IList<TElement>> ruleBuilder, int num)
{
return ruleBuilder.Must(list => list.Count < num).WithMessage("The list contains too many items");
}
this.RuleFor(it => it.Products).ListMustContainFewerThan(10).WithMessage(@"产品数据必须大于 10");
// 使用自定义规则实现一些复杂的验证规则 , NamePropertyValidator : PropertyValidator
this.RuleFor(it => it.Surname).SetValidator(new NamePropertyValidator());
}
protected override bool PreValidate(ValidationContext<Customer> context, ValidationResult result)
{
// 在验证前进行数据校验,返回 true 才进行下一步的验证
if (context.InstanceToValidate == null)
{
result.Errors.Add(new ValidationFailure(string.Empty, @"请设置有效对象"));
return false;
}
return base.PreValidate(context, result);
}
}
与其它框架整合
https://www.xcode.me/post/5849#
https://docs.fluentvalidation.net/en/latest/index.html