How do you handle Session variables?

Published Sun, Nov 6 2005 16:12 | William

One of my many pet peeves is working with Session variables that are treated as Strings.  For instance, when I see something like this:

tbFirstName.Text = Session[”FirstName”].ToString();

Why?  Well, because a typical application has zillions of Session variables and using this methodology means that there's no easy way to determine what all the session variables are and you run the risk of misspelling them.  This also means that there's a good chance that you are going to have two or more session variables that store essentially the same information.  I've heard the argument that if you are careful, document your code, blah blah blah that this is an 'ok' methodology, but the question that begs to be asked is “WHY?”  Ok, if you really bend over backward then the above argument is true. But just because it's manageable doesn't means it's a good way to handle things.

Two things come to mind in handling Session variables.  First, get them out of your pages.  Huh?  Well, as i learned from my friend Phil Hunt at TiBA Solutions , you can use an area specific BasePage (which may or may not inherit from a global BasePage), and handle Session variables via properties in the base page.  This has the benefit of centralizing your code, strongly typing session variables, allowing for  null checks, default values etc without having to rewrite the code all over the place and elminating the possibility of spelling mistakes.  Plus, since it gives you intellisense support, you or a newer developer can do a lot better job at finding and guessing what session variables are available.

One other thing I'd recommend though is creating a class that holds the actual strings used in the session variables.  Since these are as static as can be, I'm not using Get/Set accessor (this is probably the only case I wouldn't) b/c it really doesn't matter much. Just to be pure, I'd probably go back and add accessors later but essentially, I recommend as one approach, creating a class to hold your session variables in , then nest another class for each functional area like so:

public class SessionVariables
{
   public SessionVariables()
   {
   }
   public class Authentication
   {
      public static String UserName = "UserName";
      public static String EncryptedPassword = "EncryptedPassword";
   }
   public class SearchValues
   {
      public static String BeginDate = "BeginDate";
      public static String EndDate = "EndDate";
   }
}

Now you can reference session variables like this:

String UserName = Session[SessionVariables.Authentication.UserName].ToString();

This is actually the code I'd stick in the base page accessors so you don't reference it in the pages.  I know, this is hardly groundbreaking stuff, it's old as dirt.  But I still run into quite  a few applications that have Hard coded session/view/querystring variables and well, it's not something that ought to be.

So far, this is one of the most straightforward ways to get the desired results, but I'm not claiming it's the best.  If anyone else has any suggestions that get you to the same place, please let me know.

Filed under:

Comments

# William said on November 6, 2005 6:15 PM:

My approach was a bit different... I created an interface to represent a repository data source, and implemented it against the Session variable. Then I created a class that had the fields for the session variables as strongly typed objects, and it worked through that repository interface.

So now I can access session variables with something like this:
SessionVariables.SomeSessionVariable = "test";
and I can do unit testing against it.

As an added bonus, since I have to add a field to that class everytime I need another session variable, I am constantly reminded of the currently available fields, which helped me quite a few times find places where i would be duplicating behaviour otherwise.

# William said on November 6, 2005 11:49 PM:

Good tips.

You treat your session variable names as constants though - you should probably just declare them as such instead of as statics. They will show up a little different in intellisense that way too.

public static String EndDate = "EndDate";

becomes

public const String EndDate = "EndDate";

Constants are also validated by the compiler - so accessors are irrelevant.

# William said on November 7, 2005 10:24 AM:

I prefer to create a "SessionManager" class that has properties for each value I want to store in session. Then I just stored the instance of that class to session instead of each individual value.

# William said on November 7, 2005 3:20 PM:

Keith - I should have caught that, definitely should have done it with const.

# William said on November 7, 2005 3:21 PM:

Miki - I never really thought about that but I like it. The only thin i don't follow you on is the unit test part, how do you test against that?

# William said on November 7, 2005 7:21 PM:

Well, since I give this SessionVariables class an interface to a data repository class that I created, I can just pass it a mock one and see how it behaves, I don't have to rely on actually having a Session object around.

The data repository class does all the talking with the Session, the SessionVariables class essentially becomes a generic wrapper for the session variables.

# William said on November 20, 2005 1:28 PM:

I'm not sure what to think about this. You actually learned something from Phil?

# William said on November 20, 2005 1:28 PM:

I'm not sure what to think about this. You actually learned something from Phil?

# William said on November 20, 2005 1:30 PM:

I'm not sure what to think about this. You actually learned something from Phil

# William said on November 21, 2005 12:24 PM:

T- on a serious note, what do you think? how are you handlign them? I know you two architected a lot- so what's your preferred way to handle them? Same, different, none of the above?

# William said on November 21, 2005 3:39 PM:

Seriously, I'm doing mine a lot like Miki is doing them. I have an interface that defines my session store. I have a session provider tell my app what object is handling the persistence, then I simply access them in a strongly typed way. This was mainly for portability reasons.

# Frank said on December 19, 2005 6:08 PM:

You could just write a wrapper class:

public class VivensSession
{
private Page thisPage;

public VivensSession(Page page)
{
thisPage = page;
}

public string DemoSessionProp
{

get { return thisPage.Session["DemoSessionProp"].ToString(); }
set { thisPage.Session["DemoSessionProp"] = value; }
}
}



on the page:

VivensSession mysession = new VivensSession(this);
mysession.DemoSessionProp = "bladiebla";

Typesafe and intellisense. Maybe there is a more smooth solution that doesnt need the page in the constructor..

cheers,

frank

Search

This Blog

Tags

Community

Archives

News

My other sites

Cool Stuff

Book Stuff

Security

ORM

Data Access

Funny Stuff

Compact Framework Stuff

Web Casts

My KnowledgeBase Articles

My MVP Profile

Design Patterns

Performance

Debugging

Remoting

My Fellow Authors

My Books

LINQ

Misc

Speech

Syndication

Email Notifications