按下后退按钮后防止重新提交表单
Prevent form resubmit after pressing back button
我的处境有点微妙。在我的组织中,我们设计了库存管理系统,它是一个基于 JSP 页面和处理它们的 servlet 的 Web 应用程序。
有人要求我解决一个具体问题。我们有一个 JSP 页面,其中包含 HTML 表单 table,其中包含库存详细信息。当用户手动输入详细信息并提交表单时,数据库中的库存详细信息会更新并且工作正常。
问题是这样的:当用户按下浏览器的后退按钮时,用户可以回到他提交详细信息的上一页。当用户提交时,数据将再次保存到 database.I 需要防止这种行为。(类似清除并重新加载页面。)
到目前为止我所做的事情:清除浏览器 cache.Code 工作正常但不是预期的结果。
很遗憾,由于公司规定,我无法分享代码。我需要的是帮助防止这种行为或解决方法。
提前致谢..
您必须使用 Post-Redirect-Get 模式:https://en.m.wikipedia.org/wiki/Post/Redirect/Get.
实际上,每次使用带有 method="post"
的标准 HTML 表单都应该使用该模式来实现。它对 AJAX 发布的表单没有任何用处,这实际上可能是另一种解决方案,但需要更多的工作并且可能需要一些架构更改。
When the user press the browser's back button, user can come to the
previous page where he submitted the details. And when the user submit
this, data is saved once more to the database.
按照你的描述,是基于doGet请求。这意味着每次您访问 URL 时,它都会发送带有添加的任何参数的请求。
正如有人已经提到的,如果您将表单切换为 post 方法 并且 将 Servlet 切换为 doPost , 你不会再有这个问题了。
或者,您可以使用 javascript 解决方案来规避此问题。以下是一些选项:
您可以检查用户是否 clicked the back button,如果为真则禁用表单。
另一种方法是通过 storing a cookie 检查页面加载,如果存在,您可以禁用表单。
您可以在隐藏属性的帮助下使用 javascript 函数来重新加载网页。当用户按下后退按钮时,根据隐藏属性的值,将重新加载页面而不加载缓存页面。
您清除缓存的方法是正确的。再加上,您可以使用这种方法。
<input type="hidden" id="refreshed" value="no">
<script type="text/javascript">
onload=function(){
var e=document.getElementById("refreshed");
if(e.value=="no")e.value="yes";
else{e.value="no";location.reload();}
}
</script>
这种方法的一个缺点是,如果您的客户的浏览器禁用了 JS,这将不会work.Otherwise它应该起作用。
您也可以使用此代码
$(document).ready(function() {
function disableBack() { window.history.forward() }
window.onload = disableBack();
window.onpageshow = function(evt) { if (evt.persisted) disableBack() }
});
我在构建 Django 网络应用程序时遇到了同样的问题,我的解决方案是不允许缓存包含表单的 html。在您的请求处理程序中,不允许浏览器缓存页面。这将强制浏览器从文档中获取新页面。
在这种情况下,您只需在请求处理程序中验证请求的表单是否已经提交。
我的参考代码:
from django.views.decorators.cache import never_cache
@never_cache
def GetForm(request, pk):
# Logic #
if (IsFormCompleted(pk)):
# Handle request #
我的处境有点微妙。在我的组织中,我们设计了库存管理系统,它是一个基于 JSP 页面和处理它们的 servlet 的 Web 应用程序。
有人要求我解决一个具体问题。我们有一个 JSP 页面,其中包含 HTML 表单 table,其中包含库存详细信息。当用户手动输入详细信息并提交表单时,数据库中的库存详细信息会更新并且工作正常。
问题是这样的:当用户按下浏览器的后退按钮时,用户可以回到他提交详细信息的上一页。当用户提交时,数据将再次保存到 database.I 需要防止这种行为。(类似清除并重新加载页面。)
到目前为止我所做的事情:清除浏览器 cache.Code 工作正常但不是预期的结果。
很遗憾,由于公司规定,我无法分享代码。我需要的是帮助防止这种行为或解决方法。
提前致谢..
您必须使用 Post-Redirect-Get 模式:https://en.m.wikipedia.org/wiki/Post/Redirect/Get.
实际上,每次使用带有 method="post"
的标准 HTML 表单都应该使用该模式来实现。它对 AJAX 发布的表单没有任何用处,这实际上可能是另一种解决方案,但需要更多的工作并且可能需要一些架构更改。
When the user press the browser's back button, user can come to the previous page where he submitted the details. And when the user submit this, data is saved once more to the database.
按照你的描述,是基于doGet请求。这意味着每次您访问 URL 时,它都会发送带有添加的任何参数的请求。
正如有人已经提到的,如果您将表单切换为 post 方法 并且 将 Servlet 切换为 doPost , 你不会再有这个问题了。
或者,您可以使用 javascript 解决方案来规避此问题。以下是一些选项:
您可以检查用户是否 clicked the back button,如果为真则禁用表单。
另一种方法是通过 storing a cookie 检查页面加载,如果存在,您可以禁用表单。
您可以在隐藏属性的帮助下使用 javascript 函数来重新加载网页。当用户按下后退按钮时,根据隐藏属性的值,将重新加载页面而不加载缓存页面。
您清除缓存的方法是正确的。再加上,您可以使用这种方法。
<input type="hidden" id="refreshed" value="no">
<script type="text/javascript">
onload=function(){
var e=document.getElementById("refreshed");
if(e.value=="no")e.value="yes";
else{e.value="no";location.reload();}
}
</script>
这种方法的一个缺点是,如果您的客户的浏览器禁用了 JS,这将不会work.Otherwise它应该起作用。
您也可以使用此代码
$(document).ready(function() {
function disableBack() { window.history.forward() }
window.onload = disableBack();
window.onpageshow = function(evt) { if (evt.persisted) disableBack() }
});
我在构建 Django 网络应用程序时遇到了同样的问题,我的解决方案是不允许缓存包含表单的 html。在您的请求处理程序中,不允许浏览器缓存页面。这将强制浏览器从文档中获取新页面。
在这种情况下,您只需在请求处理程序中验证请求的表单是否已经提交。
我的参考代码:
from django.views.decorators.cache import never_cache
@never_cache
def GetForm(request, pk):
# Logic #
if (IsFormCompleted(pk)):
# Handle request #