Доступ к Request.Cookies из конструктора контроллера - PullRequest
4 голосов
/ 17 июня 2009

Я использую свойство UserData FormsAuthenticationTicket для хранения некоторой пользовательской информации. У меня есть HelperClass, который десериализует эти UserData в пользовательский объект для строго типизированного доступа. У меня есть настройки моего контроллера следующим образом

public class SomeController : Controller
{
    private CookieData _cookieData;

    public SomeController()
    {
        _service = new ForderungsStellerService(new ModelStateWrapper(this.ModelState));
        HttpCookie cookie = Request.Cookies[FormsAuthentication.FormsCookieName];
        FormsAuthenticationTicket ticket = FormsAuthentication.Decrypt(cookie.Value);
        _cookieData= GetSessionData.FromCookie(ticket);
    }
}

Проблема, похоже, в том, что запрос равен нулю во время создания контроллера. При доступе к Request.Cookies из ActionMethod этот фрагмент работает.

Я бы хотел, чтобы объект _cookieData был заполнен в конструкторе по СУХИМЫМ причинам.

У кого-нибудь есть подсказка по этой проблеме?

С наилучшими пожеланиями ...

Ответы [ 3 ]

6 голосов
/ 17 июня 2009

Переопределить Controller.Initialize ():

protected override void Initialize(RequestContext requestContext) {
  base.Initialize(requestContext);
  // do further initialization here
}

Свойства, такие как «Запрос» и т. Д., Будут доступны после вызова base.Initialize ().

6 голосов
/ 17 июня 2009

Я бы создал ModelBinder, который понимает CookieData и как получить его из объекта Request. Я боюсь, что код создания модульного теста необходим, чтобы сделать конструктор счастливым. Если вы возьмете его в качестве параметра для контроллера с помощью связывателя модели, вы можете избежать этих накладных расходов на тестирование.

public class SomeController : Controller
{
  // only need to pass in the data object for unit testing.
  // ModelBinder takes care of DRY
  public ActionResult Index(CookieData cookieData)
  {
  }
}

Ответом на то, почему это не работает в конструкторе, является то, что Controller не был инициализирован с ControllerContext в этот момент.

public HttpContextBase HttpContext {
  get {
    return ControllerContext == null 
      ? null 
      : ControllerContext.HttpContext;
  }
}

Если вы действительно хотите сделать это в конструкторе (не), тогда используйте HttpContext.Request вместо оболочки. Но тем самым вы сделаете свой код непроверяемым, а выравнивание снизится на 3 пункта.

0 голосов
/ 17 июня 2009

Хорошо быть СУХИМ, но в случае ASP.NET MVC это чаще всего означает использование настраиваемого атрибута фильтра, или как Talljoe показал Model Binder.

    public override void OnActionExecuting(ActionExecutingContext filterContext)
     {
         HttpCookie cookie = filterContext.HttpContext.Request.Cookies[FormsAuthentication.FormsCookieName];
        FormsAuthenticationTicket ticket = FormsAuthentication.Decrypt(cookie.Value);
        filterContext.ActionParameters["CookieData"] = GetSessionData.FromCookie(ticket);


         base.OnActionExecuting(filterContext);
     }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...