第3、10章
一般情况下,定义presentation model,然后形成强类型视图,可以结合ViewData传递小的片段和简单数据,以增加代码的维护性
presentation model类中可以加入data annotations属性,控制数据的验证
DisplayFor
DisplayTextFor
EditorFor
CheckBoxFor
DropDownListFor
HiddenFor
LabelFor
ListBoxFor
PasswordFor
RadioButtonFor
TextAreaFor
TextBoxFor
ValidateFor
ValidationMessageFor
以上类都在 System.Web.Mvc ..::. HtmlHelper 类中,MSDN文档可以察看明细,目前这些代码自能手工编写或使用T4自动生成,我估计以后IDE会提供类似WebForm的可视化支持
根据察看和编辑的不同,分为两类
■ Html.Display("Message")
■ Html.DisplayFor(m => m.Message)
■ Html.DisplayForModel()
■ Html.Editor("UserName")
■ Html.EditorFor(m => m.UserName)
■ Html.EditorForModel()
模板查找顺序和自定义
If the template helper method is used inside an area-specific view, these folders include
■ <Area>/<ControllerName>/EditorTemplates/<TemplateName>.ascx (or .aspx)
■ <Area>/Shared/EditorTemplates/<TemplateName>.ascx (or .aspx)
If a template isn’t found in these folders, or if the view isn’t in an area, the default view search locations are used:
■ <ControllerName>/EditorTemplates/<TemplateName>.ascx (or .aspx)
■ Shared/EditorTemplates/<TemplateName>.ascx (or .aspx)
对于察看模板在DisplayTemplates下[第20章有一个使用这个的例子]
和Web Form基本类似
RenderPartial method or the Partial method in a parent view
对于RenderPartial中视图名称在Views目录下的查找顺序:
1 <Area>\<Controller>\<PartialName>.aspx and .ascx
2 <Area>\Shared\<PartialName>.aspx and .ascx
3 \<Controller>\<PartialName>.aspx and .ascx
4 \Shared\<PartialName>.aspx and .ascx
处理RouteValueDictionary,使URL象以前的格式如:***?##=##
在MVC中使用Router基本上这种形式不再使用,除非和已有的一些老系统兼容处理可能用到
默认是Web Form视图引擎
开源的Spark引擎,具体使用需要遵守这个的语法即可
在MVC 3中已经有Razor视图引擎,微软PI一体化简装包中安装后默认建立的页面使用的就是Razor,毕竟是新加的,没有历史包袱,比Web Form简化
第4、9、16章
所有的请求都通过这个进行服务
用于防止表单提交的问题,如果在同一个视图中展现提交结果,客户端刷新时会再次提交从而造成数据的重复和不一致
[HttpPost]
public ActionResult Edit(UserInput input)
{
if (ModelState.IsValid)
{
UpdateUserFromInput(input);
TempData["message"] = "The user was updated";
return RedirectToAction("index");
}
return View(input);
}
private void UpdateUserFromInput(UserInput input)
{
User user = UserRepository.GetByUsername(input.Username);
user.FirstName = input.FirstName;
user.LastName = input.LastName;
UserRepository.Save(user);
}
This extensibility point allows you to intercept the execution of an action and inject behavior before or after the action is executed. This is similar to aspect-oriented programming, which is a technique for applying cross-cutting concerns to a code base without having lots of duplicate code to maintain.
自己实现只要从ActionFilterAttribute继承即可,如记录日志等
ChildActionOnlyAttribute是框架内置的,比较这个属性的Action,只能在Html.RenderAction的视图中使用
AuthorizeAttribute
The action selector is used to control which action method is selected to handle a particular route.
System.Web.Mvc ..::. ActionMethodSelectorAttribute
System.Web.Mvc ..::. AcceptVerbsAttribute
System.Web.Mvc ..::. HttpDeleteAttribute
System.Web.Mvc ..::. HttpGetAttribute
System.Web.Mvc ..::. HttpPostAttribute
System.Web.Mvc ..::. HttpPutAttribute
System.Web.Mvc ..::. NonActionAttribute
Custom action results can be used to remove code that’s duplicated across methods and to extract dependencies that can make an action difficult to test.
直接继承ActionResult类
System.Web.Mvc ..::. ActionResult
System.Web.Mvc ..::. ContentResult
System.Web.Mvc ..::. EmptyResult
System.Web.Mvc ..::. FileResult FileContentResult
System.Web.Mvc ..::. HttpUnauthorizedResult
System.Web.Mvc ..::. JavaScriptResult
System.Web.Mvc ..::. JsonResult
System.Web.Mvc ..::. RedirectResult
System.Web.Mvc ..::. RedirectToRouteResult
System.Web.Mvc ..::. ViewResultBase
直接实现一个ActionReslut可以共用,如结果输出CSV文件。
public class CsvActionResult : ActionResult
{
public IEnumerable ModelListing { get; set; }
public CsvActionResult(IEnumerable modelListing)
{
ModelListing = modelListing;
}
public override void ExecuteResult(ControllerContext context)
{
byte[] data = new CsvFileCreator().AsBytes(ModelListing);
var fileResult = new FileContentResult(data, "text/csv")
{
FileDownloadName = "CsvFile.csv"
};
fileResult.ExecuteResult(context);
}
}
主要是在Action方法的返回时实例化以上不同的实现即可。
URLRewriting
路由注册在Global.asax.cs完成
public static void RegisterRoutes(RouteCollection routes)
{
/* Desired URL schema:
* 1. example.com/ home page
* 2. example.com/privacy static page containing privacy policy
* 3. example.com/widgets show a list of the widgets
* 4. example.com/<widget code> Shows a product detail page for the relevant <widget code>
* 5. example.com/<widget code>/buy Add the relevant widget to the shopping basket
* 6. example.com/basket Shows the current users shopping basket
* 7. example.com/checkout Starts the checkout process for the current user
* 8. example.com/404 show a friendly 404 page
*/
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
routes.MapRoute("404", "404", new {controller = "Error", action = "NotFound"});
routes.MapRoute("privacy_policy", "privacy", new { controller = "Home", action = "Privacy" });
routes.MapRoute("widget", "{widgetCode}/{action}",
new { controller = "Catalog", action = "Show" },
new { widgetCode = @"WDG-\d{4}" });
routes.MapRoute("widgets", "widgets", new {controller = "Catalog", action = "index"});
routes.MapRoute("catalog", "{action}",
new { controller = "Catalog" },
new { action = @"basket|checkout|index" });
routes.MapRoute(
"Default", // Route name
"{controller}/{action}/{id}", // URL with parameters
new { controller = "Home", action = "Index", id = UrlParameter.Optional } // Parameter defaults
);
routes.MapRoute("404-catch-all", "{*catchall}", new {Controller = "Error", Action = "NotFound"});
}
路由处理的优先级从上到下,因此这个的设计是关键
URL生成
Html.ActionLink
Html.RouteLink
Url.Action
…
以上的缺点是参数都是字符串的形式,如果Action换名后,需要手动修改
T4MVC是一个自动化的辅助工具处理URL的生成问题,变成强类型,编译时完成处理。