我正在为Parent实体开发一个表单,其中包含一个Child实体列表。
在Parent.cshtml中,我使用foreeach在局部视图中渲染子项:
@foreach (var child in Model.Children)
{
Html.RenderPartial("_Child", child);
}
在_Child.cshtml中我使用此代码:
@using (Html.BeginCollectionItem("Children"))
{
@Html.EditorFor(model => Model.ValidatedProperty, new {htmlAttributes = new {@class = "form-control"}})
@Html.ValidationMessageFor(model => Model.ValidatedProperty, "", new {@class = "text-danger"})
}
当表单发回服务器时,我需要向Child.ValidatedProperty添加验证。 ValidatedProperty中的值必须按升序排序。 对于给定的Child实体,如果任何前面的Child实体在ValidatedProperty中具有更高的值,或者以下任何Child实体具有更低的值,则ValidatedProperty无效。
当我尝试实现这一点时,我遇到了以下问题:
当我尝试在控制器操作中验证并使用
时ModelState.AddModelError("Parent.Children.Child[" + i + "].ValidatedProperty", "Please enter a value between " + prev + " and " + next);
消息未出现在屏幕上。
当我尝试创建ValidationAttribute或使用IValidatableObject接口时,我无法访问前面和后面的Child实体,因此我无法从那里进行验证。
当我查看源代码时,我的ValidationMessage html节点具有以下标记:
<span class="field-validation-valid" data-valmsg-replace="true" data-valmsg-for="Children[533f90da-4c11-40ca-bb07-e3f6bcbd7260].ValidatedProperty"></span>
非常欢迎所有建议! 如果我需要提供更多信息,请告诉我您需要了解的内容。 谢谢!
P.S。这是我正在尝试做的简化版本,真正的验证比检查正确的顺序要复杂一点。
编辑: 似乎对Html.BeginCollection的调用是将Children [533f90da-4c11-40ca-bb07-e3f6bcbd7260]部分添加到验证元素的名称中。当我删除BeginCollection语句时,它出现为:
<span class="field-validation-valid" data-valmsg-replace="true" data-valmsg-for="ValidatedProperty"></span>
不幸的是,我需要BeginCollection语句来实现页面的其他功能。有没有办法让验证消息与BeginCollection一起使用?
解决:
当我使用类似teo van kot的EditorTemplate建议我可以删除BeginCollectionItem语句,并且每个Child现在都以数字而不是guid作为前缀。现在我的AddModelError语句正常工作。
答案 0 :(得分:2)
我不确定,但我猜你用Html.RenderPartial()
打破了绑定,这就是为什么当你用ModelState.AddModelError()
添加错误时它没有出现的原因。
我建议您使用EditorTemplate代替Html.RenderPartial()
。
您应该在EditorTemplates
中创建文件夹Views\Shared
,并为Model.Children
属性 创建强类型视图,其名称与您的Children
属性相同类型有 。
基本上,它与现在您在_Child
名称下的视图相同。
然后改变:
@foreach (var child in Model.Children)
{
Html.RenderPartial("_Child", child);
}
要:
@Html.EditorFor(x => x.Children)
请注意,您不需要设置模型IEnumerable<YourType>
或List<YourType>
,因为即使您传递集合,EditorTemplates也能正常工作。
现在所有绑定都没问题。您可以使用 F12 键在浏览器中进行检查,并检查您的ValidatedProperty
input
name
属性。然后,您就可以使用ModelState.AddModelError()
方法。
答案 1 :(得分:1)
根据索引评估集合,但您需要在模型中引用集合名称。基于标记的ValidationMessage,模型状态错误必须为:
ModelState.AddModelError("Parent[" + i + "].ValidatedProperty", "Please enter a value between " + prev + " and " + next);