我有一张表格。在提交按钮时,它会将记录插入到数据库中。如果我回到我的浏览器并刷新页面,它会重新提交它,导致各种各样的问题,如你所能想象的那样。如何确保用户无法刷新上一页,并且该页面的状态会在刷新时自动提交另一个?
答案 0 :(得分:3)
我经常使用的解决方案是:
当用户首次访问该页面(Non-PostBack)时,生成一个令牌值(GUID很容易)。获取此标记值并将其存储在其Session变量和页面中的隐藏字段中。作为一个字段,这个值应该在没有启用ViewState的情况下通过往返服务器来持续存在(我可能会误认为那个数量,所以请检查它!)。如果页面被刷新(表单值丢失),Non-PostBack初始化将生成一个新值。
回发页面时,检索隐藏字段值并将其与用户会话变量中的预期值进行比较:
实现此类解决方案的示例代码:
public partial class MyPage : Page
{
protected HiddenField tokenField;
protected void Page_Load()
{
if(!IsPostBack)
CreateToken();
}
// Call this method to establish a token in session and on the page.
private void CreateToken()
{
string token = new Guid().ToString();
Session["dupeToken"] = token;
tokenField.Value = token;
}
// Call this method to validate the token before continuing workflow.
private bool TokenIsValid()
{
string expectedToken = (string)Session["dupeToken"];
if(expectedToken == null)
return false;
string actualToken = tokenField.Value;
return expectedToken == actualToken;
}
// Call this method when the page submission is complete to prevent re-submission.
private void ConsumeToken()
{
Session["dupeToken"] = null;
}
}
答案 1 :(得分:1)
最简单的方法是将表单包装在< asp:UpdatePanel>
中。这样,所有回发都是通过AJAX完成的,浏览器永远不会要求您重新提交表单。
答案 2 :(得分:0)
最好的两种方法是:
对数据库执行不同字段的检查
在使用基于时间的盐的表单中创建隐藏令牌。如果您在脚本中放置逻辑以检查现有时间并将其与令牌进行比较,则可以允许提交或定义它。例如,如果在特定时间绘制表单,则存储令牌,并且可以在30-60秒内提交,但之后您不能。