2010-01-09 14 views
6

Disculpe si esta pregunta ya se ha hecho. HttpContext.Current.Session["key"] devuelve un objeto y deberíamos convertirlo a ese particular Type antes de poder usarlo. Estaba buscando en varias implementaciones de sesiones mecanografiadassesiones fuertemente tipadas en asp.net

http://www.codeproject.com/KB/aspnet/typedsessionstate.aspx http://weblogs.asp.net/cstewart/archive/2008/01/09/strongly-typed-session-in-asp-net.aspx http://geekswithblogs.net/dlussier/archive/2007/12/24/117961.aspx

y sentí que era necesario añadir algo más de código (corríjanme si me he equivocado) a la SessionManager si queríamos añadir una nuevo Type de objeto en sesión, ya sea como un método o como un contenedor separado. Pensé que podríamos utilizar los genéricos

public static class SessionManager<T> where T:class 
{ 
    public void SetSession(string key,object objToStore) 
    { 
    HttpContext.Current.Session[key] = objToStore; 
    } 

    public T GetSession(string key) 
    { 
    return HttpContext.Current.Session[key] as T; 
    } 

} 
  • ¿Hay alguna ventaja inherente a usando

    SessionManager<ClassType>.GetSession("sessionString")

de utilizar

HttpContext.Current.Session["sessionString"] as ClassType 
  • También pensaba que sería bueno tener algo como

SessionManager["sessionString"] = objToStoreInSession, pero encontró que una clase estática no puede tener un indexador. ¿Hay alguna otra forma de lograr esto?

  • Mi idea era crear un SessionObject que almacenar el Type y el objeto, a continuación, añadir a este objeto de sesión (utilizando un SessionManager), con la llave. Al recuperar, eche todos los objetos a SessionObject, obtenga el tipo (digamos t) y el Objeto (por ejemplo, obj) y marque obj como t y devuélvalo.

    public class SessionObject { public Type type {get;set;} public Object obj{get;set;}
    }

esto no funciona tan bien (como la firma de retorno sería la misma, pero los tipos de retorno será diferente).

¿Hay alguna otra manera elegante de guardar/recuperar objetos en la sesión de una manera más Tipo de manera segura

Respuesta

4

Para una forma muy limpia, fácil de mantener y hábil de tratar con la sesión, mira esto post. Te sorprenderá lo simple que puede ser.

+0

aunque un buen puesto, que se deriva de su clase a partir de una sesión de clase específica no dejaría que se derivan de su clase a partir de cualquier otra clase abstracta/clase base – ram

+0

@Ram Sí, el punto de la clase en mi publicación es que es un contenedor para los elementos que desea almacenar en sesión. Y como espero que hayas notado, realmente no podría ser más fácil. – TheObjectGuy

+1

¿Realmente funcionará para el estado fuera de proceso? Debido a que el objeto de sesión nunca se escribe en el almacén de sesión, entonces el almacén de sesión aún tendrá los valores anteriores previamente serializados. –

1

En realidad, si estaban buscando para escribir objetos, colocar el tipo en el nivel de método como:

public T GetValue<T>(string sessionKey) 
{ 

} 

El nivel de clase es más si tiene el mismo objeto en sesión, pero la sesión puede expandirse a varios tipos. No sé si me preocuparía controlar la sesión; Simplemente dejaría que haga lo que hace durante un tiempo, y simplemente proporcionaría un medio para extraer y guardar información de una manera más fuertemente tipada (al menos para el consumidor).

Sí, los índices no funcionarían; se podría crear como una instancia en su lugar, y que sea estática por:

public class SessionManager 
{ 
    private static SessionManager _instance = null; 


    public static SessionManager Create() 
    { 
     if (_instance != null) 
      return _instance; 

     //Should use a lock when creating the instance 
     //create object for _instance 

     return _instance; 
    } 

    public object this[string key] { get { .. } } 
} 

Y lo que esta es la implementación de fábrica estática, sino que también mantiene un único punto de contacto a través de una referencia estática a la clase administrador de sesión internamente . Cada método en sessionmanager podría envolver la sesión existente de ASP.NET, o usar su propio almacenamiento interno.

2

Una desventaja de la técnica es que el código de consumo debe ser consciente de qué claves usar para el almacenamiento y la recuperación. Esto puede ser propenso a errores, ya que la clave debe ser exactamente correcta, o corre el riesgo de almacenarla en el lugar incorrecto o de recuperar un valor nulo.

De hecho, utilizo la variante de tipo fuerte, ya que sé lo que necesito tener en la sesión, y así puedo configurar la clase de ajuste que mejor se adapte. Prefiero tener el código adicional en la clase de sesión y no tener que preocuparme por las cadenas clave en ningún otro lado.

+0

Sí, estoy de acuerdo contigo. Veo que configurar SessionManager.Constants para series de sesión como una implementación estándar para evitar errores tipográficos – ram

0

he publicado una solución a la cuestión StackOverflow is it a good idea to create an enum for the key names of session values?

Creo que es muy resbaladiza y contiene muy poco código para que esto ocurra. Necesita .NET 4.5 para ser el más hábil, pero aún es posible con versiones anteriores.

Permite:

int myInt = SessionVars.MyInt; 
SessionVars.MyInt = 3; 

para trabajar exactamente igual:

int myInt = (int)Session["MyInt"]; 
Session["MyInt"] = 3; 
Cuestiones relacionadas