在 C# 中防止页面刷新
Posted
技术标签:
【中文标题】在 C# 中防止页面刷新【英文标题】:Prevent Page Refresh in C# 【发布时间】:2010-10-17 15:10:17 【问题描述】:Asp.Net Button Event on refresh fires again??? GUID? 的副本
你好,我是一个网站,当用户点击一个按钮和页面回发时,如果用户刷新页面或按 F5,按钮方法会再次被调用。
任何人都知道一些方法来防止页面刷新而无需再次将页面重定向到同一页面?
类似 if (page.isRefresh) 之类的...或者如果存在任何 javascript 解决方案更好。
这看起来可行....但是当我刷新它时它不会回发而是在文本框中显示之前的值
http://www.dotnetspider.com/resources/4040-IsPageRefresh-ASP-NET.aspx
private Boolean IsPageRefresh = false;
protected void Page_Load(object sender, EventArgs e)
if (!IsPostBack)
ViewState["postids"] = System.Guid.NewGuid().ToString();
Session["postid"] = ViewState["postids"].ToString();
TextBox1.Text = "Hi";
else
if (ViewState["postids"].ToString() != Session["postid"].ToString())
IsPageRefresh = true;
Session["postid"] = System.Guid.NewGuid().ToString();
ViewState["postids"] = Session["postid"];
protected void Button1_Click(object sender, EventArgs e)
if (!IsPageRefresh) // check that page is not refreshed by browser.
TextBox2.Text = TextBox1.Text + "@";
【问题讨论】:
【参考方案1】:感谢 cmets 并为我的错误感到抱歉, 我在以下位置找到了这段代码: http://www.codeproject.com/KB/aspnet/Detecting_Refresh.aspx 这次测试了;)
private bool _refreshState;
private bool _isRefresh;
protected override void LoadViewState(object savedState)
object[] AllStates = (object[])savedState;
base.LoadViewState(AllStates[0]);
_refreshState = bool.Parse(AllStates[1].ToString());
_isRefresh = _refreshState == bool.Parse(Session["__ISREFRESH"].ToString());
protected override object SaveViewState()
Session["__ISREFRESH"] = _refreshState;
object[] AllStates = new object[2];
AllStates[0] = base.SaveViewState();
AllStates[1] = !(_refreshState);
return AllStates;
protected void btn_Click(object sender, EventArgs e)
if (!_isRefresh)
Response.Write(DateTime.Now.Millisecond.ToString());
【讨论】:
这对刷新不起作用,当您刷新页面时,它会告诉浏览器重复上一个事件 这只会让按钮停止工作不止一次,无论帖子来自重新加载还是实际按钮点击。 是的,这行得通。它与我找到的代码相同,但是当您单击按钮然后单击刷新时,它显示“HI”而不是新值。 :P 我想我可以忍受,我会尝试修改它。谢谢 但是如果在页面指令中禁用了视图状态呢?【参考方案2】:您可以测试 Page.IsPostBack 属性以查看页面是否正在响应初始请求,或者它是否正在处理诸如按钮单击事件之类的 PostBack。这里有更多信息:w3schools on IsPostBack
不幸的是,这不会解决您的问题,因为当用户单击按钮以及在按钮操作发生后刷新页面时,IsPostBack 将为 true。
如果您正在执行诸如对某些数据执行 CRUD 之类的任务,您可以 Response.Redirect 用户在您完成处理后返回到同一页面并解决此问题。它具有重新加载内容的附带好处(假设您将记录添加到现在将在页面中显示的数据库......)并防止刷新问题行为。唯一需要注意的是,他们仍然通过追溯历史来重新提交表格。
回发对于 Asp.net 来说是一个糟糕的实现选择,并且通常会毁掉我的 Webforms 平台。
【讨论】:
Response.Redirect 无法解决问题。用户仍然可以使用浏览器中的后退按钮返回并在他们提交该表单的位置刷新,它仍会向数据库发送另一个请求。【参考方案3】:这并不能解决问题。
首先,在视图状态中存储令牌不是一个好主意,因为它可以被禁用。改用控制状态。虽然,HttpModule 是更好的解决方案。
总而言之,这无论如何都行不通。如果您打开另一个选项卡/窗口,则会话对于前一个选项卡/窗口将无效。因此制动它。每次首次加载页面时,您必须以某种方式存储唯一值。使用它来确定请求来自哪里,然后检查“刷新票”。如您所见,一个用户的对象可能会变得相当大,具体取决于发出的请求数量、存储此信息的位置和时间。
恐怕我还没有看到任何解决方案,因为它非常复杂。
【讨论】:
【参考方案4】: bool IsPageRefresh ;
if (Page.IsPostBack)
if (ViewState["postid"].ToString() != Session["postid"].ToString())
IsPageRefresh = true;
Session["postid"] = System.Guid.NewGuid().ToString();
ViewState["postid"] = Session["postid"];
【讨论】:
bool IsPageRefresh;
是在哪里定义的?
最好把它作为一个全局变量和pageload方法的其余代码,这样你就可以随时使用IsPageRefresh了。【参考方案5】:
我尝试了很多方法,最终寻找触发回发/刷新时发送的表单数据...我发现创建的任何 VIEWSTATE 都有一个键,您可以比较这些键,例如...
我把它放在我的自定义主页上,以便像属性一样重用它
public bool IsPageRefresh = false; protected void Page_Init(object sender, EventArgs e) if (IsPostBack) var rForm = Request.Form; var vw = rForm["__EVENTVALIDATION"].ToString(); var svw = Session["__EVENTVALIDATION"] ?? ""; if (vw.Equals(svw)) IsPageRefresh = true; Session["__EVENTVALIDATION"] = vw;
【讨论】:
以上是关于在 C# 中防止页面刷新的主要内容,如果未能解决你的问题,请参考以下文章