ASP.NET MVC Framework (Part 2): URL Routing

Last month I blogged the first in a series of posts I'm going to write that cover the new ASP.NET MVC Framework we are working on.  The first post in this series built a simple e-commerce product listing/browsing scenario.  It covered the high-level concepts behind MVC, and demonstrated how to create a new ASP.NET MVC project from scratch to implement and test this e-commerce product listing functionality.

In today's blog post I'm going to drill deeper into the routing architecture of the ASP.NET MVC Framework, and discuss some of the cool ways you can use it for more advanced scenarios in your application.

Quick Recap from Part 1

In Part 1 of this series, we created an e-commerce site that exposed three types of URLs:

URL Format Behavior URL Example
/Products/Categories Browse all Product Categories /Products/Categories
/Products/List/Category List Products within a Category /Products/List/Beverages
/Products/Detail/ProductID Show Details about a Specific Product /Products/Detail/34

We handled these URLs by creating a "ProductsController" class like below:

Once the above class was added to our application, the ASP.NET MVC Framework automatically handled routing the incoming URLs to the appropriate action method on our controller to process.

In today's blog post we are going to drill into exactly how this URL mapping happened, as well as explore more advanced routing scenarios we can take advantage of with the ASP.NET MVC Framework.  I'll also demonstrate how you can easily unit test URL routing scenarios. 

What does the ASP.NET MVC URL Routing System do?

The ASP.NET MVC framework includes a flexible URL routing system that enables you to define URL mapping rules within your applications.  The routing system has two main purposes:

  1. Map incoming URLs to the application and route them so that the right Controller and Action method executes to process them
  2. Construct outgoing URLs that can be used to call back to Controllers/Actions (for example: form posts, <a href=""> links, and AJAX calls)

Having the ability to use URL mapping rules to handle both incoming and outgoing URL scenarios adds a lot of flexibility to application code.  It means that if we want to later change the URL structure of our application (for example: rename /Products to /Catalog), we could do so by modifying one set of mapping rules at the application level - and not require changing any code within our Controllers or View templates.

Default ASP.NET MVC URL Routing Rules

By default when you use Visual Studio to create a new project using the "ASP.NET MVC Web Application" template it adds an ASP.NET Application class to the project.  This is implemented within the Global.asax code-behind:

The ASP.NET Application class enables developers to handle application startup/shutdown and global error handling logic. 

The default ASP.NET MVC Project Template automatically adds an Application_Start method to the class and registers two URL Routing rules with it:

The first routing rule above indicates that the ASP.NET MVC framework should by default map URLs to Controllers using a "[controller]/[action]/[id]" format when determining which Controller class to instantiate, and which Action method to invoke (along with which parameters should be passed in). 

This default routing rule is why a URL request for /Products/Detail/3 in our e-commerce browsing sample from Part 1 automatically invokes the Detail method on our ProductsController class and passes in 3 as the id method argument value:

The second routing rule above is added to special-case the root "Default.aspx" URL in our application (which is sometimes passed by web servers in place of "/" when handling requests for the root URL of an application).  This rule ensures that requests for either the root "/Default.aspx" or "/" to our application are handled by the "Index()" action on the "HomeController" class (which is a controller automatically added by Visual Studio when we created a new application using the "ASP.NET MVC Web Application" project template).

Understanding Route Instances

Routing rules are registered by adding Route instances into the System.Web.Mvc.RouteTable's Routes collection.

The Route class defines a number of properties that you can use to configure the mapping rules.  You can set these properties using either "traditional" .NET 2.0 property assignments:

Or by taking advantage of the new object initializer feature in the VS 2008 C# and VB compilers to set the properties more tersely:

 

The "Url" property on the Route class defines the Url matching rule that should be used to evaluate if a route rule applies to a particular incoming request.  It also defines how the URL should be tokenized for parameters.  Replaceable parameters within the URL are defined using a [ParamName] syntax.  As we'll see later, we aren't restricted to a fixed set of "well known" parameter names - you can have any number of arbitrary parameters you want within the URL.  For example, I could use a Url rule of "/Blogs/[Username]/Archive/[Year]/[Month]/[Day]/[Title]" to tokenize incoming URLs to blog posts - and have the MVC framework automatically parse and pass UserName, Year, Month, Day and Title parameters to my Controller's action method.

The "Defaults" property on the Route class defines a dictionary of default values to use in the event that the incoming URL doesn't include one of the parameter values specified.  For example, in the above URL mapping examples we are defining two default URL parameter values - one for "[action]" and one for "[id]".  This means that if a URL for /Products/ is received by the application, the routing system will by default use "Index" as the name of the action on the ProductsController to execute.  Likewise, if /Products/List/ was specified, then a null string value would be used for the "ID" parameter.

The "RouteHandler" property on the Route class defines the IRouteHandler instance that should be used to process the request after the URL is tokenized and the appropriate routing rule to use is determined.  In the above examples we are indicating that we want to use the System.Web.Mvc.MvcRounteHandler class to process the URLs we have configured.  The reason for this extra step is that we want to make sure that the URL routing system can be used for both MVC and non-MVC requests.  Having this IRouteHandler interface means we will be able to cleanly use it for non-MVC requests as well (such as standard WebForms, Astoria REST support, etc).

There is also a "Validation" property on the Route class that we'll look at a little later in this post.  This property allows us to specify pre-conditions that need to be met for a particular routing rule to match.  For example, we could indicate that a routing rule should only apply for a specific HTTP verb (allowing us to easily map REST commands), or we could use a regular expression on arguments to filter whether a routing rule should match.

Note: In the first public MVC preview the Route class isn't extensible (instead it is a data class).  For the next preview release we are looking to make it extensible and enable developers to add scenario specific route classes (for example: a RestRoute sub-class) to cleanly add additional semantics and functionality. 

Route Rules Evaluation

When an incoming URL is received by an ASP.NET MVC Web Application, the MVC framework evaluates the routing rules in the RouteTable.Routes collection to determine the appropriate Controller to handle the request.

The MVC framework chooses the Controller to use by evaluating the RouteTable rules in the order that they have been registered.  The incoming URL is tested against each Route rule to see if it matches - and if a Route rule matches then that rule (and its associated RouteHandler) is the one that is used to process the request (and all subsequent rules are ignored).  This means that you want to typically structure your routing Rules in a "most specific to least specific" order.

Routing Scenario: Custom Search URL

Let's walk through using some custom routing rules in a real world scenario.  We'll do this by implementing search functionality for our e-commerce site.

We'll start by adding a new SearchController class to our project:

We'll then define two Action methods within our SearchController class.  The Index() action method will be used to present a search page that has a TextBox for a user to enter and submit a search term.  The Results() action will be used to handle the form submission from it, perform the search against our database, and then display the results back to the user:

 

Using the default /[controller]/[action]/[id] URL route mapping rule, we could "out of the box" use URLs like below to invoke our SearchController actions:

Scenario URL Action Method
Search Form: /Search/ Index
Search Results: /Search/Results?query=Beverages Results
  /Search/Results?query=ASP.NET Results

Note that the reason the root /Search URL by default maps to the Index() action method is because the /[controller]/[action]/[id] route definition added by default when Visual Studio creates a new project sets "Index" as the default action on Controllers (via the "Defaults" property):

While URLs like /Search/Results?query=Beverages are perfectly functional, we might decide we want slightly "prettier" URLs for our search results.  Specifically we might want to get rid of the "Results" action name from the URL, and pass in the search query as part of the URL instead of using a QueryString argument.  For example:

Scenario URL Action Method
Search Form: /Search/ Index
Search Results: /Search/Beverages Results
  /Search/ASP.NET Results

We could enable these "prettier" search result URLs by adding two custom URL Route mapping rules before the default /[controller]/[action]/[id] rule like below:

With the first two rules we are now explicitly specifying the Controller and Action parameters for /Search/ URLs.  We are indicating that "/Search" should always be handled by the "Index" action on the SearchController.  Any URL with a sub-URL hierarchy (/Search/Foo, /Search/Bar, etc) is now always handled by the "Results" action on the SearchController. 

The second routing rule above indicates that anything beyond the /Search/ prefix should be treated as a parameter called "[query]" that will then be passed as a method parameter to our Results action method on SearchController:

Most likely we will also want to enable paginated search results (where we only show 10 search query results at a time).  We could do this via a querystring argument (for example: /Search/Beverages?page=2) or we could optionally embed the page index number as part of the URL as well (for example: /Search/Beverages/2).  To support this later option all we'd need to-do is add an extra optional parameter to our 2nd routing rule:

Notice above how the new URL rule match is now "Search/[query]/[page]".  We've also configured the default page index to be 1 in cases where it is not included in the URL (this is done via the anonymous type passed as the "Defaults" property value).

We can then update our SearchController.Results action method to take this page parameter as a method argument:

 

And with that we now have "pretty URL" searching for our site (all that remains is to implement the search algorithm - which I will leave as an exercise to the reader <g>).

Validation Pre-Conditions for Routing Rules

As I mentioned earlier in this post, the Route class has a "Validation" property that allows you to add validation pre-condition rules that must be true (in addition to the URL filter) for a route rule to match.  The ASP.NET MVC Framework allows you to use regular expressions to validate each parameter argument in the URL, as well as allows you to evaluate HTTP headers (to route URLs differently based on HTTP verbs). 

Below is a custom validation rule we could enable for URLs like "/Products/Detail/43".  It specifies that the ID argument must be a number (no strings allowed), and that it must be between 1 and 8 characters long:

If we pass in a URL like /Products/Detail/12 to our application, the above routing rule will be valid.  If we pass in /Products/Detail/abc or /Products/Detail/23232323232 it will not match.

Constructing Outgoing URLs from the Routing System

Earlier in this blog post I said that the URL routing system in the ASP.NET MVC Framework was responsible for two things:

  1. Mapping incoming URLs to Controllers/Actions to handle
  2. Helping construct outgoing URLs that can be used to later call back to Controllers/Actions (for example: form posts, <a href=""> links, and AJAX calls)

The URL routing system has a number of helper methods and classes that make it easy to dynamically look up and construct URLs at runtime (you can also lookup URLs by working with the RouteTable's Route's collection directly).

Html.ActionLink

In Part 1 of this blog series I briefly discussed the Html.ActionLink() view helper method.  It can be used within views and allows you to dynamically generate <a href=""> hyperlinks.  What is cool is that it generates these URLs using the URL mapping rules defined in the MVC Routing System.  For example, the two Html.ActionLink calls below:

automatically pick up the special Search results route rule we configured earlier in this post, and the "href" attribute they generate automatically reflect this:

In particular note above how the second call to Html.ActionLink automatically mapped the "page" parameter as part of the URL (and note how the first call omitted the page parameter value - since it knew a default value would be provided on the server side). 

Url.Action

In addition to using Html.ActionLink, ASP.NET MVC also has a Url.Action() view helper method.  This generates raw string URLs - which you can then use however you want.  For example, the code snippet below:

would use the URL routing system to return the below raw URL (not wrapped in a <a href=""> element):

Controller.RedirectToAction

ASP.NET MVC also supports a Controller.RedirectToAction() helper method that you can use within controllers to perform redirects (where the URLs are computed using the URL routing system).

For example when the below code is invoked within a controller:

 

It internally generates a call to Response.Redirect("/Search/Beverages")

DRY

The beauty of all of the above helper methods is that they enable us to avoid having to hard-code in URL paths within our Controller and View Logic.  If at a later point we decide to change the search URL route mapping rule back from "/Search/[query]/[page]" to "/Search/Results/[query]/[page]" or /Search/Results?query=[query]&page=[page]" we can easily do so by editing it in one place (our route registration code).  We don't need to change any code within our views or controllers to pick up the new URL (this maintaining the "DRY principle").

Constructing Outgoing URLs from the Routing System (using Lambda Expressions)

The previous URL helper examples took advantage of the new anonymous type support that VB and C# now support with VS 2008.  In the examples above we are using anonymous types to effectively pass a sequence of name/value pairs to use to help map the URLs (you can think of this as a cleaner way to generate dictionaries).

In addition to passing parameters in a dynamic way using anonymous types, the ASP.NET MVC framework also supports the ability to create action routes using a strongly-typed mechanism that provides compile-time checking and intellisense for the URL helpers.  It does this using Generic types and the new VB and C# support for Lambda Expressions. 

For example, the below anonymous type ActionLink call:

Can also be written as:

In addition to being slightly terser to write, this second option has the benefit of being type-safe, which means that you get compile-time checking of the expression as well as Visual Studio code intellisense (you can also use refactoring tools with it):

Notice above how we can use intellisense to pick the Action method on the SearchController we want to use - and how the parameters are strongly-typed.  The generated URLs are all driven off of the ASP.NET MVC URL Routing system.

You might be wondering - how the heck does this work?  If you remember eight months ago when I blogged about Lambda Expressions, I talked about how Lambda expressions could be compiled both as a code delegate, as well as to an expression tree object which can be used at runtime to analyze the Lambda expression.  With the Html.ActionLink<T> helper method we using this expression tree option and are analyzing the lambda at runtime to look up the action method it invokes as well as the parameters types, names and values that are being specified in the expression.  We can use these with the MVC Url Routing system to return the appropriate URL and associated HTML. 

Important: When using this Lambda Expression approach we never actually execute the Controller action.  For example, the below code does not invoke the "Results" action method on our SearchController:

Instead it just returns this HTML hyperlink:

When this hyperlink is clicked by an end-user it will then send back a http request to the server that will invoke the SearchController's Results action method.

Unit Testing Routes

One of the core design principles of the ASP.NET MVC Framework is enabling great testing support.  Like the rest of the MVC framework, you can easily unit test routes and route matching rules.  The MVC Routing system can be instantiated and run independent of ASP.NET - which means you can load and unit test route patterns within any unit test library (no need to start up a web-server) and using any unit test framework (NUnit, MBUnit, MSTest, etc).

Although you can unit test an ASP.NET MVC Application's global RouteTable mapping collection directly within your unit tests, in general it is usually a bad idea to have unit tests ever change or rely on global state.  A better pattern that you can use is to structure your route registration logic into a RegisterRoutes() helper method like below that works against a RouteCollection that is passed in as an argument (note: we will probably make this the default VS template pattern with the next preview update):

You can then write unit tests that create their own RouteCollection instance and call the Application's RegisterRoutes() helper to register the application's route rules within it.  You can then simulate requests to the application and verify that the correct controller and actions are registered for them - without having to worry about any side-effects:

Summary

Hopefully this post provides some more details about how the ASP.NET MVC Routing architecture works, and how you can use it to customize the structure and layout of the URLs you publish within your ASP.NET MVC applications. 

By default when you create a new ASP.NET MVC Web Application it will pre-define a default /[controller]/[action]/[id] routing rule that you can use (without having to manually configure or enable anything yourself).  This should enable you to build many applications without ever having to register your own custom routing rules.  But hopefully the above post has demonstrated that if you do want to custom structure your own URL formats it isn't hard to-do - and that the MVC framework provides a lot of power and flexibility in doing this.

Hope this helps,

Scott

110 Comments

  • Any idea when this framework will be available for download?

    Cheers

    Harry

  • Thanks Scott.

    Nice Tutorial indeed. Counting days to lay my hands on the first MVC CTP.

    BTW, can you explain in short about the Active Record Type support in our MVC.

    Are we having such type of facility like " Active Record " as found in Ruby on Rails or we are going to have something similar to it for managing databases with ORM support.

    Thanks

  • Excellent post ScottGu! Love your work.

    Question : What is this MockHttpContext in the UnitTest class? I mean, i can guess what it is .. but is it new in .NET 3.5 or the MVC framework?

    -PK, from Melbourne, Australia-

  • Hi Scott,

    This looks very powerful - I'm looking forward to playing with the CTP.

    A couple of questions:

    1) Is it possible to use routes with a file extension if I don't want to enable wildcard script mappings? For example, /Products/List/Beverages.rails or /Products/Detail/34.rails ?
    2) Hypothetically, do you think it would be possible to customise the route creation process so that route data could be gathered from attributes on actions?

    For example:

    public class SearchController : Controller {

    [ControllerAction, Route("Search/[query]")]
    public void Results(string query) {
    ...
    }
    }

    Thanks

    Jeremy

  • All good stuff! Any news on when we can get our hands on the CTP?

  • Hi Scott,

    Great Going!

    Are there any chances of Converting one of the existing Starter kits in a modified MVC way,with all new tools and Controls.

    This will be of great advantage.

    Just my few cents

  • Using lambdas with ActionLink - slick. And a great example of less-obvious uses for expressions.

  • Imagine if you will a CMS where users can configure these urls:

    /Products/Widget.aspx
    /Services/How-may-we-help-you.aspx
    /About-us/Our-team.aspx

    Good for SEO, but it's not in the /[controller]/[action]/[id] format at all. So either I should load them all as individual routes or I should have a 'default' controller that can look them up and invoke the actual controller.

    Will there be a provider for loading routes from XML or a database? Or should a controller be able to do a lookup to find the exact controller?

  • Scott,

    It appears that ASP.NET can register http handlers at runtime now and that there is no need for an extension in a URL. Is this true for ASP.NET 3.5 or just the MVC framework? i.e. is there a way to have URLs with no extensions in a plain old ASP.NET 3.5 application without IIS7?

    Thanks,
    Dave

  • Can't wait to try MVC Scott!

    But i was wondering if you had thought about using Attributes to define routing rules for a given controller. It seems like it would be cleaner because you could keep the 'route' with the handler. So if you excluded the Controller, it's route would vanish also. Not sure it would have as good a testing story however...

    Anyway, gives us a CTP soon!! :)

  • Hi Scott,

    As for the validation rules, you only mentioned that it will match or not match based on the regular expression - how would a developer validate that? Is there an IsValid() method call or would the non-match throw an exception to be handled?

  • Scott,

    Is it possible to use IronRuby as the coding language to target the MVC framework??

  • Scott,

    Thanks for spending all these long hours on creating such great tools...2:44 AM, I don't see how you do it.

    Todd

  • Isn't there going to be a url rewriting module for web forms soon?

  • I am liking this more and more. I can see how the routing configuration code in global.asax.cs could become quite large. In my application, I can see dozens, maybe hundreds of unique routing rules. Is there any way this configuration can be put in a file somewhere? That file would be read on Application start. Seems like that would make deployment of routing changes easier, too.

  • Great article!

    Two quick questions: Is there a version of this available yet? And can I use it with VS2005?

    Thank you!!

  • Great to see the url routing offering all this functionality. I really like the validation and testing and can't wait to give it try. Looks great!

  • Any guess as to when the preview release will be available for download?

  • Could you do something wrt error handling? What would be best practice if the controller encounters an error? Or the view? Or the route doesn't exist (or fails it's validation)?

  • Its all cool, Scott is the prodigy no doubt about it? But I am not seeing any Innovations,we are just tryin 2 accomplish it in a more smart manner, though the basic achievment is the same, app still sits on IIS and people browse it! We need some cut thru Innovation....

  • Can't wait for the next article !!!!
    Please make it soon.

    Just a request
    Why dont you and Nikhil Kothari Synchronize your MVC posts ?

  • Just out of curiosity where in the HttpApplication cycle are the routing rules evaluated and are they exposed in any way to the rest of the HttpApplication cycle? My current security system grants permissions at what would become the controller-action level so if the route determination is made early enough I'd really like to drive my authorization off of it.

  • Hi Scott,

    We are starting a new project here in BBC Worldwide (UK) using MVC. I've managed to partly get the guys excited to use your MVC rather than our own, to be an early adopter.

    If it matters to you, I'm sure an encouraging/support email from you will of great help to get the team excited here.

    Thanks

    Paymon
    Paymon. k hamooshi [ at ] b b c.co.uk

  • Thank you Scott,
    A couple of questions:

    Can this handle the Url's scheme for Constructing Outgoing URLs (https or http) so that we can force a certain protocol with an absolute url in some cases.

    In the case when an application is mapped to multiple domains and aliases, can the route take the domain in consideration.
    For example:
    application.com/ maps to home controller, index action
    application.com/slug1 maps to home controller, index action, slug=slug1
    client1.com/ maps to home controller, index action, slug=slug1

  • @jeffreyabecker I'm not sure that driving authorization from routes is a good idea because there may be more than one route to a specific controller and controller action. It wouldn't be unheard of. It seems to me granting access at the controller and/or action level makes the most sense.

  • This looks really cool!

    I noticed that in Django, you have to repeat yourself kind of often when you have a deep nested hierarchy of pages. Your search & search-results pages seem to be continuing that trend.

    I'm sure I could come up with some hierarchical data structure which can be serialized into Route objects, but is the ASP.NET team planning anything along those lines that would come stock?

  • Scott
    i have been following asp.net MVC from the start...its great !!! waitin for it... well i have a question regarding view!!! how can we still use the asp.net web controls like gridview,listview which are rich controls... or more like can we do microsoft easy way of databinding??? in Asp.net MVC framework.... currently in the view i have seen the old asp way... i did not find any Expression Language(some thing like EL in jsp world) for asp.net which can make it easy.... let me know

  • Is this going to require IIS 7? Or will it work in IIS 6 but you have to map all requests to the ASP.NET engine?

  • This is great stuff ... BUT I'd like to see some definitive answers to the following questions:

    1. What is the difference between MS MVC and Castle's Monorail?

    2. Why would I choose one over the other?

    Others have asked the same question though I've been unable to track down any real substantive answers.

    thanks - wayde

  • I am very excited to start using this. The only thing that smells funny is using the lambda expression to package the information needed to determine the routing rule in the generic Html.ActionLink() method. I understand it provides an easy way to do type checking and also intellisense, but it seems strange to see what looks like a method call on an instantiated object be passed as a parameter package. I personally prefer the non-generic Html.ActionLink() method of passing the information because it's clear what is going on. I understand the cool factor of the generic call, but I just feel it might be too much. Am I alone in this thinking?

  • Excellent Post Scott, love the unit testing example to wrap things up. I can see that the routes table could grow rather large for complex applications. Is there a certain level where you could envision the routes table becoming so large that performance would start to be effected?

    Have you thought about being able to define a regular expression for url matching and using backreferences or named captures as the tokenized url? I think this would allow for much more flexibility while keeping the list of routing rules down to a minimum.

  • Great post (as always),
    Why do we need to programmatically write the routes and not use a configuration based one, seems very trivial ?
    In general I prefer to use as minimum code as possible and based everything on configuration and in such way be extendible and bring fix to productions site in an easier way.
    I must say that i am still worried about having to leave all the knowledge that we ave until now with webforms and start a new technology and still think that we would need some kind of a bridge to close the gap between today solution of webforms and tomorrow solution of MVC.

  • Rad. Can't wait to play around with the bits.

    Thanks Scott,

    Jon

  • Wow, looking very very good.. I was really happy when I saw the lambda expressions as an alternative..

    I was wondering though, could you use lambda expressions in the routing table to define the target method, or would this be damaging to the unit testing and interchangability of the system?

    If it could be done as an alternative it would be nice for the sake of absolete refactoring.. even if it's common to change the method names (given that the actual urls could be changed without the method names needing to change).

  • Scott,

    Thanks for helpful information.

    Can you please write someday about How Data Access will work with MVC framework. I read some somewhere that you are going to support all major Data Access Application Framework in MVC. But what would be the best choice?

    Can you provide us help for Exception Handling in MVC.

    Thanks
    Yash Patel

  • Can you do an example of an non-web applicaton using the exact same controller model ? for instance, maybe a windows forms app or an o/s service ? Looking to centralize all my logic and swap in/out views as necessary.

  • I can't wait for this to be released!

  • This is all fine and good but the ability to do this has been around for ages. This is just an adoption of the MVP pattern endoursed by Fowler. We have been using MVC / MVP in all our .net app's for ages we just code it up - if you look at the Gang Of Four patterns they give an excellent implementation of MVC with out all the behind the scenes nonesence. I just think its kind of funny when people get all worked up over something thats been around for ages when they think it the latest and greatest... I'm not trying to be a party crasher as patterns are a wonderful thing and add great structure to any project - but I'd recommend implmenting yourself so you are not suck into the MS way of doing things.

  • Hallo Scott,
    Thanks for the informative post - you really should encode your images as PNG instead as of JPG - the compression artifacts and jaggies are distracting

  • Great post, Scott! I'm eagerly awaiting the preview.

    I'm assuming that you can route several different URLs to the same controller/action. This would be useful if you updated your URL scheme, but didn't want to break the old URLs. How would the reverse lookup work in this case though? If I had two URLs map to one action, what would Url.Action() return?

  • Couple questions:

    1. As others have mentioned, please implement a parallel web.config-based mechanism. With Forms Authentication you locked us into web.config, now you're locking us into code-based. Please find the (correct) middle ground and let us choose.
    2. Are application-relative paths (~/[controller]) valid? You wouldn't require all sites using MVC to be the root site for the web server, right?

    Thanks,
    Chris

  • Scott,
    Will routes be able to redirects based on Sub-Domains? For example, acme.noname.com with route to /company/[name]

  • Maybe it’s silly question, but how do you resolve this URL:
    /Products/List/Grains/Cereals

    Thanks

    -Albert

  • Brandon Bloom wrote: "I noticed that in Django, you have to repeat yourself kind of often when you have a deep nested hierarchy of pages."

    Brandon -- I'm pretty sure you're looking for Django's "include()" function, which lets you nest URLconfs inside one another to solve that problem. I don't know whether something like this is available for this ASP.NET framework, but it's the kind of thing that's pretty easy to add.

  • you know i'll waiting your next Part of MVC Framework...

  • how to get the number of days by subtracting a date from a date? i m working on a project where i have to give check in date and check out date and after subtraction it will display the number of days. please let me know how to do this? I am new in asp.net with vb.net platform.so kindly help me out. plz give my problem highest priority. your reply is eargly awaited

  • Hi Harry,

    >>>>>> Any idea when this framework will be available for download?

    We are planning to release it the end of this week.

    Thanks,

    Scott

  • Hi Softmind,

    >>>>>>> BTW, can you explain in short about the Active Record Type support in our MVC.

    .NET 3.5 has LINQ to SQL built-in - which is a great ORM. LINQ to Entities will also be built-into .NET 3.5 in the future (it also ships with the MVC setup).

    The MVC framework doesn't require LINQ to SQL or LINQ to Entities as the data model - it also works with NHibernate, LLBLGen, SubSonic, DataSets, DataReaders, and/or any other data model with .NET.

    We will, though, provide out of the box scaffolding support for LINQ to SQL and LINQ to Entities that delivers nice integration with the MVC support.

    Hope this helps,

    Scott

  • Hi PK,

    >>>>>> Question : What is this MockHttpContext in the UnitTest class? I mean, i can guess what it is .. but is it new in .NET 3.5 or the MVC framework?

    The MockHttpContext is an example mock object. It isn't currently built-in with the MVC framework (with the first preview you'd need to create this yourself). I'm hoping that before the MVC framework ships, though, that there are a built-in set of mock objects and test helpers that you can use out of the box (without having to mock them yourself).

    Note that all core contracts and types with the MVC framework are mockable (non-sealed and interfaces). So you can also use any existing Mock framework to test it (RhinoMocks, TypeMock, etc).

    Hope this helps,

    Scott

  • Hi Jeremy,

    >>>>>> 1) Is it possible to use routes with a file extension if I don't want to enable wildcard script mappings? For example, /Products/List/Beverages.rails or /Products/Detail/34.rails ?

    Yes - this is fully supported. We recommend changing your route rule to /[controller].mvc/[action]/[id]. When you install the ASP.NET MVC Framework we automatically register this .mvc extension - although you are free to use any other one you want.

    >>>>>>> Hypothetically, do you think it would be possible to customise the route creation process so that route data could be gathered from attributes on actions?

    We don't currently support this built-in, but hypothetically you could load all the controllers at app-startup and use reflection on them to calculate the route rules. This would enable the scenario you are after.

    Hope this helps,

    Scott

  • Hi Neil,

    >>>>>> All good stuff! Any news on when we can get our hands on the CTP?

    Later this week! :-)

    Thanks,

    Scott

  • Hi Fredrik,

    >>>>>> Are there any chances of Converting one of the existing Starter kits in a modified MVC way,with all new tools and Controls.

    Good question. We are definitely planning on shipping starter samples - I'm not sure if we've looked yet at actually converting an existing app to use it. That is a good idea.

    Thanks,

    Scott

  • Hi Mike,

    >>>>>>>> Imagine if you will a CMS where users can configure these urls:

    >>>>>> /Products/Widget.aspx
    >>>>>> /Services/How-may-we-help-you.aspx
    >>>>>> /About-us/Our-team.aspx

    >>>>>>> Good for SEO, but it's not in the /[controller]/[action]/[id] format at all. So either I should load them all as individual routes or I should have a 'default' controller that can look them up and invoke the actual controller.

    You could do a couple of approaches. One would be to register your specific URL routes first (for example: for login, home, admin pages), and then basically do a * route rule to handle all other URLs. You could map these to a CMS content controller that was then responsible for fetching the appropriate content from the database/filesystem and displaying it.

    We'll have richer support in our next preview for handling * mapping scenairos (including the ability to-do * mapping of sub-URL namespaces). But I think the support for what you are after might even work with the first preview release.

    Hope this helps,

    Scott

  • Hi Deepak,

    >>>>>> Make life easier use URLRewriting @ http://www.urlrewriting.net

    For more on URL rewriting and ASP.NET I also recommend this previous post I've done: http://weblogs.asp.net/scottgu/archive/2007/02/26/tip-trick-url-rewriting-with-asp-net.aspx

    Hope this helps,

    Scott

  • Hi Chris,

    >>>>>> As for the validation rules, you only mentioned that it will match or not match based on the regular expression - how would a developer validate that? Is there an IsValid() method call or would the non-match throw an exception to be handled?

    There isn't currently a custom IsValid method with the first preview release. This is a scenario we are looking to potentially enable with our extensible Route types - where you could sub-class a Route object and potentially have more control for scenarios like this.

    Hope this helps,

    Scott

  • Hi Ahmad,

    >>>>> Is it possible to use IronRuby as the coding language to target the MVC framework??

    Yes - we'll support both IronRuby and IronPython with the ASP.NET MVC Framework.

    Thanks,

    Scott

  • Hi Matthew,

    >>>>>>> I am liking this more and more. I can see how the routing configuration code in global.asax.cs could become quite large. In my application, I can see dozens, maybe hundreds of unique routing rules. Is there any way this configuration can be put in a file somewhere? That file would be read on Application start. Seems like that would make deployment of routing changes easier, too.

    We don't currently have a pre-built file format for reading in mapping rules. But it should be relatively easy to build (you could even use LINQ to XML to read in and construct the rules).

    Hope this helps,

    Scott

  • Hi eponymous,

    >>>>>>> Two quick questions: Is there a version of this available yet? And can I use it with VS2005?

    We'll have the first public preview of it available later this week. It currently requires VS 2008 - since it uses some new features in .NET 3.5.

    Hope this helps,

    Scott

  • Hi Morrijr,

    >>>>>>>> Could you do something wrt error handling? What would be best practice if the controller encounters an error? Or the view? Or the route doesn't exist (or fails it's validation)?

    I'll probably do a blog post on this in the future. There are several ways that you can handle errors. The controller has an OnError method you can override to handle controller-specific errors, and you can use the standard Application_OnError event to handle global errors. Within your controller action you can then handle unhandled view exceptions using a local try/catch.

    Hope this helps,

    Scott

  • Hi JeffreyABecker,

    >>>>>>> Just out of curiosity where in the HttpApplication cycle are the routing rules evaluated and are they exposed in any way to the rest of the HttpApplication cycle? My current security system grants permissions at what would become the controller-action level so if the route determination is made early enough I'd really like to drive my authorization off of it.

    The routing rules are resolved after the OnPostMapRequestRequestHandler event. This means that it will happen *after* your authorization rules evaluate. The good news is that this means you should be able to re-use your existing security system as-is.

    Hope this helps,

    Scott

  • Hi Mike,

    >>>>>> Will there be any way to use an XML document to create the routing rules outside of the Global.asax code?

    Yep - this scenario will be supported.

    Thanks,

    Scott

  • Hi J Philip,

    >>>>>>>> Can this handle the Url's scheme for Constructing Outgoing URLs (https or http) so that we can force a certain protocol with an absolute url in some cases. In the case when an application is mapped to multiple domains and aliases, can the route take the domain in consideration.

    >>>>>>>> For example:

    >>>>>>>> application.com/ maps to home controller, index action

    Being able to route based on the sub-domain is a good question. I don't think this is supported in the first public preview bits - but it is a good idea for the future.

    Thanks,

    Scott

  • Hi Brandon,

    >>>>>>>> I noticed that in Django, you have to repeat yourself kind of often when you have a deep nested hierarchy of pages. Your search & search-results pages seem to be continuing that trend. I'm sure I could come up with some hierarchical data structure which can be serialized into Route objects, but is the ASP.NET team planning anything along those lines that would come stock?

    With our first preview the Route type is not extensible (you can't subclass it) - which means you sometimes need to register multiple routes for a series of things. For the next preview we are looking at enabling Route to be sub-classed - in which case you could easily encapsulate muliple URL mappings into a single registration.

    Hope this helps,

    Scott

  • Hi Tony,

    >>>>>> i have been following asp.net MVC from the start...its great !!! waitin for it... well i have a question regarding view!!! how can we still use the asp.net web controls like gridview,listview which are rich controls... or more like can we do microsoft easy way of databinding??? in Asp.net MVC framework.... currently in the view i have seen the old asp way... i did not find any Expression Language(some thing like EL in jsp world) for asp.net which can make it easy.... let me know

    Yes - you'll definitely be able to use declarative controls like listview within MVC views. You are not forced to only use a syntax.

    Hope this helps,

    Scott

  • Hi Luke,

    >>>>>>> Is this going to require IIS 7? Or will it work in IIS 6 but you have to map all requests to the ASP.NET engine?

    The MVC framework will work on both IIS6 and IIS7. You'll be able to get extension-less URLs out of the box with IIS7. For IIS6 you'd need to also register an ISAPI filter to have them be extension-less.

    We'll also support the ability to use file extensions with the MVC framework - so if you want to avoid using an ISAPI filter with IIS6 you can easily use this approach.

    Hope this helps,

    Scott

  • Hi Brig,

    >>>>>> I am very excited to start using this. The only thing that smells funny is using the lambda expression to package the information needed to determine the routing rule in the generic Html.ActionLink() method. I understand it provides an easy way to do type checking and also intellisense, but it seems strange to see what looks like a method call on an instantiated object be passed as a parameter package. I personally prefer the non-generic Html.ActionLink() method of passing the information because it's clear what is going on. I understand the cool factor of the generic call, but I just feel it might be too much. Am I alone in this thinking?

    Some people really prefer the parameter package, and others really prefer the lambda support. The good news is that we will support both. :-)

    Thanks,

    Scott

  • Hi Jesse,

    >>>>>>>>> Excellent Post Scott, love the unit testing example to wrap things up. I can see that the routes table could grow rather large for complex applications. Is there a certain level where you could envision the routes table becoming so large that performance would start to be effected?

    In general I'd recommend where possible to try and structure your URLs so that they map cleanly to a handful of rules (>>>>>> Have you thought about being able to define a regular expression for url matching and using backreferences or named captures as the tokenized url? I think this would allow for much more flexibility while keeping the list of routing rules down to a minimum.

    Yes - this is something we are looking at. The challange with regular expressions is that only a subset of people really understand them (and importantly - understand how to optimize them). But I agree that having this as an option would be super flexible.

    Thanks,

    Scott

  • Hi Ran,

    >>>>>>> Why do we need to programmatically write the routes and not use a configuration based one, seems very trivial ?

    In general having the ability to programmatically create routes provides the most flexibility. You can always create a file mapping that is programmatically read and added to a route table - whereas the inverse is now always possible. :-)

    >>>>>>> In general I prefer to use as minimum code as possible and based everything on configuration and in such way be extendible and bring fix to productions site in an easier way.

    You will definitely be able to store the route mappings in a configuration file/database and dynamically load them. So this will be an option you can use.

    >>>>>>> I must say that i am still worried about having to leave all the knowledge that we ave until now with webforms and start a new technology and still think that we would need some kind of a bridge to close the gap between today solution of webforms and tomorrow solution of MVC.

    Although the way you structure application flow will be different, I think you'll be pleasantly surprised by the amount of knowledge overlap that exists. Authentication, Authorization, Caching, Configuration, Compilation, Session State, Profile Management, Health Monitoring, Administration, Deployment, and many, many other things are exactly the same. MVC views are also .aspx pages (that use .ascx user controls and .master files). So the concept re-use is quite heavy there as well.

    Hope this helps,

    Scott

  • Hi Stephen,

    >>>>>>> I was wondering though, could you use lambda expressions in the routing table to define the target method, or would this be damaging to the unit testing and interchangability of the system?

    We'll need to look at this closer. I think the problem with using Lambdas with the route registration is that it is harder to indicate default and optional parameters that way. But we should definitely look harder to see if there is a clean way to-do it. :-)

    Thanks,

    Scott

  • Hi Yash,

    >>>>>>>> Can you please write someday about How Data Access will work with MVC framework. I read some somewhere that you are going to support all major Data Access Application Framework in MVC. But what would be the best choice? Can you provide us help for Exception Handling in MVC.

    I will try and cover both data access and exception handling more in the future.

    Thanks,

    Scott

  • Hi Lance,

    >>>>>> I'm assuming that you can route several different URLs to the same controller/action. This would be useful if you updated your URL scheme, but didn't want to break the old URLs. How would the reverse lookup work in this case though? If I had two URLs map to one action, what would Url.Action() return?

    Yep - you can definitely map multiple URLs to the same controller/action.

    When you use Url.Action in that scenario it will default to the first rule in the routing list. We will also in the next preview build have support for "named routes" - which would allow you to generate the URL based not on the first-match, but rather on a name you provide. This would allow you to precisely specify which to use.

    Hope this helps,

    Scott

  • Hi Albert,

    >>>>>> Maybe it’s silly question, but how do you resolve this URL: /Products/List/Grains/Cereals

    Today you could reigster a rule like /Products/List/[category]/[subcategory]

    Grains would then be the category, and Cereals the subcategory. You could make the subcategory optional - so that people could visit both:

    /Products/List/Grains/

    and

    /Products/List/Grains/Cereals

    Hope this helps,

    Scott

  • Hi SliderHouseRules,

    >>>>>>> Are application-relative paths (~/[controller]) valid? You wouldn't require all sites using MVC to be the root site for the web server, right?

    The routing rules resolve against the application root URL. So if the app root is "/" they are site rooted, and if the application root is "/application/" then they are resolved under that. No need to specify ~, that is implied.

    Hope this helps,

    Scott

  • Hi Derrick,

    >>>>>>> Will routes be able to redirects based on Sub-Domains? For example, acme.noname.com with route to /company/[name]

    Sub-domain based routing rules is a good scenario - I don't think that is currently supported, but I agree it definitely should be.

    Thanks,

    Scott

  • amazing, just amazing. I'm quite amazed you take the time to write all these replies - way beyond the call of duty. Thanks for all your hard work Scott! Looking forward to the end of the week!

  • hi scott,

    probably not exactly the right place to mention this but a printable view of your blog would be great ( without comments, etc )

  • Thanks for answering!

    Are you considering a provider model for reading route info from XML? That way it can be easily extended to read route info from a database.

    I also would like to have subdomain info avaliable in routing, we often do this:

    en.example.com/Default.aspx
    fr.example.com/Default.aspx

    Which is actually the English and French version of the same page.

  • Would you guys release source code of MVC too ?

  • >>>>>>> Is this going to require IIS 7? Or will it work in IIS 6 but you have to map all requests to the ASP.NET engine?

    The MVC framework will work on both IIS6 and IIS7. You'll be able to get extension-less URLs out of the box with IIS7. For IIS6 you'd need to also register an ISAPI filter to have them be extension-less.

    We'll also support the ability to use file extensions with the MVC framework - so if you want to avoid using an ISAPI filter with IIS6 you can easily use this approach.

    Hope this helps,

    Scott
    --------------------------------
    Dear Scott,

    Does your above statemnt mean, we cannot use IIS 5.1 that comes with windows XP.

    We are are still using Windows XP2 with VWD 2008 Express, will this support this or the internal Server that comes with Express Edition is enough.

    pl. focus more on this.

  • Hi Scott,

    You mention the routing engine being an open design that anybody can hook into using an IRouteHandler derived type. A couple of questions w.r.t. that:

    1) Does Astoria use the Routing Engine to support there framework for writing RESTfull applications?
    2) How does IRouteHandler compare to IHttpHandler?
    3) How does MVC (and the routing engine as a front-end to the application/user provided controller/action entry points) fit in with the classic ASP.NET HTTP processing model (aka Http Pipeline)?

    I guess I need a picture of the HTTP processing infrastructure performed of an MVC based asp.net 3.5 application:-)

    It would also be interesting to hear about other MS projects considering using the routing engine.

    Cheers
    Morten

  • Hi Scott,
    will you be able to define dedicated controllers for User Controls? Or are they more like a partial view? I heard that Components are somewhat deprecated in Rails.

    Florian
    n


  • Seriously!! When will we get a beta of anything working? I really need it :D

  • Is it actually REST with IIS7.0?
    And is there any relation/similarity with REST supported by WCF in .NET Framework 3.5.

  • Scott,
    The validation is a nice addition but I wish it allowed availability to other areas of the context and request. For example I would like to inspect a form field [_method] to use as an alternate of the actual http method for restful routing in instances where a normal http post has taken place but the intent was a put or delete.

  • Hi Scott,

    For what I've seen so far, great work on the MVC Framework. Can you say anything about a release schedule of the MVC Framework in 2008. E.g. the Atlas/Ajax framework took almost a year to get “out of” CTP. Can we expect this for the MVC Framework as well? Or will the roadmap be shorter?

    Grtz Pierre

  • Another fantastic post, Scott! You are the new MSDN. :)

    I would very much encourage you to provide a new ConfigurationSection for the RoutingTable... It's totally configuration fodder!!!

    Keep up the amazing work!

  • I'll second Darrell's query about using square brackets for placeholders in the URL - although I wouldn't necessarily expect the ASP.NET team to follow an example set by a third party, I'm actually surprised to see you're not using the System.UriTemplate library from WCF 3.5's System.ServiceModel.Web assembly - it seems to do exactly the same thing as this MVC templating code, but uses curly braces for its placeholders, which makes it pretty clear to me that you aren't using the existing code that was just released.

    It would be kind of helpful to be able to configure WCF's RESTful JSON endpoints and ASP.NET's MVC controllers using the same syntax... both are likely to turn up in the same applications, after all. A little co-operation might have been in order, there, surely?

  • Scott,
    Thanks for the response and i really looking forward for the CTP
    from your response
    "Yes - you'll definitely be able to use declarative controls like listview within MVC views. You are not forced to only use a syntax".

    My Question?
    1.Can we use Master pages,Ajax Toolkit controls normally???
    2.Does view have a code behind,How and where do we bind the data to Listview/Gridview??



    Hope this helps,

    Scott

  • Can you shed some light on how editable forms would work in the MVC world? If I have a form with 50+ fields on it that is being filled in by the user how is that data going to be validated and passed to the controller? Thanks (Great posts by the way!)

  • Hey Scott,
    I didn't seem it mentioned, and rather than just assume, I thought I'd better ask... will the Html.ActionLink, Url.Action, and RedirectToAction methods have support for generating fully qualified Urls? Even with the framework making the assumption that everything is relative to the Application Root, it will sometimes be necessary to generate fully qualified Urls (for spitting out things like RSS, AJAX request paths, etc...).

    Thanks for all the great work, and be sure to give Phil a hard time. :)

    -Steve

  • Scott, you mentioned the CTP would currently require VS2008 - are there any plans to either 1) make the CTP work with VS2005, or 2) provide a free (or not horrendously expensive like VS2008) VS2008 express alternative that works with the MVC CTP?

  • Hi Scott
    In our shiop we are experiencing really poor performance with regards to vss when running studio over a vpn. I wonder if you have come across this issue, and if you have any ideas. I wonder also if 2008 vs has any changes in it to address this problem.
    Thanks!

  • I cannot wait any longer for the MVC framework. *turns into an MVC zombie*

  • I would like to know is somewhere we can download the sample codes from?

  • Hi Scott,
    Great article. Do you have plan for a SilverlightViewEngine?

    Thanks.



  • >>>>>>>>>>>> Any idea when this framework will be available for download?

    >>>>>>We are planning to release it the end of this week.

    can we get the source code of the framework ?

  • Thanks Scott. Can we implement the url routing logic in an http module?

  • That'll get me switch from any PHP MVC framework in no time ! awesome. Can't wait for the release. Now, if you could convince my boss to give up on .NET 1.1 that'd be equally awesome ;-)

  • Hey Scott,

    Great article as always. I have a quick question.

    I was wondering how you would handle a search term that contained a "/" in it.

    For example, what if someone searched for "fruits/vegetables"? This would point them to the URL "/Search/fruits/vegetables", which wouldn't be handled correctly by the route table. Is there a way to configure the route table in such a way that it routes this to the correct controller and view while keeping the id intact?

  • Hi Darrel,

    >>>>>>> Can I ask why you chose to use square brackets [] in the URL template instead of curly braces {} as used in Joe Gregorio' s URI Template [1]. It seems like an arbitrary choice but it would be nice if we could avoid inconsistencies like this. It is especially confusing considering Astoria actually uses the square brackets in the resolved URL.

    The next CTP is switching to use { } brackets instead of square ones. Just saw the bug fix go in tonight. :-)

    Thanks,

    Scott

  • Hi Eric,

    >>>>>>> was wondering how you would handle a search term that contained a "/" in it. For example, what if someone searched for "fruits/vegetables"? This would point them to the URL "/Search/fruits/vegetables", which wouldn't be handled correctly by the route table. Is there a way to configure the route table in such a way that it routes this to the correct controller and view while keeping the id intact?

    That is actually a very good question - and one that I realized after I posted this article is something to consider. For cases where users are able to submit arbitrary queries, you might not want the actual search path to be part of the URL - since unless you encode it using JavaScript on the client they could always in theory escape out your values. Having the category name be part of the URL is probably a better scenairo - since you have control over that.

    Hope this helps,

    Scott

  • Hey Scott,

    In reference to your answer to my previous question (many thanks for getting back to me), I have an additional part to ask on it. I think Albert touched upon this part in a previous question you answered, but you may have missed his intention due to the lack of a full explanation of the issue.

    In the northwind database, there are a few categories which contain the "/". For example, "Grains/Cereals" and "Meat/Poultry" are actual categories, but with the routing tables, how would you handle these for use as an id in the URL ("Product/List/Grains/Cereals" should bring a list back for the "Grains/Cereals" category).

    Thanks again,
    -Eric

  • Hi Scott,

    I'm having the same problem als Albert and Eric. My routing rule uses the [controller]/[action]/[category] pattern. However, the "Grains/Cereals" category causes the url to look like Product/List/Grains/Cereals. Is there a way to let the routing mechanism know that "Grains/Cereals" is on and the same category?

    Thanks, Inge


  • It's so great! But there is also two problems we may have to face :
    1. When I use IIS6 , I must "Change Url= to Url='[controller].mvc/[action]/[id]'" to make it working without VS2008 . AS we know, ".mvc" is really not a good ending for Search engine robots .That's why we take ".html" instead of ".aspx/.asp/.php" etc. .Search engine robots always take precedence of ".html" , then ".aspx/.asp/.php" etc. So what about ".mvc" ?
    2. Also there is an other problem . When we updated the IIS6 to IIS7 (i.e. we change the WindowsXP/2003 to Windows2008/Vista) , we must modify all of the links with ".mvc" to make it omit like "[controller]/[action]/[id]" format. Any other better ways?

    Of course , we have ways to meet these problems one by one , but if we can use just "[controller]/[action]/[id]" type in IIS6, it may be an all-round scenario . Can we ? And HOW can we do ?

    Thanks , James Su

  • Hi Scott,
    Great! Just a quick question.
    What about the localization of URL routing? Should I manully write each possible URL combination for each language? Or use in a tricky way the global resources?

    Thanks

    Nicola Zeni

  • Out of curiosity, will the routing engine be able to handle subdomain routing? For example, www.domain.com, cars.domain.com, or boats.domain.com routing to specified controllers?

  • Great Stuff.
    Its good to see MS finally adopting the MVC pattern. I enjoyed your MVC Video, albeit I did not understand much of the details. During the video I downloaded, and insatlled the ASP extensions and the MVC toolkit. Before you had finished, I managhed to get my Controller and Views up and running. So quite impressive. However I note your scepticism with reagrds to scaffolds. But it was the 10 minute Rails Video Demo to get a Blog up and running, with Ative Records and scaffolds, that has gor me hooked on RAILS.

    I am currently stuck on SQL Server, not installing Northwind Database, and not undestanding the LINQ ORM model. - This Database side is still all too complicated compared to RAILS.- I am really missing the quick and fast and effective means that ActiveRecord support provides to map to MySQL database Tables. Most of us are not so bright as your MVC video audience, and we are looking to less code, with simple ORM framework. If you can do a demo of a Blog up and running in 10 minutes (aka RAILS) then that would be pretty convincing.

    I am looking forward to Silverlight 2.0 + ASP.MVC ( or RAILS) Hopefully you will have got some Frameworks, and Active Record support to simple Databases like MySQL. Then you will have a winning combination.

    Cheers for all the great work you are doing.
    Jules

  • I've been following your columns on this subject of ASP.Net MVC and I have to admit I am very excited about this new approach, however I am curious about the approach, i.e. using controller classes to declare the "actions" and dictate the "views".

    In my career I've had the distinction of having worked with both .Net and Java (and I am happy to report I am back to .Net). During my exposure to Java technologies I came across an MVC technology called Java Server Faces and had a chance to build a web application with this framework.

    So I suppose what I am asking is, what are some of the advantages to implementing a set of controller classes versus using a simple config file or set of config files?

    Thanks,
    Paul
    The MVC approach with JSF involves placing all of your "actions and views" (among other things) in a config file called faces.config and this served as the "controller" for your applications.


  • I have a route rule that's specific to the Detail action on a Client controller (code to follow). On a view I have a list of clients, each with an ActionLink to the Client/Detail/[name]. The problem is the names can have spaces. I clicked on my first "View" link and it worked (despite having spaces in it). However none of the other links work (even though they also have spaces). I'm confused. Below is my currnet setup:

    Custom Route
    ------------------
    // custom easy-to-read route for the Detail view of the client
    RouteTable.Routes.Add(new Route
    {
    Url = "Client.mvc/Detail/[name]",
    Defaults = new { controller="Client", action = "Detail", name = (string)null },
    RouteHandler = typeof(MvcRouteHandler)
    });

    In the View
    -----------------










    The Rendered View
    ----------------------


    View


    RetailiQ - Development





    View


    RetailiQ - Development 3.4





    View


    RetailiQ - Development 3.5



    The problem
    ----------------
    The first link works no prob in both IE and FF, the other two links, however, fail with a big ugly .NET 404. I don't understand how one of them could work no prob and the others would fail.

    Thoughts?

  • Hello Scott,
    Amazing technology and brillant article.
    Could you add a couple of comments on support for SiteMapProvider in MVC?
    I mean that it would be quite appropriate if MVC framework allowed a way to represent the navigation structure in form of some SiteMapProvider derivative, so in case we change the routing rules "We don't need to change any code within our views or controllers or site map to pick up the new URL" ;)

Comments have been disabled for this content.