如何將ViewState持久化
如果你有一個(gè)非??岬捻?yè)面,頁(yè)面上很多東西自動(dòng)地響應(yīng)用戶(hù)操作而展現(xiàn)豐富的變化,你的ViewState是很有可能達(dá)到200K的。
這里是我將ViewState持久化保持在服務(wù)器端的代碼,這樣ViewState不占用網(wǎng)絡(luò)帶寬,因此其存取只是服務(wù)器的磁盤(pán)讀取時(shí)間。并且它很小,可以說(shuō)是磁盤(pán)隨便轉(zhuǎn)一圈就能同時(shí)讀取好多ViewState,因此可以說(shuō)“不占時(shí)間”。為了再“不占磁盤(pán)時(shí)間”,我還使用了緩存。
一下這段代碼可以放在頁(yè)面中,或者頁(yè)面的父類(lèi)中:
ViewState持久化C# code
- protected override object LoadPageStateFromPersistenceMedium()
- {
- var viewStateID = (string)((Pair)base.LoadPageStateFromPersistenceMedium()).Second;
- var stateStr = (string)Cache[viewStateID];
- if (stateStr == null)
- {
- var fn = Path.Combine(this.Request.PhysicalApplicationPath, @"App_Data/ViewState/" + viewStateID);
- stateStr = File.ReadAllText(fn);
- }
- return new ObjectStateFormatter().Deserialize(stateStr);
- }
- protected override void SavePageStateToPersistenceMedium(object state)
- {
- var value = new ObjectStateFormatter().Serialize(state);
- var viewStateID = (DateTime.Now.Ticks + (long)this.GetHashCode()).ToString(); //產(chǎn)生離散的id號(hào)碼
- var fn = Path.Combine(this.Request.PhysicalApplicationPath, @"App_Data/ViewState/" + viewStateID);
- ThreadPool.QueueUserWorkItem(obj => File.WriteAllText(fn, value));
- Cache.Insert(viewStateID, value);
- base.SavePageStateToPersistenceMedium(viewStateID);
- }
不使用Session,因?yàn)樗鼤?huì)“丟失”。ViewState保存在磁盤(pán)上,即使服務(wù)器重新啟動(dòng),也不會(huì)丟失頁(yè)面狀態(tài)。
下面這段可以放在Global.asax中,也可以根本不管:
ViewState持久化C# code
- protected void Application_Start(object sender, EventArgs e)
- {
- var dir = new DirectoryInfo(this.Server.MapPath("~/App_Data/ViewState/"));
- if (!dir.Exists)
- dir.Create();
- else
- {
- var nt = DateTime.Now.AddHours(-1);
- dir.GetFiles().ForEach(f =>
- {
- if (f.CreationTime < nt)
- f.Delete();
- });
- }
- }
這可以確保絕對(duì)穩(wěn)定可靠地工作。以后請(qǐng)放心使用ViewState,把交互式頁(yè)面提高水平才是最重要的,不要糾纏在“ViewState太大”上。實(shí)際上,由于頁(yè)面設(shè)計(jì)不夠酷,交互變化看上去不夠豐富,ViewState實(shí)在是太小太小了。
如果你使用了它有效提高了復(fù)雜交互頁(yè)面的效率,可以說(shuō)一下提高了多少?!如果你覺(jué)得沒(méi)用,也可以說(shuō)一下在什么情況下沒(méi)用。
【編輯推薦】