3

Okay, I've got this case where I have two controllers:
HomeController
MathController

I want the routing for my HomeController to stay as default:{controller}/{action}/{id}. But I want to access the actions in the MathController with http://myurl/Task/Math/{action}.

So what I've done is to write my RouteConfig like this:

    routes.MapRoute(
        name: "Math",
        url: "Task/{controller}/{action}",
        defaults: new { controller = "Math", action = "Index" }
    );  

    routes.MapRoute(
        name: "Default",
        url: "{controller}/{action}/{id}",
        defaults: new { controller = "Home", action = "Hem", id = UrlParameter.Optional }
    );

When using the above configuration and manually entering the URLs in the browser both routing methods are working. Though when trying to add a "actionLink" it always uses the Task/{Controller}/{Action} route. Even if I'm creating a link for the Home controller like this: @Html.ActionLink("Hem", "Hem", "Home", null, new { @class = "navbar-brand" })

How do I configure either my routing or my action links so that I'll get the preferred functionality?

jimutt
  • 667
  • 2
  • 13
  • 29

1 Answers1

3

Routes match from top down in RouteConfig.cs. Your problem is that both route configs are "catch all" routes, which means both work for any controller/action. When you use @Html.ActionLink, MVC will render the url based on the 1st route it finds, which matches your "Task" path. There are few ways to change this to get what you want.

If you want to only use the "Task" path for the Math controller, then I'd change your route to this:

routes.MapRoute(
    name: "Math",
    url: "Task/Math/{action}",
    defaults: new { controller = "Math", action = "Index" }
);

If you want to use several controllers for the "Task" path, then you can add a route constraint. You can use it like below and specify a list of controllers (regex), or you can create your own custom Route Constraint class and implement whatever functionality you want.

routes.MapRoute(
    name: "Math",
    url: "Task/{controller}/{action}",
    defaults: new { controller = "Math", action = "Index" },
    constraints: new { controller = "Math|OtherController" }
);

Or if you want to keep all controllers/actions matching both urls, then you have to flip your routes to get the default route to display first, or you can use @Html.RouteLink like so:

@Html.RouteLink("Hem", "Default", new { controller = "Home", action = "Hem" }, new { @class = "navbar-brand" })
Ashley Lee
  • 3,810
  • 1
  • 18
  • 26