locked
ActionLink generation issue with custom IRouteHandler RRS feed

  • Question

  • User-1660770209 posted

    I am having problems with the strongly-typed Html.ActionLink method when my routes are configured in the following manner. 

    // Custom IRouteHandler route #1
    routes.Add(new Route("simpleurl", null, new CustomRouteHandler());
    
    // Custom IRouteHandler route #2
    routes.Add(new Route("{controller}/{action}/{id}", AnotherCustomRouteHandler()) {
      Defaults = new RouteValueDictionary(new {controller = "Home", action = "Index", id = ""}),
      Constraints = new RouteValueDictionary((object)null)
    };


     

     

    Both routes work as they should, however generating links for the second route with the strongly typed helpers results in routes targetting the first route. For example:

    Html.ActionLink<MyController>(mc => mc.SomeAction(), "Link to SomeAction");

    Instead of producing the route of /My/SomeAction as expected, I get /simpleurl?Controller=MyController&Action=SomeAction.

    Any thoughts on why this is the case?

     

     

     

    Friday, October 23, 2009 6:24 PM

Answers

  • User-1563960693 posted

    Sure.  Would this work?

    routes.Add(new Route("{weblog}", null, new RouteValueDictionary(new { weblog = "metaweblog" }), new XmlRpcRouteHandler(container)));

    Hope this helps,

    Jason Conway

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Sunday, October 25, 2009 5:03 PM

All replies

  • User-1563960693 posted

    The Url (and tokens) in the Route act as positioned placeholders.  In the case of your first Route, 'simpleurl' is a literal prefix and when supplying the required Controller and Action names (which the ActionLink does), the behavior is to put those unused, untokenized values in the query string.  This means that this route is used every time in its current form (no constraints).  As an example, you could use a literal in addition to tokens as a non-existent virtual directory:

    routes.MapRoute(
        "UserShortcuts",
        "aspnetmvcrocks/{action}/{id}",
        new { controller = "user", id = "" },
        new { action = new ListConstraint(ListConstraintType.Include, "signin", "signout") }
    );

     

    <%= Html.ActionLink("signin", "signin", "user") %>

    Where 'aspnetmvcrocks' is the literal (looks like a virtual directory) and when this route is satified by using ActionLink, the end result looks like this:

              Salient6 Samples Literal Route Result

    Just out of curiosity, what is your intended purpose of the 'simpleurl' route?

    Hope this helps,

    Jason Conway

    Saturday, October 24, 2009 8:52 PM
  • User-1660770209 posted

    The literal URL in this case is used as an endpoint for a blog's MetaWeblog service.  My actual route looks like:

    routes.Add(new Route("metaweblog", null, new XmlRpcRouteHandler(container)));

    This adds the route with a specialized XmlRpcRouteHandler that in turn always returns back my MetaWeblogHandler.

    There is no controller to speak of in this instance, rather just a handler that intercepts all of the calls as XmlRpc and calls corresponding methods on my MetaWeblogHandler.

    Any thoughts of how I can keep ActionLink happy in this situation? Thanks for the help.

    Sunday, October 25, 2009 9:44 AM
  • User-1563960693 posted

    Sure.  Would this work?

    routes.Add(new Route("{weblog}", null, new RouteValueDictionary(new { weblog = "metaweblog" }), new XmlRpcRouteHandler(container)));

    Hope this helps,

    Jason Conway

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Sunday, October 25, 2009 5:03 PM
  • User-1660770209 posted

     Thanks, that works great.

    Sunday, October 25, 2009 6:10 PM