MVC特性
MVC与ASP.NET MVC基础概念
MVC是Model-View-Controller的缩写.
MVC将应用程序划分为3大组件:模型\视图\控制器.
MVC不是ASP.NET所特有,它只是一种开发理念.java中的struts2也是一种MVC模型.
ASP.NET MVC从2008年发布1.0版以来,截至2014年ASP.NET MVC最新版本已经是5.0.
ASP.NET MVC从1.0版开始,就已经开放源代码(源码地址:aspnetwebstack.codeplex.com).
ASP.NET MVC官网地址:http://www.asp.net/mvc
MVC三大组件的相互关系
- 在控制器中可以直接调用视图和模型
- 在视图中可以调用模型.
- 模型不能调用视图
- 模型能够限定视图中使用的数据,但视图中使用的模型应由控制器提供
- 在视图中可以调用控制器(通过视图中表单的提交和点击超链接的方式调用)
ASP.NET Webform模型和ASP.NET MVC模型的关系
二者都是基于ASP.NET Web框架构建的开发模型.所以ASP.NET中的一些功能可以被二者公用.
Webform编程模型是典型的以事件驱动的web模型,而MVC则不是.
Webform的URL地址是基于文件系统的,而MVC则是基于Action.
ASP.NET MVC中的约定
- 所有的控制器必须放到Controllers文件夹下
- 所有的控制器类名必须以Controller结尾
- 所有的模型应该放到Models目录下
- 所有的视图文件都应该放到Views目录下.
- 所有的控制器类都应该继承自Controller类(本质上是要继承Icontroller接口)
- 在控制器类中的public方法被成为Action(行为)
- 如果在相应的视图目录中没有找到视图文件,那么会寻找Views\Shared目录下名称相同的视图文件
- 在Action中return view(),默认会返回和Action名称一样的视图文件.
- 在Global.asax全局应用程序类中注册了默认路由(名称为Default),默认路由指定了Controller默认为Home,Action默认为Index,参数id为可选参数.所以在URL地址中如果不输入controller默认访问Home控制器;如果不输入action默认访问名称为Index的action.
- http://localhost:54321/ 解释:
根据默认路由规则,等价于 => http://localhost:54321/Home/Index
- http://localhost:54321/Home/Index/5 解释:
数值5会自动映射到action中名称为id的参数中。
- Http://localhost:54321/Home/Index/5?name=jack&age=20 解释:
其中参数包括id、name和age三个
其他
在视图文件中,有一个名称为Model属性,它指代的是从Action中传递的模型数据.为了使用模型数据,我们还需要在<%@Page %>指令的Inherits属性中设置模型数据的类型.
ASP.NET MVC进阶一
控制器相关
- 在Controller类中方法访问级别为public的方法,就是行为(Action).
- 如果不希望Controller类中的方法成为Action(可以在地址栏中被访问),有两种实现方式:
- 将方法的访问级别设置为private
- 在方法上添加特性标记[NonAction]
- 诸如新增\修改等功能模块,我们往往会创建2个名称相同的Action:一个action用于加载新增\修改页面;另一个action用于处理新增\修改页面提交的表单数据.那么如何区分在何时调用哪个action呢?
我们将加载新增|修改页面时被调用的action,添加[HttpGet]特性标记;将处理页面提交的表单数据时调用的action,添加[HttpPost]特性标记.下面的示例代码演示了如何实现学生的新增(action相关的代码)
- 如何在Action中获取表单提交的数据?
表单中提交的数据,可以通过Action的参数进行映射.
映射的前提条件:Html标记的name属性值和action中参数的名称要一致.
下面的示例代码演示了映射的过程(注意粉色框标记的部分):
- Action中如何映射复杂对象?
对于上面的映射代码,我们还可以有另外一种等价的写法,就是将映射的属性定义到一个实体类中,这样我们就可以在action中添加该实体类型的参数,参考代码如下所示:
- 如何从一个Action中跳转至另外一个Action?
新增或修改功能完成后,需要跳转至数据列表页面,我们可以通过如下代码实现:
代码 => return RedirectToAction(“ActionName”, “ControllerName”).
视图相关
- 在ASPX视图引擎中,可以使用asp服务器控件,但它的作用仅仅局限与生成html代码,而不推荐开发人员使用asp控件的事件.因此建议开发人员手工编写Html标记。
但是手写Html标记比较耗费时间,有没有更好的解决方案?答案就是使用Html辅助方法。
- Html辅助方法
Html辅助方法的作用就是通过调用C#方法的方式,快速的生成相应的html标记.
Html辅助方法分为2大类:弱类型html辅助方法和强类型html辅助方法.
其中以For关键字结尾的都是强类型的辅助方法.下面的示例代码演示了二者的调用方式,以及生成的html源码。
注意:Html辅助方法有很多种重载形式,在开发过程中可以根据实际需要自行选择.比如要实现一个包含class\style\onchange属性和事件的单行文本框,可以参考如下代码:
强调:如何使用HTML辅助方法生成form标记?
生成form标记的两个Html辅助方法为:Html.BeginForm()和Html.EndForm(),但他们在使用时和其他的Html辅助方法有所不同,下面的示例代码演示了它们的两种用法:
- 如何在URL地址中传递参数?
场景一:将学生ID值映射到名称为id参数上
场景二:将学生ID值映射到名称为stuId参数上
场景三:url地址中包括stuId和name两个参数
这三种场景的使用代码如下所示:
其他
- 在实际开发过程中,一个小的功能模块就对应一个控制器.比如学生信息管理就是一个控制器,新增学生\修改学生\查询学生列表\删除学生都可以对应控制器中的Action.
- 常用Html辅助方法汇总
|
弱类型 |
强类型 |
单行文本框 |
Html.TextBox() |
Html.TextBoxFor() |
多行文本框 |
Html.TextArea() |
Html.TextAreaFor() |
密码框 |
Html.Password() |
Html.PasswordFor() |
复选框 |
Html.Checkbox() |
Html.CheckBoxFor() |
单选按钮 |
Html.RadioButton() |
Html.RadioButtonFor() |
下拉列表框 |
Html.DropdownList() |
Html.DropdownListFor() |
平铺列表框 |
Html.ListBox() |
Html.ListBoxFor() |
Label |
Html.Label() |
Html.LabelFor() |
Form表单 |
Html.BeginForm() Html.EndForm() |
|
超链接 |
Html.ActionLink() |
- 如何在视图中使用下拉列表
第一步:在action中构造好下拉列表中需要的数据,数据的类型为IEnumerable<SelectListItem>。
第二步:将构造好的数据放到Controller中的ViewData(ViewBag|TempData)属性中。
第三步:在视图view中使用Html.DropDownList辅助方法来生成下拉列表,而绑定的数据可以使用视图View中的ViewData来获取(换句话讲就是,Controller中放置到ViewData的数据,可以在视图View中的ViewData属性中提取)。
在视图中使用Html.DropDownList绑定Ienumerable<SelectListItem>
ASP.NET MVC进阶二
数据验证
数据验证的步骤
- 在模型类中添加与验证相关的特性标记
- 在客户端导入与验证相关的js文件和css文件
- 使用与验证相关的Html辅助方法
- 在服务器端判断是否通过服务器端验证
常用的验证标记
- Required:非空验证
- StringLength:验证字符串的长度
- RegularExpression:正则表达式验证
- Compare:比较两个字段的值是否相等
- Range:范围验证
- Remote:服务器验证(需要在controller中编写返回值为JsonResult的Action)
- 自定义验证标记
与验证相关的js文件
在ASP.NET MVC中提供了2套验证框架,分别是微软验证框架和jquery验证框架.默认启用了jquery验证框架.
注意:这些js文件的顺序不能颠倒;其中Site.css文件中定义了数据验证使用的样式.
验证相关的Html辅助方法
注意:1.必须使用Html.ValidationMessage()和Html.ValidationMessageFor()来显示验证失效的提示信息;
2.被验证的控件(如文本框\下拉列表框等)必须使用Html辅助方法生成才有效.
在服务器端判断模型是否通过了验证(服务器端验证)
页面中如果使用了MVC验证功能,那么在后台对应的Action中必须通过ModelState.IsValid判断是否通过了服务器端验证。只有通过了服务器端验证,才能执行其他的业务逻辑代码。
使用要点:
- 被验证的标记不能是纯html,必须使用相应的html辅助方法
例如:Html.TextBoxFor(model=>model.UserName),则验证有效;
<input type=”text” id=”UserName” name=”UserName” />,则验证无效;
- 必须使用相应的html辅助方法显示验证消息(Html.ValidationMessage)
- 被验证的控件必须放在有html.beginform的辅助方法内部(不能是纯<form>标记).
- 客户端验证是不安全的,容易被禁用或欺骗,所以一定要在服务器端判断ModelState.IsValid是否为true.
Action与View的数据传递
在某些情况下,视图需要显示多份数据(比如被修改的员工信息\岗位列表\部门列表),但是Action在返回视图时,View()方法只能传递1个object类型的数据,那么其他的数据该如何传递?
ASP.NET MVC为我们提供了3种方案:ViewData\TempData\ViewBag.
重要提示:在Controller和View中都有这三个属性,在Controller的相应属性中存放了数据后,就可以在View的相应属性中提取这些数据。
ViewData
ViewData是一个字典类型.向里面添加数据时要以键值对的形式添加.
首先在Action中向ViewData中添加,其次就可以在View中访问ViewData来提取数据.
ViewBag
ViewBag是一个动态类型的属性。在ASP.NET MVC 3.0中才加入了ViewBag属性.
动态类型:dynamic,就是可以事先不为其定义属性,通过直接给属性赋值的方式就可以随时为它添加新的属性.
下面的代码演示了向ViewBag中存放cls和stu两个对象,这两个对象分别放到了属性ClassInfo和StudentInfo中。
TempData
TempData的用法和ViewData很相似,都是字典类型.那他们的区别是什么?
ViewData中存储的数据仅仅对本次访问的当前action有效.而TempData中存储的数据,除了对本次访问的当前action有效外,还对本次访问的其他action有效(比如在Action1中向TempData中存放了数据,即使从Action1跳转至Action2后,仍然可以在Action2中从TempData提取数据。而ViewData和ViewBag都无法做到这一点).因此,TempData中数据的生命周期比ViewData|ViewBag中的生命周期要长.
ActionResult的实现类
在ASP.NET MVC模型中,Action用于响应用户的各种请求,比如向客户端返回html文档、html片段、json数据、纯文本、文件等结果。在ASP.NET MVC中通过在Action(行为或操作)方法中返回ActionResult类型的对象来实现向客户端响应上面的各种结果。
ActionResult类是个抽象类(抽象类无法直接被实例化).
ActionResult有很多实现类,不同的实现类用于响应客户端不同的结果。并且在Controller类中提供了大量的辅助方法,这些辅助方法可以快速的创建各种ActionResult.
在实际开发中,我们更多的是使用Controller类中的辅助方法,而非自己手工创建ActionResult的实现类。
ViewResult类
ViewResult类的作用是向客户端响应View目录中一个视图文件.
Controller类中提供了View()方法,来快速的返回一个ViewResult类对象.
ContentResult类
该类用于向客户端返回一段文本内容(纯文本\HTML...).
在Controller类中的辅助方法为:Controller.Content(string content);
RedirectToRouteResult类
该类的作用是从当前action跳转至其他action.
在Controller类中的辅助方法为:RedirectToAction(“ActionName”, “ControllerName”)
RedirectResult类
在服务器端从当前Action跳转到其他URL地址.
在Controller类中的辅助方法为:Controller.Redirect(string url)
JsonResult类
该类用于向客户端返回一段Json格式的字符串.
在Controller类中的辅助方法为:Controller.Json(object data);
注意:默认情况下mvc拒绝响应以get方式发送的ajax请求,需要使用JsonRequestBehavior.AllowGet。
PartialViewResult类
该类的作用是向客户端响应Views目录的一个分部视图文件。分部视图就是只包含html片段的视图文件.
在Controller类中的辅助方法为:Controller.PartialView();
FilePathResult类
该类用于实现文件下载.
在Controller类中的辅助方法为:Controller.File(string filePath, string contentType, string fileName);
EmptyResult类
该类用于向客户端响应一个空结果。
HttpStatusCodeResult类
该类用于向客户端相应指定的状态码.
HttpNotFoundResult类就是HttpStatusCodeResult的子类,表示404这一状态码。
下面的是一些常用的http状态码:
404:资源未找到(表示客户端请求服务器的资源地址不存在)
500:服务器内部错误(以5XX开头的表示服务器端在处理过程中出现的错误)
200:成功(表示客户端发送的请求被服务器成功的处理和响应)
其他
如何在aspx页面中导入命名空间?
方式一:在指定的页面添加<%@ Import Namespace=”命名空间” %>
方式二:在项目的web.config配置文件中添加pages---namespaces----add
通过方式二添加的命名空间可以在所有的aspx页面中使用;而方式一添加的命名空间只能在当前页面中使用.
ASP.NET MVC进阶三
ASP.NET MVC中的AJAX应用
首先,在ASP.NET MVC中使用自带的ajax功能,必须要导入2个js文件(顺序不能颠倒):
ASP.NET MVC提供了2个常用的ajax辅助方法.
Ajax.ActionLink
该辅助方法用于在页面上生成具有ajax功能的超链接.
在该辅助方法中有一个AjaxOptions类型的参数,它包括如下属性:
- Confirm:在发送ajax请求前,弹出确认对话框,该属性就是设置对话框中的提示消息
- HttpMethod:用于设置请求的类型:Get|Post
- UpdateTargetId:用于设置服务器响应的结果更新到页面中目标元素ID
- InsertionMode:用于设置服务器相应的结果如何插入到被更新的元素中,它的值可以包括3种:
InsertionMode.Replace:用新值替换旧值(默认值)
InsertionMode.InsertAfter:将新值插入到目标元素的底部
InsertionMode.InsertBefore:将新值插入到目标元素的顶部
- OnBegin:当执行ajax请求前,执行的js函数
- OnSuccess:当执行ajax请求成功时,执行的js函数
- OnFailure:当ajax请求失败时,执行的js函数
- OnComplate: 当ajax请求完成后,执行的js函数(不管请求失败或成功,都会执行)
- LoadingElementId:在ajax请求期间,可以显示一段友好的提示,该属性用于设置提示元素的ID
- LoadingElementDuration: 提示元素在显示和隐藏时,可以执行一段动画,该属性用于设置提示元素的动画执行时间
Ajax.BeginForm
该ajax辅助方法用于以ajax方式提交表单数据.
其他
如何在页面中加载分部视图?
方式一:调用Html.RenderPartial(“viewName”)
方式二:调用Html.RenderAction(“actionName”)
何时使用RenderAction,何时使用RenderPartial?
如果需要向视图中传递数据,而原视图中又没有需要传递的数据时,就需要调用RenderAction.
注意: Html.RenderPartial有多种重载形式,下面列举它的2种常用形式:
Html.RenderPartial(“分布视图的名称”)
Html.RenderPartial(“分部视图的名称”, object 模型数据)
如何从服务器获取一段json格式的字符串?
服务器的Action方法返回值类型为JsonResult,并且在方法内部可以调用Controller.Json()辅助方法.
ASP.NET MVC进阶四
ASP.NET MVC中使用母版页
ASPX视图引擎的母版页功能
Aspx视图引擎中母版页的用法,在webform模型和Mvc模型中,都是一样的.
Aspx视图有2个很重要的标记:
- asp:ContentPlaceHolder标记
- asp:Content标记
asp:Content用于替换母版页中的asp:ContentPlaceHolder.
在母版页中应该根据实际需要,定义多个asp:ContentPlaceHolder,而非默认的2个.
注意:在mvc中添加母版页时一定要选择 MVC3视图母版页,而不能选择下面的母版页和嵌套的母版页.
在MVC中,没有提供嵌套的母版页模版文件,需要用户自行定义:
Razor视图引擎
Razor视图引擎的宗旨:将键盘的敲击次数降到最低
Razor基本语法
- 定义变量:
- 输出变量的值:
- 如何在页面中原样输出@符号
- 如何在页面中输出hisageis5.
- if-else的写法:
- for|foreach的写法:
注意:如果在for循环中需要进行条件判断,不需要在if前加@符号.
- Html辅助方法的使用:
注意:@Html.TextBox()后面不能有分号.
- 在razor视图页面中定义数据模型的类型信息:
- 在razor视图页面中加载分部视图或加载其他action:
注意:@{}里面的分号不能省略.
- 在Razor视图中如何生成form标记:
Razor视图引擎中母版页的用法
- Razor视图中母版页功能称之为布局页.
- Razor视图的布局页文件名必须以下划线_开头.
- Mvc项目中如何添加Razor布局页:
- Razor视图中布局页的默认代码如下:
@RenderBody的作用同aspx视图中的asp:ContentPlaceHolder相似,用于加载内容页.
- Razor视图引擎中,如何让内容页继承布局页?
在内容页中使用Layout属性指定要继承的布局页.代码如下:
其中ViewBag.Title是用于设置布局页中的页面title.
如果不需要内容页继承布局页,只需要将Layout属性的值设置为null.
如果没有将Layout设置为null,而是将其删除掉,那么内容页仍然有可能会继承一个默认的布局页.因为在Views目录中存在一个名称为:_ViewStart.cshtml的文件,该文件是视图的默认配置文件,它里面设置了默认的布局页面,示例代码如下:
嵌套的布局页,在mvc中也没有提供默认的模版文件,需要用户自行添加.
Html.RenderSection()
该辅助方法用于加载html片段.该段Html代码可以是本页面中定义的,也可以是内容页面中定义的.
示例代码如下:
Razor视图中如何自定义辅助方法
使用@helper来定义辅助方法.示例代码如下:
在ASP.NET MVC中如何实现模块化开发?
对于一个系统而言,往往包含前台和后台两大块.比如,前后台都包含用户登录功能,它们的控制器都叫Account,对应的登录方法也都叫Login,那么如何区分哪个是后台的,哪个是前台的???
ASP.NET MVC在2.0中就添加了Area(区域)的功能,用来解决上面的问题.
通过Area功能可以将一个大的软件项目划分为N个功能模块,每个功能模块中都可以相同名称的控制器和视图文件.
首先,右击项目,在弹出的右键菜单中选择----添加----区域
ASP.NET MVC数据分页
Aspx视图引擎和razor视图引擎中如何实现分页功能
主要使用了第三方的一个分页控件MvcPager.dll
分页功能分三步实现:
第一步是在项目中导入MvcPager.dll,并导入相应的命名空间: Webdiyer.WebControls.Mvc
第二步是在Action中组织要分页的数据
第三步是在页面中生成页码信息
注意:MvcPager.dll包括非ajax和ajax两种使用模式.ajax模式下需要使用Ajax.Pager辅助方法.
其他
- 如何在页面中加载静态文件(图片\css\js)?
使用Url.Content(“filePath”)方法.
Aspx视图引擎
Razor视图引擎
- 添加新的Area后,访问报错的解决办法:
修改Global.ashx文件中注册的默认路由
ASP.NET MVC进阶五
重写Controller类的虚方法
OnActionExecuting\OnActionExecuted
OnActionExecuting:该方法在执行目标Action之前被调用
OnActionExecuted:该方法在执行目标Action之后被调用
OnResultExecuting\OnResultExecuted
OnResultExecuting:该方法在执行目标视图之前被调用
OnResultExecuted:该方法在执行目标视图之后被调用
OnAuthorization
该方法用于验证用户的授权信息.因此如果要进行身份的验证,应该在该方法中进行.
OnException
当访问Action出现异常时,该方法会自动被调用.
下面的示例代码演示了如何自动捕获系统异常,并将异常信息记录到日志文件中.
ASP.NET MVC中的过滤器
过滤器是指在用户发送请求时,MVC框架可以对用户的请求进行拦截,根据特定的条件对这些请求进行筛选过滤.
ASP.NET MVC中提供了下面几种过滤器,他们的作用和上面将的重写方法功能类似,但是这些过滤器是全局的,默认对所有的Action请求都有效.
IAuthorizationFilter
授权过滤器
IActionFilter
行为过滤器
IResultFilter
结果过滤器
IExceptionFilter
异常过滤器
注意:过滤器需要在Global.asax文件中进行注册后方能起效.