Web应用中避免Form重复提交的三种方案

本文介绍了三种防止Web应用中表单重复提交的方法:通过JavaScript控制提交逻辑、禁用提交按钮及利用Struts的同步令牌机制。这些方法有助于提高用户体验并减少服务器负载。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Web应用中避免Form重复提交的三种方案
2007-08-21 18:29
Web应用中重复提交的问题的三种解决方案

前两种是利用javascript,后面一种是在使用Struts的情况下的参考实现

1 javascript ,设置一个变量,只允许提交一次。
  1. <script language="javascript">
  2. var checkSubmitFlg = false;
  3. function checkSubmit() {
  4. if (checkSubmitFlg == true) {
  5. return false;
  6. }
  7. checkSubmitFlg = true;
  8. return true;
  9. }
  10. document.ondblclick = function docondblclick() {
  11. window.event.returnValue = false;
  12. }
  13. document.onclick = function doconclick() {
  14. if (checkSubmitFlg) {
  15. window.event.returnValue = false;
  16. }
  17. }
  18. </script>

<html:form action="myAction.do" method="post" onsubmit="return checkSubmit();">

2 还是javascript,将提交按钮或者image置为disable

  1. <html:form action="myAction.do" method="post"
  2. onsubmit="getElById('submitInput').disabled = true; return true;">
  3. <html:image styleId="submitInput" src="images/ok_b.gif" border="0" />
  4. </html:form>


3 利用struts的同步令牌机制

利用同步令牌(Token)机制来解决Web应用中重复提交的问题,Struts也给出了一个参考实现。
基本原理:

服务器端在处理到达的请求之前,会将请求中包含的令牌值与保存在当前用户会话中的令牌值进行比较,
看是否匹配。在处理完该请求后,且在答复发送给客户端之前,将会产生一个新的令牌,该令牌除传给
客户端以外,也会将用户会话中保存的旧的令牌进行替换。这样如果用户回退到刚才的提交页面并再次
提交的话,客户端传过来的令牌就和服务器端的令牌不一致,从而有效地防止了重复提交的发生。
  1. if (isTokenValid(request, true)) {
  2. // your code here
  3. return mapping.findForward("success");
  4. } else {
  5. saveToken(request);
  6. return mapping.findForward("submitagain");
  7. }

Struts根据用户会话ID和当前系统时间来生成一个唯一(对于每个会话)令牌的,具体实现可以参考
TokenProcessor类中的generateToken()方法。

1. //验证事务控制令牌,<html:form >会自动根据session中标识生成一个隐含input代表令牌,防止两次提交
2. 在action中:
  1. //<input type="hidden" name="org.apache.struts.taglib.html.TOKEN"
  2. // value="6aa35341f25184fd996c4c918255c3ae">
  3. if (!isTokenValid(request))
  4. errors.add(ActionErrors.GLOBAL_ERROR,
  5. new ActionError("error.transaction.token"));
  6. resetToken(request); //删除session中的令牌

3. action有这样的一个方法生成令牌
  1. protected String generateToken(HttpServletRequest request) {
  2. HttpSession session = request.getSession();
  3. try {
  4. byte id[] = session.getId().getBytes();
  5. byte now[] =
  6. new Long(System.currentTimeMillis()).toString().getBytes();
  7. MessageDigest md = MessageDigest.getInstance("MD5");
  8. md.update(id);
  9. md.update(now);
  10. return (toHex(md.digest()));
  11. } catch (IllegalStateException e) {
  12. return (null);
  13. } catch (NoSuchAlgorithmException e) {
  14. return (null);
  15. }
  16. }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值