Mvc系统学习9——Areas学习
? 在Mvc2.0中,新增加了一個(gè)特性就是Areas。在沒有有使用Areas的情況下,我們的Mvc項(xiàng)目組織是下面這樣的。當(dāng)項(xiàng)目龐大的時(shí)候,Controllers,Model,View文件下下面勢必會(huì)有很多文件。項(xiàng)目將難以管理。
????? 通過使用Areas使我們可以很好的組織項(xiàng)目,通過單機(jī)添加Areas(區(qū)域),使用Areas來組織項(xiàng)目。可以得到新的項(xiàng)目組織結(jié)構(gòu)。
????? First,Second對應(yīng)著我們項(xiàng)目的子模塊(First,Second命名不是很好)。在這兩個(gè)文件夾下,有各自獨(dú)立的Controllers,Models,Views。此外還多了個(gè)文件AreaRegistration為后綴的.cs文件. 這個(gè)文件主要的作用是給Areas下的子模塊配置路由。在全局文件Global.asax中的Application_Start事件里有這么一句代碼?AreaRegistration.RegisterAllAreas(),通過mvc源碼可以發(fā)現(xiàn)通過這句代碼最后會(huì)調(diào)用各個(gè)AreaRegistration類,實(shí)現(xiàn)路由的注冊。
//重寫了AreaName用于給DataToken["area"]賦值public class FirstAreaRegistration : AreaRegistration{public override string AreaName{get{return "First";}}//這里會(huì)添加一個(gè)相應(yīng)的Area名稱的前綴,因?yàn)橄旅孢@樣的添加也是作用到全局路由表的.//而且這里的MapRoutes,和在全局的MapRoutes是不同的//這時(shí)AreaRegistrationContext里面的方法,它里面的方法會(huì)自動(dòng)給DataToken["area"]鍵賦值當(dāng)前的AreaName public override void RegisterArea(AreaRegistrationContext context){context.MapRoute("First_default","First/{controller}/{action}/{id}",new { controller = "Home", action = "Index", id = UrlParameter.Optional });} View Code???????當(dāng)調(diào)用?AreaRegistration.RegisterAllAreas()時(shí),會(huì)最后調(diào)用下面這個(gè)方法。通過下面的代碼可以得出,這個(gè)方法會(huì)通過反射得出所有的AreaRegistration的Type實(shí)例。接下來依次通過Activator創(chuàng)建實(shí)例,進(jìn)而調(diào)用CreateContentAndRegister方法。\
internal static void RegisterAllAreas(RouteCollection routes, IBuildManager buildManager, object state) {List<Type> areaRegistrationTypes = TypeCacheUtil.GetFilteredTypesFromAssemblies(_typeCacheName, IsAreaRegistrationType, buildManager);foreach (Type areaRegistrationType in areaRegistrationTypes) {AreaRegistration registration = (AreaRegistration)Activator.CreateInstance(areaRegistrationType);registration.CreateContextAndRegister(routes, state);}} View Code? ? ? ?registration.CreateContextAndRegister方法:
internal void CreateContextAndRegister(RouteCollection routes, object state) {//實(shí)例化一個(gè)AreaRegistrationContext 實(shí)例,AreaName已經(jīng)傳遞給AreaRegistrationContext了AreaRegistrationContext context = new AreaRegistrationContext(AreaName, routes, state);string thisNamespace = GetType().Namespace;if (thisNamespace != null) {context.Namespaces.Add(thisNamespace + ".*");}//調(diào)用注冊方法,這個(gè)方法在各個(gè)AreaRegistration中被重寫 RegisterArea(context);} View Code? ? ? 各個(gè)AreaRegistration重寫的RegisterArea(context)方法里面通過調(diào)用AreaRegistrationContext的Maproute方法來實(shí)現(xiàn)注冊,這個(gè)方法最后的調(diào)用方法是下面這個(gè)。可以發(fā)現(xiàn)下面這個(gè)方法也會(huì)調(diào)用RouteCollection的MapRoute方法,調(diào)用這個(gè)方法之后,又向route的DataTokens字典的area和UseNamespaceFallback鍵設(shè)置值。這有什么作用?
public Route MapRoute(string name, string url, object defaults, object constraints, string[] namespaces) {if (namespaces == null && Namespaces != null) {namespaces = Namespaces.ToArray();}Route route = Routes.MapRoute(name, url, defaults, constraints, namespaces);route.DataTokens["area"] = AreaName;// disabling the namespace lookup fallback mechanism keeps this areas from accidentally picking up// controllers belonging to other areasbool useNamespaceFallback = (namespaces == null || namespaces.Length == 0);route.DataTokens["UseNamespaceFallback"] = useNamespaceFallback;return route;} View Code? ? ? ? 還有幾個(gè)疑問待解決:
??????? 1.Area下的路由過程是怎么樣的?
??????? 2.在Area下可以實(shí)現(xiàn)不同的Area有相同的ControllerName,可以在全局的Global.ascx進(jìn)行文件配置,但是如果是同名的Controller則會(huì)出現(xiàn)錯(cuò)誤,而對沒有同名的Controller進(jìn)行配置則不會(huì),這是為什么?
????????比如在First,Second都有HomeController,如果在全局的Global.ascx文件進(jìn)行配置,下面的配置不會(huì)出錯(cuò),但是如果namespaces是MvcAreaDemo2.Areas.First時(shí)則會(huì)出現(xiàn)錯(cuò)誤。這時(shí)為什么?如果沒有用同名的Controller則namespace是MvcAreaDemo2.Areas.First和MvcAreaDemo2.Areas.First.Controllers都沒有錯(cuò)。
routes.Add(new Route("Index1", new MvcRouteHandler()){Defaults = new RouteValueDictionary(new { controller = "Home", action = "Index", id = UrlParameter.Optional }),DataTokens = new RouteValueDictionary(new { area = "First", namespaces = new[] { "MvcAreaDemo2.Areas.First.Controllers" } })});routes.Add(new Route("Index2", new MvcRouteHandler()){Defaults = new RouteValueDictionary(new { controller = "Home", action = "Index", id = UrlParameter.Optional }),DataTokens = new RouteValueDictionary(new { area = "Second", namespaces = new[] { "MvcAreaDemo2.Areas.Second.Controllers" } })}); View Code? ? ? ? 3.在Area的使用況下,如果要跳轉(zhuǎn)到另外一個(gè)Area的頁面,則使用Html.ActionLink進(jìn)行編寫似乎更加麻煩了,有木有更加簡便的方法?
轉(zhuǎn)載于:https://www.cnblogs.com/fhlj/p/3615244.html
總結(jié)
以上是生活随笔為你收集整理的Mvc系统学习9——Areas学习的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: MarkDown2安装后不能预览的问题
- 下一篇: Win7安装MarkdownPad2破解