I am working on a pluggable ASP.NET MVC web app that discovers and registers areas at runtime from the Areas directory.
My problem is that the view engine does not find any views from that area.
I have one partial view located at
~/Areas/Catalog/Views/Shared/_SearchBarPartial.cshtml
I set the area using:
htmlHelper.ViewContext.RouteData.DataTokens["area"] = "Catalog";
But when executing
Html.Partial("_SearchBarPartial")
I get the following error:
The partial view '_SearchBarPartial' was not found or no view engine supports the searched locations. The following locations were searched:
~/Areas/Catalog/Views/Home/_SearchBarPartial.aspx ~/Areas/Catalog/Views/Home/_SearchBarPartial.ascx ~/Areas/Catalog/Views/Shared/_SearchBarPartial.aspx ~/Areas/Catalog/Views/Shared/_SearchBarPartial.ascx ~/Views/Home/_SearchBarPartial.aspx ~/Views/Home/_SearchBarPartial.ascx ~/Views/Shared/_SearchBarPartial.aspx ~/Views/Shared/_SearchBarPartial.ascx ~/Areas/Catalog/Views/Home/_SearchBarPartial.cshtml ~/Areas/Catalog/Views/Home/_SearchBarPartial.vbhtml ~/Areas/Catalog/Views/Shared/_SearchBarPartial.cshtml ~/Areas/Catalog/Views/Shared/_SearchBarPartial.vbhtml ~/Views/Home/_SearchBarPartial.cshtml ~/Views/Home/_SearchBarPartial.vbhtml ~/Views/Shared/_SearchBarPartial.cshtml ~/Views/Shared/_SearchBarPartial.vbhtml
My folder structure is:
bin/
Areas/
Catalog/
bin/
CatalogArea.dll
Content/
Scripts/
Views/
Shared/
_SearchBarPartial.cshtml
CatalogArea.cs
Content/
Scrips/
Views/
Global.asax
To register areas i use the following code, executed before application start:
[assembly: WebActivatorEx.PreApplicationStartMethod(typeof(Bootstrapper), "LoadAreas")]
public class Bootstrapper
{
public static string ModuleDirectory
{
get { return Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Areas"); }
}
public static void LoadAreas()
{
var assemblyFiles = Directory.GetFiles(ModuleDirectory, "*.dll", SearchOption.AllDirectories);
assemblyFiles.ForEach(af =>
{
var assembly = Assembly.LoadFile(af);
if(assembly.GetTypes().Any(t => IsArea(t))
{
BuildManager.AddReferencedAssembly(assembly);
}
});
}
private static bool IsArea(Type t)
{
return typeof (AreaRegistration).IsAssignableFrom(t) && !t.IsAbstract;
}
}
Global.asax.cs
public class MvcApplication : System.Web.HttpApplication
{
protected void Application_Start()
{
AreaRegistration.RegisterAllAreas();
// ...
}
}