0

I already have controllers and views in folders under the project name. I added an Area folder and then an area inside it and called it Home and then moved my controller and index view into it. But when I connect to the index I get an error and it looks like the path where it's looking for the index is the old path, how do I change this to the new path?

Here is what I created

enter image description here

In 'HomeAreaRegistration' I see this under RegstrationArea

public class HomeAreaRegistration : AreaRegistration 
{
    public override string AreaName 
    {
        get 
        {
            return "Home";
        }
    }

    public override void RegisterArea(AreaRegistrationContext context) 
    {
        context.MapRoute(
            "Home_default",
            "Home/{controller}/{action}/{id}",
            new { action = "Index", id = UrlParameter.Optional }
        );
    }
}

But when I run the application in IE, here is what I see in the browser! It looks like it's looking for the index.cshtml in the old path location, not the new path location in the new area 'Home'

enter image description here

It looks like the route engine is looking in the wrong location. So here is what my RouteConfig.cs file looks like.

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

Even when I try 'https://localhost:44301/Home/Index.cshtml' it throws a HTTP 404 error.

chuckd
  • 13,460
  • 29
  • 152
  • 331
  • Add your custom location path, by declaring `ViewLocationFormats` in your view engine search. Or you can keep `HomeController` and use `RedirectToAction` on Index action method to your area. – Tetsuya Yamamoto Oct 19 '16 at 03:47
  • can you show me an example of how you would modify the ViewLocationFormats? I'm not sure what that is? – chuckd Oct 19 '16 at 03:55
  • PS: Can you also show code inside `HomeAreaRegistration.cs` file? I want to clarify the contents carefully before writing example code that includes `ViewLocationFormats` and route configuration steps. – Tetsuya Yamamoto Oct 19 '16 at 04:07
  • I've reposted the code from HomeAreaRegistration – chuckd Oct 19 '16 at 04:30
  • Your folder structure looking out of order. Please see my answer for correct structure and related changes for same. – Jaimin Dave Oct 19 '16 at 05:17

3 Answers3

3

The 404 error shows the main problem itself: default routing and view engine search cannot found default Index.cshtml view file in Views directory on your project (i.e. ProjectName/Views/Index.cshtml pointed by route ~/Views/Home/Index).

First, create a class to include view location search for your custom area like this example:

public class CustomView : RazorViewEngine
{
    public CustomView()
    {
        MasterLocationFormats: new[]
        {
            "~/Areas/Home/Views/{0}.cshtml",
            "~/Areas/Home/Views/{1}/{0}.cshtml"
        }

        ViewLocationFormats: new[]
        {
            "~/Areas/Home/Views/{0}.cshtml",
            "~/Areas/Home/Views/{1}/{0}.cshtml"
        }

        PartialViewLocationFormats = ViewLocationFormats;

        FileExtensions = new[]
        {
            "cshtml"
        };
    }
}

Then, include all areas and your custom view engine into Global.asax:

protected void Application_Start()
{
    // register all area locations
    AreaRegistration.RegisterAllAreas();

    // clear default view engine
    ViewEngines.Engines.Clear();

    // add your custom view engine here
    // the custom view engine should loaded before default view engine (e.g. Razor)
    ViewEngines.Engines.Add(new CustomView());
    ViewEngines.Engines.Add(new RazorViewEngine());
}

If you have RouteConfig class on App_Start directory, make sure RegisterAllAreas has included before default route:

public static void RegisterRoutes(RouteCollection routes)
{
    routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
    AreaRegistration.RegisterAllAreas();
    routes.MapRoute(
        name: "Default",
        url: "{controller}/{action}/{id}",
        defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
    );
}

Additionally, add namespace of the controller name when required or the above solution still doesn't work:

public class HomeAreaRegistration : AreaRegistration 
{
    public override string AreaName 
    {
        get 
        {
            return "Home";
        }
    }

    public override void RegisterArea(AreaRegistrationContext context) 
    {
        context.MapRoute(
            "Home_default",
            "Home/{controller}/{action}/{id}",
            new { action = "Index", id = UrlParameter.Optional },
            namespaces: new[] { "ProjectName.Areas.Home.Controllers" }
        );
    }
}

NB: Create Home directory under Views if you want to follow route convension ~/Areas/Views/Home/Index, and put Index.cshtml file into it.

References:

How to set a Default Route (To an Area) in MVC

How to register areas for routing

Community
  • 1
  • 1
Tetsuya Yamamoto
  • 24,297
  • 8
  • 39
  • 61
0

you have to do below corrections in your solution:

1) Add a Folder Home in Views and place index.cshtml in it. Folder structure for view must be: Home(Area name) > Views > Home (same name as controller) > index.cshtml (as shown in picture)

enter image description here

2)change namespace of your Homecontroller to (Solution name).Areas.Home.Controllers

3)Also you have to refer following route pattern for area:

localhost/AreaName/Controller/Action

which in your case:

https://localhost:44301/Home/Home/Index

Hope this might solve your problem

Jaimin Dave
  • 1,224
  • 10
  • 18
0

your area folder structure look like this

enter image description here

Reister your area in Global.asax

AreaRegistration.RegisterAllAreas();

and try with this url

http://localhost:44301/Home/Home/Index