对于Html.CheckBoxFor,必需的Checkbox验证反向运行

时间:2017-09-13 02:37:45

标签: c# html asp.net-mvc razor checkbox

在我提交页面之前,我有一个复选框验证。但它反过来有效。当我选中框而不是相反时,它显示错误消息。我不知道我哪里做错了。

我的ViewModel

[Display(Name = "Terms and Conditions")]
[Range(typeof(bool), "true", "true", ErrorMessage = "Please accept Terms & Conditions")]
public bool IsTermsAccepted { get; set; }

我的观点

<div class="row col-lg-offset-2 top-buffer">
                @Html.CheckBoxFor(model => model.IsTermsAccepted)
                @Html.LabelFor(model => model.IsTermsAccepted)
            <br>@Html.ValidationMessageFor(model => model.IsTermsAccepted)
        </div>

感谢您的时间!

Edit1:我的跟踪与here

完全相同

Edit2:我能够通过添加一个简单的脚本来解决这个问题(如上面提到的链接所示)

<script>
// extend range validator method to treat checkboxes differently
var defaultRangeValidator = $.validator.methods.range;
$.validator.methods.range = function(value, element, param) {
    if(element.type === 'checkbox') {
        // if it's a checkbox return true if it is checked
        return element.checked;
    } else {
        // otherwise run the default validation function
        return defaultRangeValidator.call(this, value, element, param);
    }
}

1 个答案:

答案 0 :(得分:2)

您需要了解CheckBoxFor在ASP.NET MVC中的工作方式 - 以及复选框在HTML中的工作方式(请参阅我对此问题的回答:https://stackoverflow.com/a/11424091/159145

  • HTML复选框如果未选中,则不会在POST请求正文中发布其值。
  • 因此,为了区分&#34;复选框未检查&#34;和&#34;复选框排除&#34;你需要包含一个明确的&#34; false&#34;价值为<input type="hidden" />的{​​{1}}属性值与复选框输入相同。
  • ASP.NET MVC为您完成此操作:name=""同时呈现Html.CheckBoxFor() <input type="checkbox" value="true" />
    • 如果您查看网页的呈现HTML,您将同时看到它们。

因此,当您提交选中的复选框时,您的浏览器实际上会发送两个值:<input type="hidden" value="false" />true。它是导致false验证程序失败的"false"值,即使它还发送了Range值。

但是,true不够智能,无法处理使用RangeValidatorAttribute设置的布尔ViewModel属性的特定情况。

据我所知,没有内置的CheckBoxFor属性来处理这种情况 - 您需要在Controller Action中自己实现它,如下所示:

DataAnnotation

...或者你可以尝试自己实现一个新的验证属性,它需要做这样的事情。

请注意,它派生自[HttpPost] public IHttpActionResult Foo(FooViewModel model) { if( !model.IsTermsAccepted ) { this.ModelState.AddModelError( nameof(model.IsTermsAccepted), "you must accept the terms." ); return this.View( model ); } } 属性,因为您需要确保属性在请求正文中具有值(即复选框包含在响应中,隐藏输入) Required值存在。

true