如何区分PostBack是F5刷新还是FormSubmit
在一个页面上有很多 Button
或者可以提交的 Html Dom
对象,如何区分服务器端收到的 PostBack
是用户点击的 FromSubmit
还是 F5 页面刷新。在 http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnvs05/html/BedrockASPNET.asp 这篇文章的 Trap the Browser Refresh
部分讲述了一个办法,用 Page.RegisterHiddenField
注册一个 HiddenField
和 Session
中的Ticket
比较,确定是否是 Refresh
的办法。这个办法用到了 IHttpModule
HttpContext
,在 IHttpModule.Init(HttpApplication context)
时把是否是 Refresh
的属性放在 HttpContext
中,供整个Page
的生命周期 (LifeCycle) 使用。和这个方法的想法,差不多,下面是一个比较简便的实现方法。
用 Session
和 ViewState
的特定 Key 比较检查是否是刷新。每次 OnPreRender
后再次重新发号。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
public partial class F5 : System.Web.UI.Page
{
private static string MaskKey = "____MASKKEY"; //注册全局的MaskKey
protected void Page_Load(object sender, EventArgs e)
{
ShowStatus();//打印状态
}
private void InitialMask()
{
this.Session[MaskKey] = this.ViewState[MaskKey] = Guid.NewGuid().ToString();//重新发号 给Session 和 ViewState 新的Guid Session在服务器端标志 ViewState放在客户端标志
}
protected override void OnPreRender(EventArgs e)
{
base.OnPreRender(e);
InitialMask();//发号
}
public bool IsRefresh
{
get
{
if (this.Session[MaskKey] == null || this.ViewState[MaskKey] == null) return false;
return !this.Session[MaskKey].ToString().Equals(this.ViewState[MaskKey].ToString());//检查Key是否相同
}
}
protected void btnTest_Click(object sender, EventArgs e)
{
this.lblGuid.Text = this.Session[MaskKey].ToString() + " " + this.ViewState[MaskKey].ToString();//打印Key
}
private void ShowStatus()
{
if (this.IsRefresh)
{
this.lblShow.Text = "F5 Refresh";
}
else
{
this.lblShow.Text = "Html Dom submit";
}
}
}
IE 的 F5 Refresh 提交的是IE中最后一次对服务器的请求,也就是上的ViewState
中的东西,由于没有使用Html Dom
来提交,没有提交这次新发的ViewState Key
。这样Session
中的Key
和ViewState
中的Key
(上次的ViewState
)不相同,则认为是 F5 刷新。如果是相同的则说明用了最后Render
的 Session Key
和ViewState Key
所以被认为是Html Dom
的FormSubmit
。 如下图: