.NET MVC экземпляр контроллера внутри другого контроллера
возможно ли ASP.NET контроллер MVC для создания нового экземпляра другого контроллера и эффективного делегирования резонансной способности к этому?
предположим, например, что у меня есть два контроллера в каталоге / Controllers/:
public class HomeController : Controller
{
public ActionResult Index()
{
var otherController = new OtherController();
return otherController.ShowNumberOfThings(100);
}
}
public class OtherController : Controller
{
public ActionResult ShowNumberOfThings(int index)
{
return View(index);
}
}
...и представление под названием Views/Other / ShowNumberOfThings.aspx:
<%@ Page Language="C#" MasterPageFile="~/Views/Shared/Site.Master" Inherits="ViewPage<int>" %>
Number of things: <%= Model.ToString() %>
когда я нажму url:
Я хочу, чтобы мне представили страница, которая гласит:
"количество вещей: 100"
Я хотел бы иметь возможность сохранять временные данные между перенаправлениями контроллера без принудительного использования объекта сеанса (TempData[""] использует объект сеанса для перекрестных перенаправлений контроллера). Мой реальный случай имеет сложный объект, который нуждается в передаче (а не только int), поэтому использование URL/Cookie не может быть и речи, а состояние сеанса-нет.
в WebForms, по крайней мере, мы могли бы использовать сервер.Передача и поддерживать любое состояние в HttpContext.Коллекция элементов. В MVC единственным вариантом, который я вижу, является вызов метода контроллера, непосредственно передающего требуемые аргументы.
на данный момент у него возникли проблемы с попыткой решить папку представления, поскольку "контекст" все еще работает под HomeController.
Я думаю, куда я иду с этим пытается cludge ASP.NET MVC действует как FrontContoller.
любой идеи?
редактировать
в конце концов нам пришлось сериализовать все в сеанс и использовать это. Жаль, но я слышал, что MVC2 будет поддерживать сериализацию объектов в ViewState.
4 ответов
Я думаю, что было бы предпочтительным использовать.
return RedirectToAction("Controller", "Action")
однако я предполагаю, что вы хотите сохранить url Home/Index. Если вы смотрите на шаблон FrontController, то вы должны исследовать написание пользовательского ControllerFactory, который наследуется от DefaultControllerFactory, а затем переопределить метод CreateController. Вы можете зарегистрировать свою фабрику, используя код ниже.
protected void Application_Start()
{
ControllerBuilder.Current.SetControllerFactory(new MyCustomControllerFactory();
RegisterRoutes(RouteTable.Routes);
}
в Фабрике регулятора вы имеете доступ к RequestContext поэтому вы можете измените RouteData по мере необходимости и делегируйте правильный контроллер.
вы можете, конечно, просто установить пользовательский маршрут для Home / Index, который идет в OtherController.ShowNumberOfThings ()
routes.MapRoute("Home", "Home/Index/{id}",
new {controller = "Other", action = "ShowNumberOfThings", id = 100});
Если вы хотите, чтобы вам было представлено "количество вещей: 100", когда вы нажмете действие индекса, почему бы напрямую не отобразить соответствующее представление:
public class HomeController : Controller
{
public ActionResult Index()
{
return View("~Views/Other/ShowNumberOfThings.aspx", 100);
}
}
другим подходом было бы использование частичных представлений
вместо ~Views/Other/ShowNumberOfThings.aspx
вы можете поместить свой взгляд в ~Views/shared/ShowNumberOfThings.ascx
иметь оба вида ~Views/Other/ShowNumberOfThings.aspx
и ~Views/Home/Index.aspx
выполнить частичный вид
public class HomeController : Controller
{
public ActionResult Index()
{
return View(100);
}
}
public class OtherController : Controller
{
public ActionResult ShowNumberOfThings(int index)
{
return View(index);
}
}
и в обоих представлениях реализовать частичный вид
<% Html.RenderPartial("~Views/shared/ShowNumberOfThings.ascx", ViewData.Model); %>
вы можете изменить int для любого объекта, который будет передан в модель
другая возможность (аналогичная частичным представлениям) - использовать Html.RenderAction
. Это позволяет использовать различные классы моделей представления и отдельные методы контроллера.
<% Html.RenderAction("yourActionName", "yourControllerName", routeValues); %>