如何为复杂属性将FluentValidation错误映射到ModelState?
在.NET 7 Razor Pages中解决FluentValidation复杂属性验证错误映射问题
在.NET 7 Razor Pages项目中使用FluentValidation 11.4.0时,手动验证并将错误复制到ModelState字典时,简单属性可以正常配合asp-validation-for显示错误,但嵌套/复杂属性必须在ModelState键前加上类名前缀(比如Sample.TestValue)才能让asp-validation-for="Sample.TestValue"生效。手动拼接类名和属性名虽然能解决,但代码不够优雅,以下是两种更规范的实现方式:
方案1:通过ValidationContext指定根属性前缀
FluentValidation的Validate方法支持传入自定义ValidationContext,通过设置上下文的根属性名称,让验证错误的PropertyName自动带上前缀,无需手动拼接。
修改后台IndexModel的OnPost方法:
public void OnPost() { var validator = new SampleValidator(); // 创建验证上下文并指定根属性前缀为Sample var validationContext = new ValidationContext<Sample>(Sample) { RootContextData = { ["PropertyChain.RootPropertyName"] = nameof(Sample) } }; var result = validator.Validate(validationContext); foreach (var error in result.Errors) { this.ModelState.AddModelError(error.PropertyName, error.ErrorMessage); } }
此时验证错误的PropertyName会自动生成为Sample.TestValue,直接添加到ModelState后,asp-validation-for="Sample.TestValue"就能正常匹配并显示错误。
方案2:注册FluentValidation服务实现自动验证(推荐)
更符合ASP.NET Core最佳实践的方式是注册FluentValidation服务,让框架自动处理验证逻辑和错误映射,完全无需手动编写验证代码。
步骤1:安装依赖包
确保已安装FluentValidation.AspNetCore NuGet包:
Install-Package FluentValidation.AspNetCore
步骤2:在Program.cs中注册服务
builder.Services.AddRazorPages() .AddFluentValidation(config => { // 自动注册当前程序集中的所有验证器 config.RegisterValidatorsFromAssemblyContaining<SampleValidator>(); // 启用自动验证,框架会自动执行验证并将错误映射到ModelState config.AutomaticValidationEnabled = true; });
步骤3:简化PageModel代码
移除手动验证逻辑,框架会自动完成验证:
public class IndexModel : PageModel { [BindProperty] public Sample Sample { get; set; } public IActionResult OnPost() { if (!ModelState.IsValid) { return Page(); } // 验证通过后的业务逻辑处理 return RedirectToPage(); } public void OnGet() { } }
前端HTML代码(无需修改)
<form method="post"> <div asp-validation-summary="All"></div> <input type="text" asp-for="Sample.TestValue" /> <span asp-validation-for="Sample.TestValue"></span> <button type="submit">提交</button> </form>
内容的提问来源于stack exchange,提问作者Victorio Berra
相关产品推荐
相关产品推荐

