我想弄清楚为什么我的FluentValidation
不会不引人注意地验证我的一些View Model属性。
我通过NuGet安装了MVC3的FluentValidation包:
Install-Package FluentValidation.MVC3
结果:
<package id="FluentValidation" version="5.0.0.1" targetFramework="net45" />
<package id="FluentValidation.MVC3" version="5.0.0.1" targetFramework="net45" />
未验证的属性是在我的View模型中声明的 Guitar 类对象的某些成员。 Guitar.ProductionYear属性获取不显眼的验证代码,但吉他对象的其他2个属性不是。
public Guitar Guitar1 { get; set; }
public Guitar Guitar2 { get; set; }
public Guitar Guitar3 { get; set; }
我阅读了FluentValidation文档,现在特别关注limitations regarding FluentValidation's client-side validation of lists,但这不是一个列表,所以我希望有人可以看到错误和/或提供一些建议。
我也尝试使用自定义吉他对象验证器,但仍然得到相同的结果
观察
示例
<!-- Unobtrusive JS generated-->
<input type="text" value="" name="FirstName" id="FirstName" data-val-required="'First Name' must not be empty." data-val="true" class="input-validation-error">
<div class="messageBottom">
<span data-valmsg-replace="true" data-valmsg-for="FirstName" class="field-validation-error"><span for="FirstName" generated="true" class="">'First Name' must not be empty.</span>
</span>
</div>
<!-- Unobtrusive JS Partially generated for Guitar object-->
<input type="text" value="" name="Guitar.Make" id="Guitar_Make" placeholder="Make">
<div class="messageBottom">
<span data-valmsg-replace="true" data-valmsg-for="Guitar1.Make" class="field-validation-valid"></span>
</div>
<input type="text" value="" name="Guitar1.Model" id="Guitar1_Model" placeholder="Model">
<div class="messageBottom">
<span data-valmsg-replace="true" data-valmsg-for="Guitar1.Model" class="field-validation-valid"></span>
</div>
<input type="text" value="" name="Guitar1.ProductionYear" id="Guitar1_ProductionYear" data-val-number="The field ProductionYear must be a number." data-val="true" placeholder="Production Year" class="valid">
<div class="messageBottom">
<span data-valmsg-replace="true" data-valmsg-for="Guitar1.ProductionYear" class="field-validation-valid">
</span>
</div>
由于
的Global.asax.cs
FluentValidationModelValidatorProvider.Configure();
视图模型
[FluentValidation.Attributes.Validator(typeof(CustomerViewModelValidator))]
public class CustomerViewModel
{
[Display(Name = "First Name")]
public string FirstName { get; set; }
[Display(Name = "Last Name")]
public string LastName { get; set; }
[Display(Name = "Phone")]
public string Phone { get; set; }
[Display(Name = "Email")]
public string EmailAddress { get; set; }
[Display(Name = "Guitar 1")]
public Guitar Guitar1 { get; set; }
[Display(Name = "Guitar 2")]
public Guitar Guitar2 { get; set; }
[Display(Name = "Guitar 3")]
public Guitar Guitar3 { get; set; }
}
自定义吉他对象验证器
public class GuitarValidator : AbstractValidator<Guitar>
{
public GuitarValidator()
{
RuleFor(x => x.Make).NotEmpty();
RuleFor(x => x.Model).NotEmpty();
RuleFor(x => x.ProductionYear).NotEmpty();
}
}
查看模型验证程序
public class CustomerViewModelValidator : AbstractValidator<CustomerViewModel>
{
public CustomerViewModelValidator()
{
RuleFor(x => x.FirstName).NotNull();
RuleFor(x => x.LastName).NotNull();
RuleFor(x => x.Phone).NotNull();
RuleFor(x => x.EmailAddress).NotNull();
//1st Guitar Object is Required
RuleFor(x => x.Guitar).SetValidator(new GuitarValidator());
}
}
视图
<!-- Guitar Object #1 -->
<div id="cosponsorsTemplate_1">
<div class="formColumn1">@Html.LabelFor(x=>x.Guitar1)</div>
<div class="formColumn2">@Html.TextBoxFor(x => x.Guitar1.Make, new { Placeholder = "Make" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar1.Make)</div>
</div>
<div class="formColumn3">@Html.TextBoxFor(x => x.Guitar1.Model, new { Placeholder = "Model" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar1.Model)</div>
</div>
<div class="formColumn4">@Html.TextBoxFor(x =>x.Guitar1.ProductionYear, new { Placeholder = "Production Year" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar1.ProductionYear)</div>
<a class="icon delete" data-delete-id="1">Delete</a>
</div>
</div>
<!-- Guitar Object #2 -->
<div id="cosponsorsTemplate_2">
<div class="formColumn1">@Html.LabelFor(x=>x.Guitar2)</div>
<div class="formColumn2">@Html.TextBoxFor(x => x.Guitar2.Make, new { Placeholder = "Make" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar2.Make)</div>
</div>
<div class="formColumn3">@Html.TextBoxFor(x => x.Guitar2.Model, new { Placeholder = "Model" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar2.Model)</div>
</div>
<div class="formColumn4">@Html.TextBoxFor(x => x.Guitar2.ProductionYear, new { Placeholder = "Production Year" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar2.ProductionYear)</div>
<a class="icon delete" data-delete-id="2">Delete</a>
</div>
</div>
<!-- Guitar Object #3 -->
<div id="cosponsorsTemplate_3">
<div class="formColumn1">@Html.LabelFor(x=>x.Guitar3)</div>
<div class="formColumn2">@Html.TextBoxFor(x => x.Guitar3.Make, new { Placeholder = "Make" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar3.Make)</div>
</div>
<div class="formColumn3">@Html.TextBoxFor(x => x.Guitar3.Model, new { Placeholder = "Model" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar3.Model)</div>
</div>
<div class="formColumn4">@Html.TextBoxFor(x => x.Guitar3.ProductionYear, new { Placeholder = "Production Year" })
<div class="messageBottom">@Html.ValidationMessageFor(x => x.Guitar3.ProductionYear)</div>
<a class="icon delete" data-delete-id="3">Delete</a>
</div>
</div>
答案 0 :(得分:2)
文档说明复杂的图形应该使用专门的验证器。您可以这样使用它:
public class Customer {
public string Name { get; set; }
public Address Address { get; set; }
}
public class Address {
public string Line1 { get; set; }
public string Line2 { get; set; }
public string Town { get; set; }
public string County { get; set; }
public string Postcode { get; set; }
}
public class AddressValidator : AbstractValidator<Address> {
public AddressValidator() {
RuleFor(address => address.Postcode).NotNull();
//etc
}
}
public class CustomerValidator : AbstractValidator<Customer> {
public CustomerValidator() {
RuleFor(customer => customer.Name).NotNull();
RuleFor(customer => customer.Address).SetValidator(new AddressValidator())
}
}
自: 重复使用复杂属性的验证器
http://fluentvalidation.codeplex.com/wikipage?title=CreatingAValidator&referringTitle=Documentation
对于您的用例,您将为聚合对象创建Guitar Validator和模型验证器。我记得有一个朋友遇到类似的问题,因为验证器不知道如何在没有中间验证器的情况下遍历对象图。
答案 1 :(得分:0)
我想出了这个问题。
吉他课
public class Guitar
{
public string Model { get; set; }
public int? ProductionYear { get; set; }
public string Make { get; set; }
}
需要验证器类型装饰器
[Validator(typeof(GuitarValidator))]
<强>正确强>
[Validator(typeof(GuitarValidator))]
public class Guitar
{
public string Model { get; set; }
public int? ProductionYear { get; set; }
public string Make { get; set; }
}