【发布时间】:2020-06-27 10:30:39
【问题描述】:
我想实现流畅的验证,而无需重复验证相同的属性。我正在寻找一种可以重复使用验证的方法。
我有如下三个类,Customer 和 NewClass 都是一样的,只是 NewClass 继承了 PageRequest。
public sealed class Customer {
public int Id{get; set;}
public string FirstName {get; set;}
public string LastName {get; set;}
public string MiddleName {get; set;}
public string Address {get; set;}
}
public class PageRequest
{
public int CurrentPage {get; set;}
public int PerPage {get; set;}
public string SortBy {get; set;}
}
public class NewClass : PageRequest
{
public int Id{get; set;}
public string FirstName {get; set;}
public string LastName {get; set;}
public string MiddleName {get; set;}
public string Address {get; set;}
}
Fluent 验证如下:
public abstract class GetPaginatedDataRequestValidator<TRequest, TModel> : AbstractValidator<TRequest>
where TRequest : PageRequest
{
protected GetPaginatedDataRequestValidator()
{
var properties = typeof(TModel).GetProperties().Select(x => x.Name).ToList();
RuleFor(x => x.CurrentPage).Required().GreaterThan(0);
RuleFor(x => x.PerPage).Required().GreaterThan(0);
RuleFor(x => x.SortBy)
.Must(x => properties.Contains(x, StringComparer.OrdinalIgnoreCase))
.When(x => !string.IsNullOrEmpty(x.SortBy))
.WithMessage("{PropertyName} must be a known property name of a " + typeof(TModel).Name.Humanize());
}
}
public class NewClassValidator : GetPaginatedDataRequestValidator<
NewClass, SomeDto>
{
public NewClassValidator()
{
const string message = "At least one of either first name, last name, address and postcode are required.";
RuleFor(x => x.FirstName)
.Required()
.When(x => string.IsNullOrEmpty(x.LastName)
&& string.IsNullOrEmpty(x.Address) && string.IsNullOrEmpty(x.PostCode))
.WithMessage(message);
RuleFor(x => x.LastName)
.Required()
.When(x => string.IsNullOrEmpty(x.FirstName)
&& string.IsNullOrEmpty(x.Address) && string.IsNullOrEmpty(x.PostCode))
.WithMessage(message);
RuleFor(x => x.Address)
.Required()
.When(x => string.IsNullOrEmpty(x.LastName)
&& string.IsNullOrEmpty(x.FirstName) && string.IsNullOrEmpty(x.PostCode))
.WithMessage(message);
RuleFor(x => x.PostCode)
.Required()
.When(x => string.IsNullOrEmpty(x.LastName)
&& string.IsNullOrEmpty(x.Address) && string.IsNullOrEmpty(x.FirstName))
.WithMessage(message);
}
}
public class CustomerValidator : AbstractValidator<Customer>
{
public CustomerValidator()
{
const string message = "At least one of either first name, last name, address and postcode are required.";
RuleFor(x => x.FirstName)
.Required()
.When(x => string.IsNullOrEmpty(x.LastName)
&& string.IsNullOrEmpty(x.Address) && string.IsNullOrEmpty(x.PostCode))
.WithMessage(message);
RuleFor(x => x.LastName)
.Required()
.When(x => string.IsNullOrEmpty(x.FirstName)
&& string.IsNullOrEmpty(x.Address) && string.IsNullOrEmpty(x.PostCode))
.WithMessage(message);
RuleFor(x => x.Address)
.Required()
.When(x => string.IsNullOrEmpty(x.LastName)
&& string.IsNullOrEmpty(x.FirstName) && string.IsNullOrEmpty(x.PostCode))
.WithMessage(message);
RuleFor(x => x.PostCode)
.Required()
.When(x => string.IsNullOrEmpty(x.LastName)
&& string.IsNullOrEmpty(x.Address) && string.IsNullOrEmpty(x.FirstName))
.WithMessage(message);
}
}
您可以在客户和新类验证器中看到相同的属性验证。无论如何我可以创建一个自定义验证器并在 Customer 和 NewClass 验证器中重用?由于属性重复,是否需要对类结构进行任何修改?
【问题讨论】:
标签: c# fluentvalidation