ASP.NET MVC 入门 -- 8、ModelState与数据验证

ASP.NET MVC 入门8、ModelState与数据验证 原帖地址:http://www.cnblogs.com/QLeelulu/archive/2008/10/08/1305962.html 阅读详情

 

ViewData有一个ModelState的属性,这是一个类型为ModelStateDictionary的ModelState类型的字典集合。在进行数据验证的时候这个属性是比较有用的。在使用Html.ValidationMessage()的时候,就是从ViewData.ModelState中检测是否有指定的KEY,如果存在,就提示错误信息。例如在前一篇文章ASP.NET MVC 入门7、Hellper与数据的提交与绑定中使用到的UpdateModel方法:

image

我们在View中使用Html.ValidationMessage(string modelName)来对指定的属性进行验证:

image

Html.ValidationMessage()有几个重载:

image

其中ValidationSummary()是用于显示全部的验证信息的。跟ASP.NET里面的ValidationSummary验证控件差不多。

我们测试一下/Admin/Setting页面:

image

在用UpdateModel方法更新BlogSettings.Instance.PostsPerPage的时候,当我们如图所示填写"10d"的时候,由于PostsPerPage为整型的,所以UpdateModel方法就会出错,同时会往ViewData.ModelState添加相应的错误信息,从而Html.ValidationMessage()方法就可以从ViewData.ModelState中检测到错误并提示。同时Html.ValidationMessage()方法会为出错的属性的输入框添加一个名为"input-validation-error"的CSS类,同时后面的提示信息的CSS类名为"field-validation-error":

image

CSS类的样式是可以由我们自己自由定义的。如上图的红色高亮显示。

好,下面我们来实现发表新随笔的功能。我们先写一个提供用户输入随笔内容的表单页面:

<p>
   
<label for="Title">标题</label>
   
<% = Html.TextBox( " Title " , new { id =   " Title " , @class =   " required " }) %>
   
<% = Html.ValidationMessage( " Title " ) %>
</p>
<p>
   
<label for="Content">内容</label>
   
<% = Html.TextArea( " Content " ) %>
   
<% = Html.ValidationMessage( " Content " ) %>
</p>
<p>
   
<label for="Slug">URL地址别名(如果为空则和标题同名)</label>
   
<% = Html.TextBox( " Slug " , new { id =   " Slug " , @class =   " required " }) %>
   
<% = Html.ValidationMessage( " Slug " ) %>
</p> 

 

然后我们对用户提交过来的数据进行保存:

[AcceptVerbs("POST"), ActionName("NewPost" )]
public
ActionResult SaveNewPost(FormCollection form)
{
    Post post
= new
Post();

   
try

    {
        UpdateModel(post,
new[] { "Title", "Content", "Slug" });
    }
   
catch

    {
       
return View(post);
    }

    post.Save();
   
return ShowMsg(new List<string>() { "发表新随笔成功"
});
}

 

由于这三个值都是字符串类型,所以如果值为空的话,UpdateModel也是不会出错的,而我们的Title和Content是不允许为空的,或者我们想我们的Slug的长度不能超过100,也就是需要有我们自己的业务规则。这时候我们或许会这样写:

try
{
    UpdateModel(post,
new[] { "Title", "Content", "Slug" });
}
catch

{
   
return View(post);
}

if (string
.IsNullOrEmpty(post.Title))
{
    ViewData.ModelState.AddModelError(
"Title", post.Title, "标题不能为空"
);
}
if (string
.IsNullOrEmpty(post.Content))
{
    ViewData.ModelState.AddModelError(
"Content", post.Content, "内容不能为空"
);
}

if (!
ViewData.ModelState.IsValid)
{
   
return
View(post);
}

 

ViewData.ModelState提供了一个AddModelError的方法,方便我们添加验证失败的信息。我们可以如上代码这样进行对象的业务规则验证,但是一旦业务规则多了,这样的代码是非常壮观的,而且不好控制。那么我们该怎么更好的进行业务规则的验证呢?得意于BlogEngine.Net的良好架构,我们可以很轻松的完成这一点。

首先,让我们修改一下BlogEngine.Core里面BusinessBase的代码。我们前面说过,BusinessBase实现了IDataErrorInfo接口,该接口有个索引器,导致ViewData.Eval()方法调用时搜索索引器的值时返回String.Empty而使ViewData.Eval()认为是找到值了,从而失效。

image

我们可以将return string.Empty修改为return null。但我们这里并不需要用到这个接口,所以我们把该接口去掉,并把相应的代码注释了。然后我们再暴露一个BrokenRules的属性,用于返回当前的所有破坏性业务规则(红框部分代码为我们添加的):

image

BusinessBase提供了一个抽象的ValidationRules方法,用于在业务类重写这个方法往里面添加验证规则(具体请看BusinessBase的Validation节)。

Validation

 

我们在Post类中重写这个方法来添加验证规则:

image

然后我们可以在Controller的Action中很优雅的书写我们的代码来进行业务规则的验证:

[AcceptVerbs("POST"), ActionName("NewPost" )]
public
ActionResult SaveNewPost(FormCollection form)
{
    Post post
= new
Post();

   
try

    {
        UpdateModel(post,
new[] { "Title", "Content", "Slug" });
    }
   
catch

    {
       
return View(post);
    }

   
if (!
post.IsValid)
    {
       
foreach (string key in
post.BrokenRules.Keys)
        {
            ViewData.ModelState.AddModelError(key, form[key], post.BrokenRules[key]);
        }
       
return
View(post);
    }

    post.Save();
   
return ShowMsg(new List<string>() { "发表新随笔成功"
});
}

 

我们注意到上面的Action中用到了一个FormCollection 的参数,这个参数系统会自动将Form提交过来的全部表单值(Request.Form)赋给它的。客户端验证可以用jQuery的验证插件来,这里就不罗嗦了。

uniapp 实现RFID识别的实战指南 本文提供了在uniapp中实现RFID识别的完整实战指南。核心在于通过Android系统广播机制,利用uni-app的plus对象调用原生接口,完成与RFID手持设备的“软硬件握手”。文章详细介绍了从环境准备、设备选型、核心代码实现到避坑优化的全流程,帮助开发者快速构建高效的RFID盘点或管理应用。 阅读详情

相关推荐

网工实验笔记:SNMP的配置

简单网络管理协议SNMP(Simple Network Management Protocol)是广泛应用于TCP/IP网络的网络管理标准协议。SNMP提供了一种通过运行网络管理软件的中心计算机(即网络管理工作站)来管理设备的方法。

2301_76170756的博客 2116

ASP.NET MVC中ModelState的使用

在ASP.NET MVC中,我們說下關于使用ModelState 的幾個技巧,它可以拓寬我們應用的視野,使用代碼更加的簡潔有效。 關于ModelState 的使用,我們經常是停留在Control Action 綁定模型的有效性驗證 ,包括 輸入驗證 (Input Validation) 與 模型驗證 (Model Validation) 是否成功。 例如: if(!ModelState.IsValid) { return … } 我們再深入學習下。 一.定義 將模型綁定的狀態、值封裝到 action-met

segclliwf的博客 1377

腾讯2020 unreal虚幻面试题

解析一下,腾讯的unreal客户端面试题: 1.lua性能优化的方向 申请的内存,是造成卡顿的原因之一,在C++与lua交互中,如果参数或者返回值有类变量,那么这个变量不会再交互的栈中存放数据,而会通过申请内存,再指定在交互,这样就造成卡顿,因此可以通过把C++的对象的每个参数分开单独传递,可以解决问题,当时我们游戏改完这个问题后,整体提升了2帧。 其实,主要是Tick循环中,减少与C++的交互,需要的数据不要每帧都去拿,其次,经常拿的一些数据(比方说主角信息),可以做一个lua缓存,...

qq_17347313的博客 1万+

.NET 8 组件之MVC/WebAPI核心组件

NET 8中的MVC和WebAPI核心组件为开发者提供了更加丰富和强大的工具集,能够满足现代Web应用和服务开发的各种需求。通过示例代码,我们可以更直观地理解如何使用这些核心组件来构建高性能、可扩展的Web应用程序和服务。无论是构建复杂的企业级Web应用,还是开发高性能的RESTful API服务,.NET 8都能提供出色的性能和灵活性。掌握这些核心组件对于每一个Web开发者来说都是至关重要的。

hy_4377的博客 1907

【unity】解决unity编译器安装中文汉化包失败

查看是否有Localization目录如果没有就进行创建,然后点击打开Localization把下载的zh-hans.po文件复制剪切进去即可。如果有的同学中文包安装失败,我们找到相应的编译器版本,点击在资源管理器中显示按钮,我们找到简体中文,复制downloadUrl后面的值到浏览器打开进行下载,点击Edtior language选择框,选择简体中文,等待加载。我们点击当前目录的上一级,进入编译器目录。返回在文件管理器中点击Editor目录。编译器启动后点击Edit[编辑]按钮。复制或者剪切下载的文件。

weixin_44959182的博客 8025

Stable-Baselines3性能优化:多环境训练对比指南(DummyVecEnv vs SubprocVecEnv)

本文深入对比了Stable-Baselines3中DummyVecEnv与SubprocVecEnv两种向量化环境的性能差异与应用场景。DummyVecEnv适用于轻量级、步进快的环境,调试友好且开销低;而SubprocVecEnv则通过真正的多进程并行,能显著加速计算密集型环境的训练。文章通过基准测试与决策树,指导开发者根据环境计算成本、CPU核心数等关键因素做出最优选择,以实现训练效率最大化。

weixin_29063979的博客 148

ASP.NET Core 模型验证系列一

什么是模型验证? 模型验证是给模型属性提供一种规则,并且可以验证模型属性的值,以至于他们是合法的,如果这些值不合法,给客户显示一些容易理解的错误并且帮助客户修改正这个问题模型验证分为两类:1服务器端验证2客户端验证1 ASP.NET Core ModelState什么是ModelState ? ModelState 是一个键值对的集合包含了模型绑定和验证过程中发生的错误,例如-使用一个字符串类...

dotNET跨平台 812

Python 静态导入与动态导入

python中模块的静态导入 与 动态导入(运行时指定模块),以及具体对应示例。

慢也好,步子小也好,往前走就好~ 717

[转]ASP.NET MVC 入门8、ModelState与数据验证

ViewData有一个ModelState的属性,这是一个类型为ModelStateDictionary的ModelState类型的字典集合。在进行数据验证的时候这个属性是比较有用的。在使用Html.ValidationMessage()的时候,就是从ViewData.ModelState中检测是否有指定的KEY,如果存在,就提示错误信息。例如在前一篇文章ASP.NET MVC 入门7、...

dianjin3567的博客 102

OSG第三方库编译之二十一:minizip编译(Windows、Linux、Macos环境下编译)

OSG编译;第三方库;跨平台编译;minizip编译(Windows、Linux、Macos环境下编译)

LuckyHanMo的博客 2623

西门子G120变频器在立体仓库堆垛机应用参数设置

本文详细介绍了G120 CU240E及CU250S变频器的参数设置流程。主要内容包括:1)快速调试步骤,从新建项目、扫描节点到设置电机类型、负载类型等参数;2)抱闸参数设置方法;3)参数下载异常时的处理方案。重点说明了通过STARTER软件进行向导式调试的完整过程,包括电机铭牌参数输入、识别方式选择等关键环节,并提示了通讯连接注意事项。当下载失败时,提供了通过导入导出项目文件解决问题的具体方法。

xdpcxq的专栏 864
上一篇: ASP.NET MVC 入门 -- 7、Hellper与数据的提交与绑定
下一篇: ASP.NET MVC 入门 -- 9、Action Filter 与 内置的Filter实现(介绍)
DiscussQuestions
博客等级 码龄19年 28粉丝 29原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值