Sök…


Introduktion

Routing är hur ASP.NET MVC matchar en URI till en åtgärd. Routing-modulen är ansvarig för att kartlägga inkommande webbläsarförfrågningar till specifika MVC-controlleråtgärder.

MVC 5 stöder en ny typ av routing, kallad attribut routing. Som namnet antyder använder attributruting attribut för att definiera rutter. Attributruting ger dig mer kontroll över URI: erna i din webbapplikation.

Anpassad routing

Anpassad routing ger specialiserat behov av routing för att hantera specifika inkommande förfrågningar.

För att definiera anpassade rutter, kom ihåg att ordningen på rutter som du lägger till i ruttabellen är viktig.

public static void RegisterRoutes(RouteCollection routes)
{
    routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
    
    // this is an advanced custom route
    // you can define custom URL with custom parameter(s) point to certain action method
    routes.MapRoute(
    "CustomEntry", // Route name
    "Custom/{entryId}", // Route pattern
    new { controller = "Custom", action = "Entry" } // Default values for defined parameters above
    );

    // this is a basic custom route
    // any custom routes take place on top before default route
    routes.MapRoute(
    "CustomRoute", // Route name
    "Custom/{controller}/{action}/{id}", // Route pattern
    new { controller = "Custom", action = "Index", id = UrlParameter.Optional } // Default values for defined parameters above
    );

    routes.MapRoute(
    "Default", // Route name
    "{controller}/{action}/{id}", // Route pattern
    new { controller = "Home", action = "Index", id = UrlParameter.Optional } // Default values for defined parameters above
    );
}

controller och action är reserverade. Som standard kartlägger MVC {controller} del av URL: n till klassen <controller>Controller och letar sedan efter en metod med namnet <action> utan att lägga till några suffix.

Även om det kan vara frestande att skapa en familj av rutter med hjälp av {controller}/{action}/{parameter} -mall, anser du att genom att göra detta avslöjar du strukturen i din applikation och gör webbadresser något spröda eftersom att ändra namnet på kontrollern ändrar rutt och bryter länkarna som sparats av användaren.

Föredrar uttrycklig ruttinställning:

routes.MapRoute(
    "CustomRoute", // Route name
    "Custom/Index/{id}", // Route pattern
    new { controller = "Custom", action = nameof(CustomController.Index), id = UrlParameter.Optional }
);

(du kan inte använda nameof operatör för controller namn som det kommer att ha ytterligare suffix Controller ) som måste utelämnas vid inställning controller namn på rutten.

Lägga till anpassad rutt i Mvc

Användaren kan lägga till anpassad rutt, kartlägga en URL till en specifik åtgärd i en kontroller. Detta används för sökmotoroptimeringsändamål och gör webbadresser läsbara.

routes.MapRoute(
  name: "AboutUsAspx", // Route name
  url: "AboutUs.aspx",  // URL with parameters
  defaults: new { controller = "Home", action = "AboutUs", id = UrlParameter.Optional }  // Parameter defaults
);

Attribut routing i MVC

Tillsammans med det klassiska sättet att definiera rutten definierade MVC WEB API 2 och sedan MVC 5-ramverk Attribute routing :

public class RouteConfig
{
    public static void RegisterRoutes(RouteCollection routes)
    {
        routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
 
        // This enables attribute routing and must go  before other routes are added to the routing table.
        // This makes attribute routes have higher priority
        routes.MapMvcAttributeRoutes();  
    }
}

För rutter med samma prefix inuti en styrenhet kan du ställa in ett gemensamt prefix för hela handlingsmetoder inuti styrenheten med attributet RoutePrefix .

[RoutePrefix("Custom")]
public class CustomController : Controller
{
    [Route("Index")]
    public ActionResult Index()
    {
        ...
    }
}

RoutePrefix är valfritt och definierar den del av webbadressen som är förinställd för alla kontrollerens åtgärder.

Om du har flera rutter kan du ställa in en standardrutt genom att fånga åtgärd som parameter och sedan använda den för hela kontrollen såvida inte specifikt Route definierat i vissa handlingsmetoder som åsidosätter standardrutten.

[RoutePrefix("Custom")]
[Route("{action=index}")]
public class CustomController : Controller
{
    public ActionResult Index()
    {
        ...
    }

    public ActionResult Detail()
    {
        ...
    }
}

Grunderna för routing

När du begär url yourSite/Home/Index via en webbläsare, kommer routingmodulen rikta begäran till Index action metoden HomeController klass. Hur vet det att skicka begäran till den här klassens specifika metod? där kommer RouteTable.

Varje applikation har en ruttabell där den lagrar ruttmönstret och information om var du ska rikta begäran till. Så när du skapar din mvc-applikation finns det en standardrutt som redan är registrerad i routingtabellen. Det kan du se i klassen RouteConfig.cs .

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

Du kan se att posten har ett namn och en mall. Mallen är ruttmönstret som ska kontrolleras när en förfrågan kommer in. Standardmallen har Home som värdet för kontrollens url-segment och Index som värdet för actionsegmentet. Det innebär att om du inte uttryckligen skickar en kontrollernamn och åtgärd i din begäran, kommer den att använda dessa standardvärden. Detta är anledningen till att du får samma resultat när du går in på yourSite/Home/Index och yourSite

Du kanske har lagt märke till att vi har en parameter som heter id som det sista segmentet i vårt ruttmönster. Men i standardinställningarna anger vi att det är valfritt. Det är anledningen till att vi inte behövde ange ID-värdet i den url vi försökte.

Gå tillbaka till indexmetoden i HomeController och lägg till en parameter till det

public ActionResult Index(int id)
{
     return View();
}

Nu sätter en Visual Studio brytpunkt i denna metod. Kör ditt projekt och få åtkomst till yourSite/Home/Index/999 i din webbläsare. Brytpunkten träffas och du bör kunna se att värdet 999 nu är tillgängligt i id parametern.

Skapa ett andra ruttmönster

Låt oss säga att vi vill ha en uppsättning så att samma handlingsmetod kallas för ett annat ruttmönster. Vi kan göra det genom att lägga till en ny ruttdefinition till ruttabellen.

public static void RegisterRoutes(RouteCollection routes)
{
   routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
   
   // New custom route definition added
   routes.MapRoute("MySpecificRoute",
    "Important/{id}",
    new { controller = "Home", action = "Index", id = UrlParameter.Optional });

   //Default catch all normal route definition
   routes.MapRoute("Default", "{controller}/{action}/{id}",
             new { controller = "Home", action = "Index", id = UrlParameter.Optional });
}

Den nya definitionen som jag lade till har ett mönster Important/{id} där id igen är valfritt. Det betyder att när du begär yourSiteName\Important eller yourSiteName\Important\888 kommer det att skickas till indexåtgärden för HomeController.

Order för registrering av ruttdefinition

Ruttregistreringens ordning är viktig. Du bör alltid registrera de specifika ruttmönstren innan generisk standardrutt.

Fånga alla rutter

Anta att vi vill ha en rutt som tillåter ett obundet antal segment som så:

Vi måste lägga till en rutt, normalt i slutet av ruttabellen eftersom det troligtvis skulle fånga alla förfrågningar, så:

routes.MapRoute("Final", "Route/{*segments}",
      new { controller = "Product", action = "View" });

I regulatorn kan en åtgärd som kan hantera detta vara:

public void ActionResult View(string[] segments /* <- the name of the parameter must match the name of the route parameter */)
{
    // use the segments to obtain information about the product or category and produce data to the user
    // ...
}

Fånga alla rutter för att möjliggöra routing på klientsidan

Det är en bra praxis att koda tillståndet för enkel sida-applikation (SPA) i url:

my-app.com/admin-spa/users/edit/id123

Detta gör det möjligt att spara och dela applikationstillstånd.
När användaren sätter url i webbläsarens adressfält och träffar anges servern måste ignorera klientsidan av den begärda url. Om du betjänar ditt SPA som en visad rakknivvy (resultat av samtalskontrollens handling) snarare än en statisk html-fil kan du använda en fångst-rutt:

public class AdminSpaController
{
    [Route("~/admin-spa/{clienSidePart*}")]
    ActionResult AdminSpa()
    {
        ...
    }
}

I detta fall returnerar servern bara SPA, och den initialiserar sig sedan enligt rutten. Detta tillvägagångssätt är mer flexibelt eftersom det inte beror på url-omskriva modulen.

Attribut routing i områden

För att använda Attribut Routing i områden krävs registrering av områden och [RouteArea(...)] definitioner.

I RouteConfig.cs :

public class RouteConfig
{
    public static void RegisterRoutes(RouteCollection routes)
    {
        routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
        routes.MapMvcAttributeRoutes();
        AreaRegistration.RegisterAllAreas();
    }
}

I en provområdesregleringsdefinition för attributruting:

[RouteArea("AreaName", AreaPrefix = "AreaName")]
[RoutePrefix("SampleAreaController")]
public class SampleAreaController : Controller
{
    [Route("Index")]
    public ActionResult Index()
    {
        return View();
    }
}

För att använda Url.Action länkar i områden:

@Url.Action("Index", "SampleAreaController", new { area = "AreaName" })


Modified text is an extract of the original Stack Overflow Documentation
Licensierat under CC BY-SA 3.0
Inte anslutet till Stack Overflow