tags:

views:

37

answers:

2

To support legacy URLs in my application, I use a regex to convert URLs of the form /Repo/{ixRepo}/{sSlug}/{sAction} to the new form /Repo/{sName}/{sAction}, using the ixRepo to get the correct sName. This works well, and I can redirect the user to the new URL with a RedirectResult.

However, I'd like to catch legacy URLs with an invalid action before I redirect the user. How can I verify if a URL string will map to a registered route? MVC clearly does this internally to map a request to the correct action, but I'd like to do it by hand.

So far, I've come up with this:

var rd = Url.RouteCollection.GetRouteData(new HttpContextWrapper(new HttpContext(
    new HttpRequest("", newPath, ""),
    new HttpResponse(null))));

which appears to always return a System.Web.Routing.RouteData, even for bad routes. I can't find a way to check if the route was accepted as a catch all, or if actually mapping to a route that's registered on the controller.

How can I use MVC's routing system to check if a URL maps to a valid controller/action via a registered route?

(I've seen http://stackoverflow.com/questions/1621212/asp-net-mvc-verify-the-existence-of-a-route, but that's really inelegant. MVC has a routing system built in, and I'd like to use that.)

+1  A: 

Wrong question. Anything can be a route, whether or not it actually maps to an action.

I think you're asking, "Will this execute OK, or will it 404?" That's a different question.

For that, you need to do what MVC does. Look in the MVC source at MvcHandler.ProcessRequestInit and then ControllerActionInvoker.InvokeAction to see how MVC looks up the controller and action, respectively.

Craig Stuntz
+1  A: 

If you know the controller and ask for valid actions, just do some reflection stuff as done in here.

If the redirected url goes to your application, then you can check if the url goes to a valid route. Some code on haacked.com http://haacked.com/archive/2007/12/17/testing-routes-in-asp.net-mvc.aspx does route testing as a unit test. After this you have controller and action as routedata and you have to do, what Craig said "do the same as mvc does".
The routing system maps request uris to route handler. The mvc route handler (class) throws an exception if it fails. There is no checking.

You can add constraints to your routes. If you constrain the action property. Then checking if the url goes to a valid route my be what you want.

Christian13467
The code linked in the other answer only checks that the `action` token is OK, not the whole set of route values (e.g., `id`).
Craig Stuntz