Кажется, контроллеры не распознаются фабрикой контроллеров
Я хочу создать фабрику контроллеров с Autofac, но у меня есть ошибка экземпляра нулевой ссылки в этой строке: string ctrName = contr.ControllerContext.RouteData.Values["Controller"].ToString()
когда я запускаю свой проект.
Это мое controller factory
:
internal class ControllerFactory : DefaultControllerFactory
{
private readonly Dictionary<string, Func<RequestContext, IController>> _controllerMap;
public ControllerFactory()
{
List<IController> lstControllers = DependencyResolver.Current.GetServices<IController>().ToList();
_controllerMap = new Dictionary<string, Func<RequestContext, IController>>();
foreach (Controller contr in lstControllers)
{
string ctrName = contr.ControllerContext.RouteData.Values["Controller"].ToString(); //iv got null instance error in this line
_controllerMap.Add(ctrName, c => contr);
}
}
public override IController CreateController(RequestContext requestContext, string controllerName)
{
if (_controllerMap.ContainsKey(controllerName))
{
return _controllerMap[controllerName](requestContext);
}
else
throw new KeyNotFoundException(controllerName);
}
}
и это мой appstart:
protected void Application_Start()
{
var builder = new ContainerBuilder();
builder.RegisterControllers(typeof(MvcApplication).Assembly).AsImplementedInterfaces();
builder.Register(s => new ControllerFactory()).As<IControllerFactory>();
var container = builder.Build();
DependencyResolver.SetResolver(new AutofacDependencyResolver(container));
AreaRegistration.RegisterAllAreas();
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);
BundleConfig.RegisterBundles(BundleTable.Bundles);
}
Причина ошибки понятна: ControllerContext
моего элемента foreach - ноль... но почему? У меня есть контроллер в моем решении:
public class HomeController : Controller
{
public ActionResult Index()
{
return View();
}
public ActionResult About()
{
ViewBag.Message = "Your application description page.";
return View();
}
public ActionResult Contact()
{
ViewBag.Message = "Your contact page.";
return View();
}
}
Обновление: я проверял отладчик на foreach.. тип элемента WebApplication1.Controllers.HomeController
означает именно мой домашний контроллер, но контекст контроллера элемента mt равен нулю!!!
1 ответ
Это означает, что самой ранней точкой, в которой вы можете получить доступ к свойству ControllerContext, является переопределение метода Execute или Initialize (но сначала вызывается base.Execute или base.Initialize):
protected override void Execute(RequestContext requestContext)
{
base.Execute(requestContext);
// .ControllerContext is available from this point forward.
}
protected override void Initialize(RequestContext requestContext)
{
base.Initialize(requestContext);
// .ControllerContext is available from this point forward.
}
Последнее (Initialize) является абсолютной самой ранней точкой, в которой вы можете использовать свойство ControllerContext, если только вы не обработали присвоение самостоятельно, что не рекомендуется (поскольку части каркаса будут зависеть от того, назначено ли это свойство в то время).
Источник: Null ControllerContext в моем собственном контроллере, наследуемом от BaseController
Вам придется map
ваш Controllers
в другом месте на основе этой новой информации.