Routing در MVC

جمعه 30 مرداد 1394

این مقاله نحوه Routing (مسیریابی) در MVC را بررسی خواهد نمود.

Routing در MVC

MVC از سیستم مسیریابی ASP.NET برای Map کردن درخواستهای ورودی از مرورگر به متد کنترلر استفاده می کند. این یک سیستم pattern-matching (الگوی تطبیق) برای Map کردن درخواستهای ورودی برای مشخص نمودن کنترلرهای MVC می باشد. اگر این موفق به مسیردهی درخواستهای ورودی نشود سپس MVC پیغام خطای 404 تولید می نماید. سیستم مسیریابی ASP.NET از Route Table (جدول مسیر) استفاده می کند.

Route Table در اولین اجرای برنامه ساخته می شود. زمانی که اولین بار برنامه MVC اجرا می شود متد ()Application_Start صدا زده می شود. این متد خود متد ()RegisterRoutes را صدا می زند.

متد ()RegisterRoutes جدول Route را ساخته و یک یا چند الگوی مسیردهی دیگر را به جدول Route یا همان RouteTable اضافه می نماید. اگر ما یک برنامه MVC 4 یا MVC 5 ایجاد کنیم این برنامه به صورت پیش فرض دارای route های Register مانند شکل زیر است.

 

Global.asax File

    protected void Application_Start()  
    {  
       AreaRegistration.RegisterAllAreas();  
      
       WebApiConfig.Register(GlobalConfiguration.Configuration);  
       FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);  
       RouteConfig.RegisterRoutes(RouteTable.Routes);  
       BundleConfig.RegisterBundles(BundleTable.Bundles);  
    }   

 

RouteConfig

public static void RegisterRoutes(RouteCollection routes)  
{  
   routes.IgnoreRoute("{resource}.axd/{*pathInfo}");  
   routes.MapRoute(  
   name: "Default",  
   url: "{controller}/{action}/{id}",  
   defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }  
   );  
} 

 

این تکه کدها می تواند یک مسیر “Default” با الگوی "{controller}/{action}/{id}” ثبت نماید. همچنین MVC دارای مقادیری برای کنترلر ها و اکشن ها می باشد. این به این معناست که هنگامی که ما url ای مانند :

 /<http:// <ApplicationDomain

بدون کنترلر وارد نماییم متد Index از کنترلر Home اجرا می شود. همچنین اگر url ای تنها با نام کنترلر وارد نماییم متد Index این کنترلر فراخوانی می شود. “Id” پارامتری است که به اکشن متد پاس داده می شود و در این Route اختیاری می باشد. (یعنی می توان آن را وارد نکرد)

 

ما دیدیم که Routing در MVC شامل 3 قسمت زیر است :


نام کنترلر

نام متد اکشن

پارامتری که به این متد پاس داده می شود

 

لازم به ذکر است که اگر در پروژه خود بیش از یک Route دارید نام های آنها باید متفاوت و منحصر به فرد باشند.

 

 

ما همچنین می توانیم توسط دستور ()routes.IgnoreRoute از فریم ورک بخواهیم که از بعضی مسیر ها چشم پوشی نماید. فرض کنید نمی خواهیم MVC درخواستهای زیر را انجام دهد :
 

http://<ApplicationDomain>/Home/

http://<ApplicationDomain>/Home/index

http://<ApplicationDomain>/Home/index/10

 

برای این کار نیاز به استفاده از دستور ()routes.IgnoreRoute می باشد.

 

    public static void RegisterRoutes(RouteCollection routes)  
    {  
       routes.IgnoreRoute("Home/*pathInfo}");  
      
       routes.MapRoute(  
       name: "Default",  
       url: "{controller}/{action}/{id}",  
       defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }  
    );  
      
    }   

حال url های موجود در شکل قبلی را امتحان می نماییم. تنها اولین درخواست انجام شده و در بقیه درخواستها با پیغام 404 روبرو خواهیم شد.

 

 

اضافه نمودن Route سفارشی و محدودیتها

حالا برای تست محدودیت Route یک کنترلر اضافه می کنیم که دارای یک متد با نام Details می باشد.

public ActionResult Details(int DepartmentID)  
{  
return Content("received the DepartmentID as : "+ Convert.ToString(DepartmentID));  
} 

حالا یک Route برای Department اضافه می نماییم :

public static void RegisterRoutes(RouteCollection routes)  
{  
   routes.IgnoreRoute("{resource}.axd/{*pathInfo}");  
  
   routes.MapRoute(  
   name: " Department",  
   url: "Department/{DepartmentID}",  
   defaults: new { controller = "Department", action = "Details"}  
   );  
  
   routes.MapRoute(  
   name: "Default",  
   url: "{controller}/{action}/{id}",  
   defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }  
   );   
} 

لطفا توجه داشته باشید که باید ما این Route را قبل از Route اصلی قرار دهیم.

حالا اگر به [http://localhost:[Port]/Department/[int value بروید با صفحه زیر روبرو می شوید:

 

اگر اقدام به پاس دادن رشته نمایید با پیغام زیر مواجه می شوید.

 

 

زمانی که ما یک Route اضافه می کنیم می توانیم آن را محدود نماییم. ما می توانیم با استفاده از Regular expression ها و یک شیء که اینترفیس IRouteConstraint را پیاده سازی می کند Route را محدود نماییم.

حالا ما می خواهیم کاربران را محدود کنیم که تنها اعداد را پاس دهند. برای این کار لازم است تا ما DepartmentID را محدود نماییم.

ما برای این کار از Regular Expression aka RegEx استفاده می نماییم. بنابراین Route مانند زیر می شود:

routes.MapRoute(  
name: "Department",  
url: "Department/{DepartmentID}",  
defaults: new { controller = "Department", action = "Details" },  
constraints: new { DepartmentID=@"\d+"}  
); 

 

حالا دوباره هر دو url را باز می کنیم. دومی با ارور 404 مواجه می شود چون MVC نمی تواند route را در RouteTable پیدا کند.

 

 

 

توجه داشته باشید که این خیلی مهم است که محدودیت RegEx را یه همه قسمتهای route از قبیل کنترلر، اکشن و پارامتر اضافه نمایید.

همچنین ما یک Route توسط IRouteConstraint ساختیم. این داخل System.Web.Routing می باشد و دارای یک متد می باشد  :

public bool Match(HttpContextBase httpContext, Route route, string parameterName, RouteValueDictionary values, RouteDirection routeDirection)

همچنین ما می خواهیم کاربران را وادار کنیم تا محدوده ای بین 20 تا 30 را برای DepartmentID انتخاب کنند.

برای این کار ما نیاز داریم تا کلاسی برای پیاده سازی IRouteConstraint مانند زیر ایجاد نماییم.

 

public class MyConstraint :IRouteConstraint  
{  
  
   public bool Match(HttpContextBase httpContext, Route route, string parameterName, RouteValueDictionary values, RouteDirection routeDir   ection)  
   {  
      int id=0;  
      int.TryParse(values[parameterName].ToString(), out id);  
      if (20 <= id && id <= 30)  
      return true;  
      else  
      return false;  
   }  
} 

 

حالا نیاز است تا محدودیت زیر را برای Route در نظر بگیریم :
 

    routes.MapRoute(  
    name: "Department",  
    url: "Department/{DepartmentID}",  
    defaults: new { controller = "Department", action = "Details" },  
    constraints: new { DepartmentID=new MyConstraint()}  
    );   

 

حالا برنامه را اجرا کرده و خروجی ها را مشاهده نمایید :
 

 

 

برنامه نویسان

نویسنده 3355 مقاله در برنامه نویسان

کاربرانی که از نویسنده این مقاله تشکر کرده اند

در صورتی که در رابطه با این مقاله سوالی دارید، در تاپیک های انجمن مطرح کنید