Как получить доступ к переменным сеанса из любого класса в ASP.NET? - PullRequest
150 голосов
/ 07 марта 2009

Я создал файл класса в папке App_Code в моем приложении. У меня есть переменная сеанса

Session["loginId"]

Я хочу получить доступ к этим переменным сеанса в моем классе, но когда я пишу следующую строку, это выдает ошибку

Session["loginId"]

Может кто-нибудь сказать мне, как получить доступ к переменным сеанса в классе, который создается в папке app_code в ASP.NET 2.0 (C #)

Ответы [ 7 ]

351 голосов
/ 07 марта 2009

(обновлено для полноты)
Вы можете получить доступ к переменным сеанса с любой страницы или элемента управления, используя Session["loginId"] и из любого класса (например, из библиотеки классов), используя System.Web.HttpContext.Current.Session["loginId"].

Но, пожалуйста, читайте мой оригинальный ответ ...


Я всегда использую класс-оболочку вокруг сеанса ASP.NET, чтобы упростить доступ к переменным сеанса:

public class MySession
{
    // private constructor
    private MySession()
    {
      Property1 = "default value";
    }

    // Gets the current session.
    public static MySession Current
    {
      get
      {
        MySession session =
          (MySession)HttpContext.Current.Session["__MySession__"];
        if (session == null)
        {
          session = new MySession();
          HttpContext.Current.Session["__MySession__"] = session;
        }
        return session;
      }
    }

    // **** add your session properties here, e.g like this:
    public string Property1 { get; set; }
    public DateTime MyDate { get; set; }
    public int LoginId { get; set; }
}

Этот класс хранит один свой экземпляр в сеансе ASP.NET и позволяет вам обращаться к свойствам сеанса безопасным для типов способом из любого класса, например, так:

int loginId = MySession.Current.LoginId;

string property1 = MySession.Current.Property1;
MySession.Current.Property1 = newValue;

DateTime myDate = MySession.Current.MyDate;
MySession.Current.MyDate = DateTime.Now;

Этот подход имеет несколько преимуществ:

  • это спасает вас от большого количества типов
  • вам не нужно использовать жестко закодированные сеансовые ключи во всем приложении (например, Session ["loginId"]
  • вы можете задокументировать элементы сеанса, добавив XML-комментарии к документам о свойствах MySession
  • вы можете инициализировать переменные сеанса значениями по умолчанию (например, если они не равны NULL)
100 голосов
/ 07 марта 2009

Доступ к сеансу через потоки HttpContext: -

HttpContext.Current.Session["loginId"]
22 голосов
/ 10 июня 2010

Проблема с предлагаемым решением заключается в том, что оно может нарушить некоторые функции производительности, встроенные в SessionState, если вы используете внешнее хранилище сеансов. (либо «Режим сервера состояний», либо «Режим сервера SQL»). В режиме oop данные сеанса должны быть сериализованы в конце запроса страницы и десериализованы в начале запроса страницы, что может быть дорогостоящим. Для повышения производительности SessionState пытается десериализовать только то, что необходимо, только десериализовать переменную при первом обращении к нему, и он только повторно сериализует и заменяет переменную, которая была изменена. Если у вас есть много переменных сеанса и они объединены в один класс, то, по сути, все в вашем сеансе будет десериализовано при каждом запросе страницы, который использует сеанс, и все будет необходимо снова сериализовать, даже если изменилось только 1 свойство, так как класс изменился. Просто кое-что, чтобы рассмотреть, если вы используете много сеанса и режим oop.

12 голосов
/ 07 марта 2009

Ответы, представленные ранее, дают правильное решение проблемы, однако я чувствую, что важно понять, почему возникает эта ошибка:

Свойство Session Page возвращает экземпляр типа HttpSessionState относительно этого конкретного запроса. Page.Session фактически эквивалентно звонку Page.Context.Session.

MSDN объясняет, как это возможно:

Поскольку страницы ASP.NET содержат ссылку по умолчанию на пространство имен System.Web (которое содержит класс HttpContext), вы можете ссылаться на элементы HttpContext на странице .aspx без полной ссылки на класс HttpContext.

Однако, когда вы пытаетесь получить доступ к этому свойству внутри класса в App_Code, это свойство будет вам недоступно, если ваш класс не является производным от класса страницы.

Мое решение этого часто встречающегося сценария состоит в том, что Я никогда не передаю объекты страниц классам . Я бы предпочел извлечь нужные объекты со страницы Session и передать их в Class в виде коллекции значений / массивов / списков, в зависимости от случая.

1 голос
/ 13 февраля 2012

У меня была такая же ошибка, потому что я пытался манипулировать переменными сеанса внутри пользовательского класса Session.

Мне нужно было передать текущий контекст (system.web.httpcontext.current) в класс, а затем все работало нормально.

MA

0 голосов
/ 30 января 2019

В ядре asp.net это работает по-разному:

public class SomeOtherClass
{
    private readonly IHttpContextAccessor _httpContextAccessor;
    private ISession _session => _httpContextAccessor.HttpContext.Session;

    public SomeOtherClass(IHttpContextAccessor httpContextAccessor)
    {
        _httpContextAccessor = httpContextAccessor;
    }

    public void TestSet()
    {
        _session.SetString("Test", "Ben Rules!");
    }

    public void TestGet()
    {
        var message = _session.GetString("Test");
    }
}

Источник: https://benjii.me/2016/07/using-sessions-and-httpcontext-in-aspnetcore-and-mvc-core/

0 голосов
/ 20 апреля 2018

Это должно быть более эффективным как для приложения, так и для разработчика.

Добавьте следующий класс в ваш веб-проект:

/// <summary>
/// This holds all of the session variables for the site.
/// </summary>
public class SessionCentralized
{
protected internal static void Save<T>(string sessionName, T value)
{
    HttpContext.Current.Session[sessionName] = value;
}

protected internal static T Get<T>(string sessionName)
{
    return (T)HttpContext.Current.Session[sessionName];
}

public static int? WhatEverSessionVariableYouWantToHold
{
    get
    {
        return Get<int?>(nameof(WhatEverSessionVariableYouWantToHold));
    }
    set
    {
        Save(nameof(WhatEverSessionVariableYouWantToHold), value);
    }
}

}

Вот реализация:

SessionCentralized.WhatEverSessionVariableYouWantToHold = id;
...