第23章 模型验证

----------------------------------------------

注:1.在web.config中,对system.web元素添加<globalization culture="en-US" uiCulture="en-US">来改变区域文件设置。

      2.DataType注解属性不能用于验证用户输入,只能对使用模板辅助器进行渲染提示。

  3.实现IValidatableObject接口验证模型类,不支持客户端验证

----------------------------------------------

模型验证(Model Validation):确保用户所接收的数据适合于绑定到模型,当不合适时,给用户提供反馈信息,以帮助修改问题的过程。

    过程:

    1.检查接收的数据,保持域模型完整性的方式之一。通过拒绝域环境中无意义的数据,防止应用程序出现奇怪的情况。

    2.帮助用户修正问题,给用户提供一些需要他们遵循的、与应用程序进行交互所需要的信息和工具。

重要:验证模型的原因是防止在存储库中放置劣质或无意义的数据。

一、明确地验证模型:

  1.设置复选框样式 :

    在~/Views/Shared/EditorTemplates/Boolean.cshtml中:

@model bool?

@if (ViewData.ModelMetadata.IsNullableValueType)
{
    @Html.DropDownListFor(m => m, new SelectList(new[] {"Not Set", "True", "False"}, Model))
}
else
{
    ModelState state = ViewData.ModelState[ViewData.ModelMetadata.PropertyName];
    bool value = Model ?? false;
    if (state != null && state.Errors.Count > 0)
    {
        <div class="input-validation-error" style="float: left">
            @Html.CheckBox("",value)
        </div>
    }
    else
    {
        @Html.CheckBox("",value)
    }
}

  2.显示验证消息:

@model ModelValidation.Models.Appointment

@{
    ViewBag.Title = "Make A Booking";
}

<h2>预约</h2>
@using (Html.BeginForm())
{
    @Html.ValidationSummary()

    <p>姓名:@Html.EditorFor(m => m.ClientName)</p>
    
    <p>预约日期:@Html.EditorFor(m => m.Date)</p>
    <p>@Html.EditorFor(m => m.TermAccepted)接收协议条款
       </p>  
    <input type="submit" value="预约"/>
}

有用的ValidationSummary辅助器重载方法

重载方法 描述
Html.ValidationSummary() 生成所有验证错误的摘要
Html.ValidationSummary(bool) true:只显示模型级错误。默认false:显示所有错误
Html.ValidationSummary(string) 在所有验证错误摘要之前加一条消息(string)
Html.ValidationSummary(bool,string) 在所有验证错误摘要之前加一条消息(string)true:只显示模型级错误

  显示属性级验证消息: 

@model ModelValidation.Models.Appointment

@{
    ViewBag.Title = "Make A Booking";
}

<h2>预约</h2>
@using (Html.BeginForm())
{
    @Html.ValidationSummary(true)
    <p>姓名:@Html.EditorFor(m => m.ClientName)@Html.ValidationMessageFor(m=>m.ClientName)</p>    
    <p>预约日期:@Html.EditorFor(m => m.Date)@Html.ValidationMessageFor(m=>m.Date)</p>
    <div>@Html.EditorFor(m => m.TermAccepted)接收协议条款
        @Html.ValidationMessageFor(m=>m.TermAccepted)</div>  
    <input type="submit" value="预约"/>
}

 二、默认模型绑定器中执行验证

DefaultModelBinder中对绑定过程添加验证的方法

方法 描述 默认实现
OnModelUpdated 在绑定器试图对模型对象中的所有属性进行赋值时调用 运用由模型元数据定义的验证规则,并用ModelState注册错误。
SetProperty 在绑定器对一个特定属性运用一个值时调用

如果该属性不能保存Null值,并且没有可用值时,

将用ModelState注册一条“The <name> fieldis required”的错误消息;

如果有一值,但不能进行解析,那会将注册“The value <value> is not validfor <name>”

  1.用元数据指定验证规则:

    public class Appointment  //  :IValidatableObject
    {
        [DisplayName("客户名称")]
        [Required]
        public string ClientName { get; set; }

        [DataType(DataType.Date)]
        [DisplayName("日期")]
        [Required(ErrorMessage = "请输入时间")]
        public DateTime Date { get; set; }
        [DisplayName("接受条款")]
        [Range(typeof(bool),"true","true",ErrorMessage = "必须接受协议条款")]  
        public bool TermAccepted { get; set; }

内建的验证注解属性

注解属性 示例 描述
Compare [Compare("MyOtherProperty)] 两个属性必须有同样的值。当要求用户对一个属性提供两个同样的值时,这是有用的。
Range [Range(10,20)] 一个数字值(实现IComparable的属性类型),取值范围,[Range(int.MinValue,50)]
RegularExpression [RegularExpression("pattern")] 一个字符串值,必须匹配的正则表达式模式。所有值,而不是子串。大小写不敏感:[RegularExpression("(?i)mypattern")]
Required [Required] 非空值。空格可以接受:[Required(AllowEmptyStrings=true)]
StringLength [StringLength(10)] 一个字符串值的最大长度,最小长度:[StringLength(10,MinimumLength=2)]

三、客户端验证

   启用:1.web.config中<AppSettings>

    <add key="ClientValidationEnabled" value="true" />
    <add key="UnobtrusiveJavaScriptEnabled" value="true" />

      2.引用三个JS库:

      jquery

      jquery.Validate

      jquery.validate.unobtrusive

四、远程验证:必须JosnResult类型,接收一个string参数,执行类型转换、解析或明确的模型绑定。

  1.动作方法: 

        public JsonResult ValidateDate(string date)
        {
            DateTime parseDate;
            if (!DateTime.TryParse(date, out parseDate))
            {
                return Json("请输入格式为“mm/dd/yyyy”的日期", JsonRequestBehavior.AllowGet);
            }
            else if(DateTime.Now>parseDate)
            {
                return Json("请输入一个未来时间以用来预约", JsonRequestBehavior.AllowGet);
            }
            else
            {
                return Json(true, JsonRequestBehavior.AllowGet);
            }
        }

  2.Remote注解属性:

        [Remote("ValidateDate","Home")] 
        public DateTime Date { get; set; }

源码:http://yunpan.cn/ccGAZD7d5QL6Z 访问密码 672a

原文地址:https://www.cnblogs.com/wjs5943283/p/4674626.html