Friday, August 24, 2018

Removing a Route parameter from an ActionLink in MVC4

I am having a bit of a problem with a RouteData Value lingering in my View and making my @Html.ActionLink(...) look a bit ugly.

In my routes I have this:

routes.MapRoute(
    name: "SubItemLinked",
    url: "SubItems/{subitemId}/{controller}/{action}/{id}",
    defaults: new { controller = "DeepDownItems", action = "Index", id = UrlParameter.Optional },
    constraints: new { subitemId = "^[0-9]*$", id = "^[0-9]*$" }
);

routes.MapRoute(
    name: "ItemLinked",
    url: "Items/{itemId}/{controller}/{action}/{id}",
    defaults: new { controller = "SubItems", action = "Index", id = UrlParameter.Optional },
    constraints: new { itemId = "^[0-9]*$", id = "^[0-9]*$" }
);

The above allows me to have Urls like these:

  • ~/Items/3 <= will show all SubItems for Item number 3
  • ~/Items/3/SubItems/Create <= exactly what you would expect
  • ~/SubItems/5 <= to show all DeepDownItems of SubItem number 5

and so on...

Now, of course the DeepDownItems controller will recognise the subitemId parameter and use it for retrieval of stuff from the DB. Problem is that if I want to put a link back to the SubItems list, I don't need this subitemId anymore and I need to remove it from the RouteValueDictionary.

As an example of the flow, let's assume I go to ~/SubItems/5, I see the list of all DeepDownItems of SubItem 5, which is correct. In that View I have this:

@Html.ActionLink("Go Back", "Index", "SubItems", new { itemId = ViewBag.itemid, subitemId = String.Empty }, null)

This should generate, according to the Routes, a link to ~/Items/3. I had to put subitemId = String.Empty or it would have matched with the top route. Problem is that the url being generated is like this ~/Items/3?subitemId=5, so basically is matching the Route correctly but then it is not clearing the subitemId parameter as instructed.

Do you have any ideas on how to do it? Notice that I have other links (Edit/Create) on the View that rely on that parameter being present and added automatically so I would really like to only remove it from that link rather than the whole Dictionary.

Solved

Not sure if it's the same issue I've been fighting for the last few hours, but if it is: Try using @Html.RouteLink where you can specify which route to create a link from.

Something like the following, if I've managed to decipher your example :P

@Html.RouteLink("Go Back", "ItemLinked", new {
        controller = "SubItems",
        action = "Index", 
        itemId = ViewBag.itemid,
    })

No comments:

Post a Comment