A placeholder (for example, {category} ) acts like a variable - it can contain any value. The framework should be able to understand what the parameters in the URL mean. You can do this in one of three ways:
- Provide them in a specific order and for a certain number of segments
- Put them in the query string so that you have name / value pairs to determine what they represent.
- Make a series of routes with literal segments to specify names to define parameters
Here is an example of option No. 3. This is slightly related to the use of query string parameters, but it is certainly possible if you provide some kind of identifier for each segment of the route.
IEnumerable Extensions
This adds LINQ support for the ability to get every possible permutation of parameter values.
using System; using System.Collections.Generic; using System.Linq; public static class IEnumerableExtensions {
Extensions RouteCollection
We are expanding the MapRoute extension method by adding the ability to add a set of routes to match all possible permutations of the URL.
using System; using System.Collections.Generic; using System.Web.Mvc; using System.Web.Routing; public static class RouteCollectionExtensions { public static void MapRoute(this RouteCollection routes, string url, object defaults, string[] namespaces, string[] optionalParameters) { MapRoute(routes, url, defaults, null, namespaces, optionalParameters); } public static void MapRoute(this RouteCollection routes, string url, object defaults, object constraints, string[] namespaces, string[] optionalParameters) { if (routes == null) { throw new ArgumentNullException("routes"); } if (url == null) { throw new ArgumentNullException("url"); } AddAllRoutePermutations(routes, url, defaults, constraints, namespaces, optionalParameters); } private static void AddAllRoutePermutations(RouteCollection routes, string url, object defaults, object constraints, string[] namespaces, string[] optionalParameters) {
Using
public class RouteConfig { public static void RegisterRoutes(RouteCollection routes) { routes.IgnoreRoute("{resource}.axd/{*pathInfo}"); routes.MapRoute( url: "Home/CategoryProducts", defaults: new { controller = "Home", action = "CategoryProducts" }, namespaces: null, optionalParameters: new string[] { "category", "manufacturer", "attribute" }); routes.MapRoute( name: "Default", url: "{controller}/{action}/{id}", defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional } ); } }
This adds a complete set of routes to match URL patterns:
Home/CategoryProducts/category/{category}/manufacturer/{manufacturer}/attribute/{attribute} Home/CategoryProducts/category/{category}/attribute/{attribute}/manufacturer/{manufacturer} Home/CategoryProducts/manufacturer/{manufacturer}/category/{category}/attribute/{attribute} Home/CategoryProducts/manufacturer/{manufacturer}/attribute/{attribute}/category/{category} Home/CategoryProducts/attribute/{attribute}/category/{category}/manufacturer/{manufacturer} Home/CategoryProducts/attribute/{attribute}/manufacturer/{manufacturer}/category/{category} Home/CategoryProducts/category/{category}/manufacturer/{manufacturer} Home/CategoryProducts/manufacturer/{manufacturer}/category/{category} Home/CategoryProducts/category/{category}/attribute/{attribute} Home/CategoryProducts/attribute/{attribute}/category/{category} Home/CategoryProducts/manufacturer/{manufacturer}/attribute/{attribute} Home/CategoryProducts/attribute/{attribute}/manufacturer/{manufacturer} Home/CategoryProducts/category/{category} Home/CategoryProducts/manufacturer/{manufacturer} Home/CategoryProducts/attribute/{attribute}
Now when you use the following url:
Home/CategoryProducts/category/c_50_ShowcasesDisplays
The CategoryProducts action on the HomeController will be called. The parameter value for your category will be c_50_ShowcasesDisplays .
It will also build the appropriate URL when using ActionLink , RouteLink , Url.Action or UrlHelper .
@Html.ActionLink("ShowcasesDisplays", "CategoryProducts", "Home", new { category = "c_50_ShowcasesDisplays" }, null)