Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

"routes.LowercaseUrls = true;" does not work?

I'm having trouble in setting my routes to lowercase by default. For some reason it does not work. I know I can set authorize and home to lowercase myself, but the Admin part (area) will still be capitalized..

@Html.ActionLink("Hello World", "Authorize", "Home")
outputs to
<a href="/Admin/Home/Authorize">Hello World</a>

Area route

public override void RegisterArea(AreaRegistrationContext context)
        {
            context.Routes.LowercaseUrls = true;
            context.MapRoute(
                "Admin_default",
                "Admin/{controller}/{action}/{id}",
                new { controller = "Home", action = "Index", id = UrlParameter.Optional },
                new string[] { "OR.Areas.Admin.Controllers" }
            );
            context.Routes.LowercaseUrls = true;
        }

Default route

public static void RegisterRoutes(RouteCollection routes)
        {
            routes.LowercaseUrls = true;
            routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
            routes.LowercaseUrls = true;
            routes.MapRoute(
                name: "Localization",
                url: "{lang}/{controller}/{action}/{id}",
                defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional },
                namespaces: new string[] { "OR.Controllers" }
            );
            routes.LowercaseUrls = true;
            routes.MapRoute(
                name: "Default",
                url: "{controller}/{action}/{id}",
                defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional },
                namespaces: new string[] { "OR.Controllers" }
            );

            routes.LowercaseUrls = true;
        }

Admin Area configs I tried

// admin/Home/Authorize
public override void RegisterArea(AreaRegistrationContext context)
{
    context.Routes.LowercaseUrls = true;
    context.MapRoute(
        "Admin_default",
        "{area}/{controller}/{action}/{id}",
        new { area = "admin", controller = "home", action = "Index", id = UrlParameter.Optional },
        new string[] { "ORMebeles.Areas.Admin.Controllers" }
    );
    context.Routes.LowercaseUrls = true;
}

// admin/Home/Authorize
public override void RegisterArea(AreaRegistrationContext context)
{
    context.Routes.LowercaseUrls = true;
    context.MapRoute(
        "Admin_default",
        "admin/{controller}/{action}/{id}",
        new { controller = "home", action = "Index", id = UrlParameter.Optional },
        new string[] { "ORMebeles.Areas.Admin.Controllers" }
    );
    context.Routes.LowercaseUrls = true;
}

Edit

As it seems this is bug with MVC4 - when you set context.Routes.LowercaseUrls = true; and you have Area/Areas context.Routes.LowercaseUrls = true; won't take any effect, where should we report it or how can we get it fixed?

like image 232
Stan Avatar asked Oct 02 '12 22:10

Stan


2 Answers

This is bug related to MVC4 and will be fixed in MVC5 release. Routes.LowercaseUrls does not affect areas. More info here.

Meanwhile you can use LowercaseRoutesMVC or LowercaseRoutesMVC4 if you need WebApi support.

like image 122
Stan Avatar answered Nov 13 '22 23:11

Stan


UPDATE: IN AN MVC4 application

Create a new blank MVC4 application and add an Area Called Test, with a Test.cshtml View and a TestController.cs controller.

So I figured out something... though I am not sure if it's a reasonable solution. After playing with the route registration routines, having the areas in the project doesn't break the lowercase functionality.

namespace MvcApplication1.Areas.Test
{
public class TestAreaRegistration : AreaRegistration
{
    public override string AreaName
    {
        get
        {
            return "Test";
        }
    }

    public override void RegisterArea(AreaRegistrationContext context)
    {
        //This line breaks the functionality in the area registration.
        context.MapRoute(
            "Test_default", // Route name
            "Test/{controller}/{action}/{id}", // URL with parameters
            new { controller = "Test", action = "Index", id = "" }, // Parameter defaults
            new string[] { "MvcApplication1.Areas.Test.Controllers" } //namespace
            );
    }
}
}

A workaround:

Comment out the lines

        //context.Routes.LowercaseUrls = true;
        //context.MapRoute(
        //    "Test_default", // Route name
        //    "Test/{controller}/{action}/{id}", // URL with parameters
        //    new { controller = "Test", action = "Index", id = "" }, // Parameter defaults
        //    new string[] { "MvcApplication1.Areas.Test.Controllers" } //namespace
        //    );

In RouteConfig.cs

namespace MvcApplication1
{
public class RouteConfig
{
    public static void RegisterRoutes(RouteCollection routes)
    {
        routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
        routes.LowercaseUrls = true;

        routes.MapRoute(
            "Default", 
            "{controller}/{action}/{id}", 
            new { controller = "Home", action = "Index", id = UrlParameter.Optional }
        );

        routes.MapRoute(
            "Test_default", // Route name
            "Test/{controller}/{action}/{id}", // URL with parameters
            new { controller = "Test", action = "Index", id = "" }, // Parameter defaults
            new string[] { "MvcApplication1.Areas.Test.Controllers" } //namespace
            );
    }
}
}

In The Area Controller Action Method

    public ActionResult Index()
    {
        // Key if statement to make sure the area maps correctly
        if (!this.ControllerContext.RouteData.DataTokens.ContainsKey("area"))
        {
            this.ControllerContext.RouteData.DataTokens.Add("area", "Test");
        }
        return View("Test");
    }

Resulting HTML for the links in the main page of the project

 <ul id="menu">
   <li><a href="/">Home</a></li>
   <li><a href="/home/about">About</a></li>
   <li><a href="/home/contact">Contact</a></li>
   <li><a href="/test?area=Test">Test</a></li>
 </ul>

Notice however the query string variables are not lowercased and it is not an seo friendly url. However it does find the view. This is as close as I've been able to come using that flag and having the urls go to lowercase.

like image 26
DRobertE Avatar answered Nov 13 '22 22:11

DRobertE