2010-04-05 2 views
0

У меня есть уникальный сценарий, где я хочу, чтобы базовый контроллер захватил некоторые данные и сохранил их в списке. Список должен быть доступен из моих представлений так же, как и ViewData. Я буду использовать этот список на каждой странице и хотел бы сделать более чистое решение, чем просто перетащить его в ViewDataDictionary.ASP.NET MVC передает информацию от контроллера для просмотра WITHOUT ViewData, ViewModel или сеанса

После попытки найти решение, я подумал, что создам пользовательскую ViewPage с свойством для хранения моего списка. Мой пользовательский ViewPage наследуется от System.Web.MVC.ViewPage. Однако я не знаю, где MVC передает данные просмотра с контроллера на представление. Что еще более важно, как мне заставить его передать мой список до представления?

Спасибо за помощь.

EDIT ....

Извините за путаницу. Я пытался максимально упростить вопрос, чтобы избежать путаницы. Очевидно, что это не сработало :)

Я реализую свое собственное управление сеансом в проекте .net mvc. Когда приходит запрос, мой базовый контроллер проверяет, был ли отправлен куки-файл сеанса вместе с запросом в методе OnActionExecuting. Если был отправлен куки-файл сеанса, мой контроллер попадает в базу данных и извлекает информацию о сеансе пользователя. Информация о сеансе (userid и т. Д.) Помещается в объект списка и сохраняется в свойстве «Sess».

Я хочу, чтобы иметь возможность доступа к элементам в списке Sess из моих взглядов, как это:

Итак, как и где я могу получить мой контроллер передавать список SESS к моим взглядам?

Я понимаю, что это не так, как обычное управление сеансом, как правило, реализуется в .net. Однако это было бы самым простым и чистым решением для моего проекта.

Спасибо всем, кто помог до сих пор!

+1

Это один из тех сценариев, которые звучат как RenderAction, могут быть лучше подходят для работы. Если есть данные, которые необходимо получить на каждой странице (например, меню), RenderAction делает это намного проще. Это простой способ пройти жизненный цикл, чтобы вы могли делиться частями вашего приложения (меню, объявления, виджеты). – Jab

+0

Я согласен с Jab, идите с RenderAction, если вам нужны динамические данные, которые должны быть вытащил из хранилища данных или отправился с RenderPartial, если вы просто хотите отобразить ASCX (вы также можете предоставить модель для RenderPartial, если хотите) – mare

ответ

0

Почему вы не хотите использовать ViewData? Это просто потому, что вы не хотите иметь строку кода в каждом отдельном действии, которое помещает некоторые данные в ViewDataDictionary?

Вы можете использовать фильтр действий и поместить эти данные прежде, чем каждое действие выполняется, как, например,

public class AddSomeDataToViewDataAttribute : ActionFilterAttribute 
{ 
    public override void OnActionExecuting(ActionExecutingContext filterContext) 
    { 
     //filterContext.Controller.ViewData.Add("SomeConstant")(data); 
    } 
} 

Тогда вы просто поставить этот атрибут в каждом контроллере или в базовом контроллере.

Edit: Вы можете сделать несколько методов расширения, как

public static void Add<T>(this IDictionary<string, object> dictionary, T anObject) 
{ 
    var key = typeof(T).Name; 
    dictionary.Add(key, anObject); 
} 

public static T Get<T>(this IDictionary<string, object> dictionary) 
{ 
    var key = typeof(T).Name; 
    return (T)dictionary[key]; 
} 

Затем вы добавляете данные, как это:

public override void OnActionExecuting(ActionExecutingContext filterContext) 
{ 
    //filterContext.Controller.ViewData.Add<YourListType>(data); 
} 

И в представлении, вы получите данные, как это:

ViewData.Get<YourListType>(); 

С уважением.

+0

Я не хочу, чтобы мне приходилось бросать ViewData ["Session"] в список время в моих взглядах. – josh

+0

Хорошо, я отредактировал свой ответ. – uvita

0

Вопрос не ясен: Чтобы ответить на его часть, вы можете использовать свойство на базе ViewModel. Вам нужно установить это свойство в конструкторе базы ViewModel.Объекты экземпляра должны явно вызывать конструктор базового ViewModel, если любые значения должны передаваться ему для любой работы, выполняемой ... Этот вызов конструктора - это все нормальный C#, поэтому в Интернете есть много примеров.

Я согласен, что если это для меню, RenderAction выглядит намного проще для реализации функциональности. Я попробовал базовый метод ViewModel для меню, а затем переключился на использование RenderAction на контроллере, который специально отвечает за навигацию.

Отсутствие динамических примеров навигации для сайтов ASP.NET MVC удивительно, поскольку это похоже на такое основное требование.

0

Необходимо более подробно описать вашу проблему.

И, ну, кроме фильтра действий или Controller.OnAction Выполнено переопределение, вы можете использовать Html.RenderAction.

2

В общем, я бы рекомендовал, чтобы явное указание того, к каким вашим представлениям разрешен доступ. Поэтому я бы рекомендовал вам поместить эти данные в ViewData из вашего контроллера, а затем вытащить его из ViewData из представления. Это держит линию связи между вашим контроллером и видом в одном месте и просто.

Однако, если вы действительно хотите получить доступ к сеансу из представления, вы можете.

<%: ViewContext.HttpContext.Session["key"] %> 

Одна вещь, которую вы могли бы сделать, это иметь свой собственный пользовательский вид страницы класс, производный от System.Web.Mvc.ViewPage и изменить Inherits заявление в верхней части страницы, чтобы указать на странице просмотра.

<%@ Page ... Inherits="YourNamespace.YourViewPage" %> 

Ваша пользовательская страница просмотра может иметь любые необходимые свойства.