ASP.NET MVC twitter / myspace style routing

This is my first post after a long lurker - so be careful :-)

I have a twitter-like site where people can sign up and choose a "friendly URL", so they will have something like this on my site:

mydomain.com/benjones

I also have static pages at the root level, such as:

mydomain.com/about

and of course my homepage:

mydomain.com/

I am new to ASP.NET MVC 2 (actually I just started working today) and I created the following routes to try to achieve the above.

public static void RegisterRoutes(RouteCollection routes) { routes.IgnoreRoute("{resource}.axd/{*pathInfo}"); routes.IgnoreRoute("content/{*pathInfo}"); routes.IgnoreRoute("images/{*pathInfo}"); routes.MapRoute("About", "about", new { controller = "Common", action = "About" } ); // User profile sits at root level so check for this before displaying the homepage routes.MapRoute("UserProfile", "{url}", new { controller = "User", action = "Profile", url = "" } ); routes.MapRoute("Home", "", new { controller = "Home", action = "Index", id = "" } ); } 

For the most part, this works great, however my homepage does not start! Essentially, when you use the mydomain.com browser, it seems to start a user profile route with an empty {url} parameter, so the home page will never be reached! Any ideas on how I can show the homepage?

+4
source share
5 answers

Can you exchange the two lower routes?

+1
source

Know that this question was asked some time ago, but I just wanted to do the same and could not find the answer that completely solved it for me, so I decided that I would add my 2 cents for others, which may also look at that to do the same in the future.

The problem with the proposed solution above (as mentioned in Astrofaes comment) is that you will need to create static routes for each controller in your assembly. So in the end, I ended up using a special route constraint to check if the controller exists in the execution assembly that could handle the request. If there is, then return false to match so that the request is processed by a different route.

 public class NotControllerConstraint : IRouteConstraint { private static readonly IEnumerable<Type> Controllers = Assembly.GetExecutingAssembly().GetTypes().Where(t => t.BaseType == typeof(Controller)); public bool Match(HttpContextBase httpContext, Route route, string parameterName, RouteValueDictionary values, RouteDirection routeDirection) { return Controllers.Where(c => c.Name == values["id"] + "Controller").Count() == 0; } } 

Then the routes can be configured as follows:

  routes.MapRoute("User", "{id}", new { controller = "User", action = "Index" }, new { notController = new NotControllerConstraint() }); routes.MapRoute("Default", "{controller}/{action}/{id}", new { controller = "Home", action = "Index", id = UrlParameter.Optional }); 
+2
source

The reason the routes change is because the {url} route has no blank line restrictions (this is your last route). As a result, it will first correspond to an empty line, since it is higher in the route table.

With this in mind, you can add restrictions or add your specially named routes above in the route table or use the default catch of all routes with which you can start mvc.

If you want to know which routes correspond at any time, you can use the Phil Haack Route Sender .

+1
source

I was looking for an implementation of the same URL style for my MVC 1.0 application.

I have implemented that with the information from this post and blog post by Guy Burshtein.

Thanks for sharing :)

0
source

I have a simlar setup as shown below:

  routes.MapRoute( "Common", "common/{action}/{id}", new { controller = "common", action = "Index", id = "" } ); routes.MapRoute( "Home", "", new { controller = "Home", action = "Index", id = "" } ); routes.MapRoute( "Dynamic", "{id}", new { controller = "dynamic", action = "Index", id = "" } ); 

It allows me to be flexible and have routes.

mysite.com/

mysite.com/common/contact/ mysite.com/common/about/ mysite.com/common/{wildcardasket/

mysite.com/{nothing}

0
source

All Articles