Filter your matches with routing constraints

You may have noticed how easy it is to set up a new route. It took us no time at all to create several rules to match various features for our product catalog in the previous recipe. The thing that you have probably noticed though is that our routes are fairly unprotected from any user input. While it is true that we can control our data entry with the parameter types in our action signatures, it would be even better if we could do some validation further up the chain.

If you expect a number in a certain format, a date, or an e-mail address, you can supply a regular expression as part of your route definition to ensure that the match occurs only when the data is appropriate. In this way, if no routes are appropriately matched, down to the actual signature of the supplied data, your 404 page or some other page can handle the missing route.

Getting ready

In this recipe, we will take a look at how to create a phone directory. We want the ability to have phone numbers as part of our route so that Google can find the information and so that our URLs are clean. But if we are going to have phone numbers as data, which is possibly entered by the users, we want to make sure that the data is appropriately formatted.

How to do it...

  1. Start by creating a new MVC application.
  2. Then open up HomeController.cs. We will add two new actions—one to handle appropriate phone number input and the other to handle everything else.

    Controllers/HomeController.cs:

    public ActionResult GetPhoneDetails(string phoneNumber)
    {
    ViewData["phoneNumber"] = phoneNumber;
    return View();
    }
    public ActionResult InputNotSupported(string phoneNumber)
    {
    ViewData["phoneNumber"] = phoneNumber;
    return View();
    }
    
  3. Next, we need to open up the Global.asax to add our new routes. We will have one route to capture all appropriate phone number entries. This route will use a regex pattern to determine if the phone number is appropriate or not. It will allow (123)123-4567 and 123-123-4567 as valid forms of phone numbers. The other route will be a pass through to capture any input that didn't match our filter.

    Global.asax:

    routes.MapRoute("PhoneLookup", //capture appropriate matches "Directory/{phoneNumber}", new {controller = "Home", action = "GetPhoneDetails"}, new {phoneNumber = @"^(()?([0-9]{3})()|-)?([0-9]{3})(-)? ([0-9]{4}|[0-9]{4})$"});
    routes.MapRoute("PhoneLookupFailed", //capture anything else that matches this signature but not the filter "Directory/{phoneNumber}", new { controller = "Home", action = "InputNotSupported" });
    
  4. You can now run your application. Browse to /Directory/123-456-7890, or /Directory/(123)456-7890, or /Directory/1234567890 and you should see the GetPhoneDetails view. If you browse to /Directory/12345678901 or /Directory/HelloWorld you will see the InputNotSupported view.

How it works...

Routing constraints are built into the routing system. You can supply any regex required to create a specific route for a set pattern of data. This not only gives you control to keep certain data out, but it also gives you control to match different patterns of data and handle those matches with different controllers and actions. In our previous example, you may want to handle the lookup for US phone numbers in one database and European phone numbers by another controller and action. This could be handled by specifying different routes with different constraints.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset