A while back, I showed you my file-based viewstate persistence solution. Thanks to Google search hits and traffic from Scott Hanselman's analysis, it's been one of my more popular entries. With ASP.net's improvements in this area, I felt that it was due for an update. So, here's a quick whack at it. The usual disclaimers apply.
2.0 adds the notion of "control state" to state persistence, which is very cool. It's an opt-in mechanism for things that need to survive postbacks even if ViewState is turned off. In addition, there's some new flexibility with page adapters and such, but we'll ignore that complexity for now and go for a direct port of my old sample, but include the new ControlState mechanism.
public class FileBasedPageStatePersister : HiddenFieldPageStatePersister {
public FileBasedPageStatePersister(Page page) : base(page) {}
public override void Load() {
//let the base class do its thing
base.Load();
//get the control state
object baseControlState = base.ControlState;
if (baseControlState != null) {
//the control state should be our Guid
Guid guid = (Guid)baseControlState;
//read the contents of the file and set the two states
using (TextReader reader = new StreamReader(CreateOfflineViewStateFilePath(guid))) {
Pair pair = this.StateFormatter.Deserialize(reader.ReadToEnd()) as Pair;
base.ViewState = pair.First;
base.ControlState = pair.Second;
}
public override void Save() {
//create a guid for this viewstate
Guid guid = Guid.NewGuid();
//serialize the states into a temp file
using (TextWriter writer = new StreamWriter(CreateOfflineViewStateFilePath(guid))) {
Pair pair = new Pair(base.ViewState, base.ControlState);
writer.Write(this.StateFormatter.Serialize(pair));
//trick the normal system into thinking all it needs to save is the guid
base.ControlState = guid;
base.ViewState = null;
base.Save();
string CreateOfflineViewStateFilePath(Guid guid) {
//TODO: put these files whereever you like
return Path.Combine(Path.GetTempPath(), string.Format("{0}.viewstate", guid));
So, we immediately see that it's much shorter. This is because ASP.net uses a mechanism very similar to my 1.1 solution, so alot of the plumbing is built-in. The only thing you need to do to use it is override the PageStatePersister property on Page and return one of these. Again, we're piggybacking on the "hidden field" persistence mechanism and using that to store our Guid for the request. Not much different, and I'm pretty happy to say that converting to this model from my old is very simple.
Another interesting idea would be to leave the ControlState in the hidden field, and only store the ViewState in the file. it would be a simple change that I'll leave as an exercise to you. Then, you could be very aggresive about purging old or large files without worrying about breaking anything (provided of course that you've made your controls tolerant to such a method).
Remember Me
Page rendered at Tuesday, January 06, 2009 3:08:07 AM (Pacific Standard Time, UTC-08:00)
Disclaimer The opinions expressed herein are my own personal opinions and do not represent my employer's view in anyway.