(.NET進階五)Route原理/約束/特殊url生成/Area分區

目錄

一、理解路由的原理

 二、路由規則定義與應用

三、路由數據、特殊匹配、默認值與約束

 四、通過路由生成URL

五、分區項目


 

一、理解路由的原理

  1. 爲什麼要定義路由?
    1. ASP.NET-MVC項目開發中的地位
      • 路由的定義->URL訪問規則,佔用的開發量很小,但是非常重要,因爲任何請求都離不開路由
    2. 使用路由的好處
      • 能夠根據系統需求,靈活的劃分請求規則(不同模塊請求的URL是不一樣的)
      • 屏幕物理路徑,提高系統安全性,一般情況是無法根據URL分析視圖文件在站點目錄中的位置
      • 用利於搜索引擎優化,可以將URL請求統一規範,以後維護中,如果頁面發生變化,URL可以保持不變
  2. ASP.NET MVC路由
    1. 路由-源自網絡中路由器的概念:負責網絡中數據傳輸路徑
    2. ASP.NET MVC路由系統主要職責:將各種請求路徑轉發給控制器處理
    3. 路由的雙向系統功能
      1. URL長相映射到Controller和Action:根據用戶輸入的URL觸發對應控制器並調用動作方法
      2. Controller和Action還可以反向映射並構造URL:根據控制器和行爲構造出URL供用戶使用

 二、路由規則定義與應用

ADP.NET MVC默認路由

  • RouteConfig.cs中的URL規則定義
public static RegisterRiutes(RouteCollection routes)
{
    routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
    routes.MapRoute(
        name:"Default",
        url:"{controller}/{action}/{id}",
        defaults:new {controller = "SysAdmin",action = "Index",
            id = UrlParameter.Optional}
    );
}
  • URL模式
    • 上面的URL中的參數值是:{controller}/{action}/{id},稱之爲URL模式
    • 該模式的是一串字符串,包括一些固定的"字符字面量"和"佔位符",佔位符用大括號"{}"表示
    • URL模式規定了URL路徑的定義規則
  • URL模式解釋
    • 定義語法:{佔位符1}字面量{佔位符2}字面量...{佔位符n}字面量n
    • 佔位符
      • 佔位符可以是一個字符串或字符,比如"x","id","year"等
      • 字面量可能是一個比較固定的字符,比較常見的是斜杆"/",也可以是字符串
    • 示例:{table}/Details.aspx     News/{action}/{id}     {pro}-{city}/{action}
    • 特殊規則:
      • 不能以斜杆"/"或者波浪線"~"字符開頭,不能包含"?":如/{controller} 、~news/details{id}、{action}?id = {id}均不符合要求
      • 佔位符不能連續:如{controller}{action}/{id}不符合要求
  • URL模式匹配示例
    • {Controller}/{action}/{id}                     /Student/Detail/1       /SysAdmin/AdminLogin/2
    • {first}/{second}/{third}                         /student/Detail/1        /sysadmin/adminlogin/2
    • {table}/Detail.aspx                             /news/Details.aspx    /product/Details.aspx
    • Course/{action}/{id}                           /Course/list/001        /Course/Detail/001
    • {lanuage}-{country}/{action}              /zh-cn/content           /en-us/display
    • {reporttype}/{year}/{month}/{day}      /sales/2015/1/5
    • 匹配要求
      • 字面量:必須嚴格匹配,即實際請求中的字符串和路由模式中的字面量字符串必須完全一致
      • 大小寫:URL模式匹配的時候不區分大小寫
      • 常量:滅有包含在大括號內的信息被作爲常量對待;比如上面的Course,以及後續學習中的分區項目中路由的定義Admin/{controller}/{action}/{id}
    • 思考:對同一個URL,如果多個路由都能匹配,該如何解析?
      • :如果一個URL能夠在多個路由中匹配,則默認使用第一個匹配的路由
  • 定義多個路由的要求
    • MapRoute(
      
              string name,//名稱
              string url,//URL模式
              object defaults,//默認值
              object constraints,//約束
              string[] namespaces//命名空間
      
      )
      
      public static RegisterRoutes(RouteCollection routes)
      {
          routes.MapRoute(
              name:"Default",
              url:"{controller}/{action}/{id}",
              defaults:
              new {controller = "SysAdmin",action = "Index",Id = UrlParameter.Optional},
              namespace:new string[]{"對應控制器的命名空間"}
          );
      
          routes.MapRoute(
              "blog",
              "{year}/{month}/{day}",
              new {controller = "blog",action = "index"},
              constraints:new{year = @"\d{4}",month = @"\d{2}",day = @"\d{2}"}//約束
          );
      }

       

      public static RegisterRoutes(RouteCollection routes)
      {
          routes.MapRoute(
              name:"Default",
              url:"{controller}/{action}/{id}",
              defaults:
              new {controller = "SysAdmin",action = "Index",Id = UrlParameter.Optional}
          );
      
          routes.MapRoute(
              name:"Test1",
              url:"{first}/{second}/{third}",
              defaults:
              new {controller = "Work",action = "Index",Id = UrlParameter.Optional}
          );
      }
      
      
      <a href = "/Home/Index/2015">測試多路由優先匹配順序</a>
      

       多路由匹配選擇:如果一個URL能夠在多個路由中匹配,則默認使用第一個匹配的路由

    • 關於UrlPrameter.Optionl

      • 作用:該參數可以作爲路由參數的默認值,當需要讓"/Home/Index"或"/Home"能夠正常匹配,但又不希望一個無意義的值,可以使用該參數

 

  • 路由匹配總結
    • 關於{controller}/{action}
      • 必不可少:在一個實際的MVC系統中,{controller}/{action}必不可少,如果缺少就會出現找不到路徑而出錯
      • 約定規則:這個佔位符是MVC中約定的,並且會被解析成控制器和對應的方法
      • 位置靈活:這兩個約定的佔位符可以在任意位置
    • 其他佔位符
      • 僅僅是佔位:比如{aa}/{ABC}/...,這裏面的aa不能被解析成控制器,ABC也不能被解析成動作方法
      • 默認要求:一個路由中,如果沒有規定{controller}/{action},或者只是規定其中之一,則沒有規定的部分將使用默認值
    • 匹配順序
      • 優先使用:多個路由匹配一個URL則優先匹配的會使用
      • 儘量避免:定義多個路由時儘量避免出現多匹配

三、路由數據、特殊匹配、默認值與約束

  1. 路由數據
    1. 存儲方法
      1. 在ASP.NET MVC路由系統中,RouteData對象用來保存URL模式和實際URL匹配產生的路由數據
      2. 路由數據保存方式:“鍵-值”對,RouteData是視圖基類和控制器基類的屬性
    2. 路由和控制器的映射 
    3. 使用路由數據
      1. RouteData.Values介紹
        1. 是RouteDataValueDictionary類型,使用方式和Dictionary<TKey,TValue>類似
        2. RouteData定義爲視圖和控制器基類的屬性
      2. 在視圖中可以遍歷RouteData.Values,來輸出路由匹配產生的路由數據
        public static void RegisterRoutes(RouteCollection routes)
        {
            routes.IgnoreRoute("{resource}.axd/{pathInfo}");   
            routes.MapRoute(
                name:"Default",
                url:"{controller}/{action}/{id},
                default:new {controller = "Home",action = "Index",id = 10}
             );
        }
        
        
        public ActionResult Index()
        {
            string id = RouteData.Values["id"].ToString();//通過鍵值對的取值方式取值
            ViewBag.id = id;
            return View();
        }
        
        
        <!--在視圖中輸出控制器中獲取的數據>
        @ViewBag.id</br>
        <!--在視圖中直接輸出>
        @ViewContent.RouteData.Values["id"]</br>
        <!--在視圖中遍歷輸出>
        @{
            foreach(KeyValuePair<string,object> data in ViewContent.RouteData.Values)
            {
                var info = data.Key + "=" (data.Value ?? string.Empty);
                @info</br>
            }
        }

         

  2. 特殊URL匹配規則

 

  1. *匹配
    1. *用來匹配URL剩餘部分 
      routes.MapRoute(
          "default",
          "{controller}/{action}/{operation}/{*plus}"
      );
      
      
           URL                              路由數據
      /home/index/select/a/b          plus = "a/b" 
      /home/index/update/a/b/c        plus = "a/b/c"
      /home/index/delete/             plus = null

       

  2.  貪婪匹配規則

  3. 路由默認值

      1. 當URL模式中包含除"/"之外的字面量時,爲佔位符定義的默認值不起作用

  4. 路由約束

    1. 定義URL模式爲{year}/{month}/{day}

      public static RegisterRoutes(RouteCollection routes)
      {
          routes.MapRoute(
              "blog",
              "{year}/{month}/{day}",
              new {controller = "blog",action = "index"},
              constraints:new{year = @"\d{4}",month = @"\d{2}",day = @"\d{2}"}//約束
          );
      }

       

 四、通過路由生成URL

  1. 視圖中的鏈接
    1. 鏈接方式
      1. 純靜態鏈接:直接指向鏈接地址,一般不需要改變
      2. 動態鏈接:爲了更好的保證web項目移植的時候路徑的正確
    2. Url.Content()方法
      <img src = "@Url.Content("~/Images/Students/1001.png")"/>
      <a href = "@Url.Content("~/students/getstulist/1001">學員詳情</a>

       

    3. 不足:當路由規則變化時,需要修改所有路徑

  2. 使用Action()生成鏈接

    1. Url.Action()方法
      public string Action(
              string actionName,        //動作方法名稱
              string controllerName,    //控制器名稱(沒有時,默認使用當前上下文的控制器)
              string routeValues        //路由參數值(是一個匿名對象)
      )
      
      public string Action(string actionName)
      public string Action(string actionName,string controllerName)

       

    2. 示例
      1. URL模式爲:stumanage/{controller}/{action}/{id}
        @Url.Action("list","student",new{id=1001})  -->/stumanage/students/list/1001
        
        @Url.Action("list","student",new{id = 1001,age=20,gender= 0})
                -->/stumanage/students/list/1001?age=20&gender=0//溢出的參數以?和&拼接在URL模式之後
        
        <a href = "@Url.Action("list","student",new{id = 1001,age=20,gender= 0})">學生管理</a>

         

  3. 使用ActionLink()生成超鏈接

    1. Html.ActionLink()方法

      MvcHtmlString ActionLink(
          string linkText,//鏈接文本
          string actionName,string controllerName,object routeValues,//routeValue是一個匿名對象
          object htmlAttributes//生成的html屬性(匿名對象)
      )

       

    2.  

      示例

      URL模式爲{controller}/{action}/{id}

       

       

      <a href="@Url.Action("GetStuList","student",new{id=1001,age=20,gender=0})">學生管理</a>
      
          <!--生成的鏈接爲> -->  <a href="/Student/GetStuList/1001?age=20&gender=0">詳細信息</a>
      
      </br><br/>
      
      @Html.ActionLink("詳細信息","GetStuList","Student",new{id=1001,age=20,gender=0},
          new {@class="stulink",title="學生姓名"})
      
         <!--生成的鏈接爲> --> <a class="stulink" href="/Student/GetStuList/1001?age=20&gender=0" title="學生姓名">詳細信息</a>

      提示:使用Html.RouteLink()代替Html.ActionLink(),可以使用Html.Action()代替Url.Action

 

五、分區項目

 

分區項目需要對路由的命名空間進行註冊

MapRoute(

        string name,//名稱
        string url,//URL模式
        object defaults,//默認值
        object constraints,//約束
        string[] namespaces//命名空間

)

//分區項目中存在同名控制器時,需在RouteConfig文件中註冊命名空間
public static RegisterRoutes(RouteCollection routes)
{
    routes.MapRoute(
        name:"Default",
        url:"{controller}/{action}/{id}",
        defaults:
        new {controller = "SysAdmin",action = "Index",Id = UrlParameter.Optional},
        namespace:new string[]{"對應控制器的命名空間"}
    );
}

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章