1. 什么是表单重复提交

    • 表单的重复提交:
    • 若刷新表单页面, 再提交表单不算重复提交.
    • 在不刷新表单页面的前提下:
      • 多次点击提交按钮
      • 已经提交成功, 按 "回退" 之后, 再点击 "提交按钮".
      • 在控制器响应页面的形式为转发情况下,若已经提交成功, 然后点击 "刷新(F5)“
    • 重复提交的缺点:
      • 加重了服务器的负担
      • 可能导致错误操作.
    • token(令牌)
      1. 用户在访问页面时,我们要生成一个随机的token值
      2. 将该值放入到session域中,同时放在表单隐藏域中
      3. 用户提交请求时,隐藏域中token将会一起提交
      4. 服务器在处理请求时先要检查请求参数中的token和session中的token是否一致
        • 如果一致,则处理请求
        • 否则,返回错误页面
      5. 注意,token使用过一次以后必须要从session域中移除
  2. Struts2 解决表单重复提交

  1. 标记管理

    • Struts 提供的 token 标签可以用来生成一个独一无二的标记. 这个标签必须嵌套在 form 标签的内部使用, 它将在表单里插入一个隐藏字段并把标记值(隐藏域的字段的值)保存在HttpSession 对象里.
    • Token 标签必须与 Token 或 TokenSession 拦截器配合使用, 这两个拦截器都能对标记进行处理.
    • Token 拦截器在遇到重复提交情况时, 会返回 invalid.token 结果并加上一个 Action 错误. 这种错误默认的消息是: The form has already been processed or no token was supplied, please try again.
    • TokenSession 拦截器采取的做法只是阻断后续的提交, 用户将看到同样的响应,但实际上并没有重复提交
  2. Struts2 解决表单的重复提交问题:

    • 在 s:form 中添加 s:token 子标签

      • 生成一个隐藏域
      • 在 session 添加一个属性值
      • 隐藏域的值和 session 的属性值是一致的.
    • 使用 Token 或 TokenSession 拦截器.

      • 这两个拦截器均不在默认的拦截器栈中, 所以需要手工配置一下
      • 若使用 Token 拦截器, 则需要配置一个 token.valid 的 result
      • 若使用 TokenSession 拦截器, 则不需要配置任何其它的 result
    • Token VS TokenSession

      • 都是解决表单重复提交问题的
      • 使用 token 拦截器会转到 token.valid 这个 result
      • 使用 tokenSession 拦截器则还会响应那个目标页面, 但不会执行 tokenSession 的后续拦截器. 就像什么都没发生过一样!
    • 可以使用 s:actionerror 标签来显示重复提交的错误消息.

      • 该错误消息可以在国际化资源文件中覆盖. 该消息可以在 struts-messages.properties 文件中找到struts.messages.invalid.token=The form has already been processed or no token was supplied, please try again.
<s:form action="testForm" >
<!-- 增加token 标签,隐藏属性 -->
<s:token></s:token> <s:textfield name="username" label="用户名"></s:textfield>
<s:submit value="提交"></s:submit>
</s:form>
<!-- token 拦截器 -->
<action name="testForm" class="org.pan.action.TestFormAction" method="testForm">
<!-- 使用token 拦截器,进行表单重复提交校验 -->
<interceptor-ref name="token"></interceptor-ref>
<!-- 不要忘记默认的拦截器栈-->
<interceptor-ref name="defaultStack"></interceptor-ref> <!-- 如果是使用的是 token 拦截器,校验失败后会转到 invalid.token -->
<result name="invalid.token">/WEB-INF/views/token-error.jsp</result>
<result name="success">/WEB-INF/views/success.jsp</result>
</action>
<action name="testForm" class="org.pan.action.TestFormAction" method="testForm">
<!-- 使用tokenSession 拦截器,进行表单重复提交校验 -->
<interceptor-ref name="tokenSession"></interceptor-ref>
<!-- 不要忘记默认的拦截器栈-->
<interceptor-ref name="defaultStack"></interceptor-ref> <!-- 如果是使用的是 tokenSession 拦截器,校验后会回到返回的 action方法 result。就像什么都没发生过 -->
<result name="success">/WEB-INF/views/success.jsp</result>
</action>

12、Struts2表单重复提交的更多相关文章

  1. Struts2防止表单重复提交

    1.说明 系统拦截器的应用. 表单重复提交:当使用请求转化进行跳转的时候,存在着表单重复提交的问题. 2.在表单中加入s:token 如果页面加入了struts2的标签,页面的请求必须进入struts ...

  2. 【转】Struts2解决表单重复提交问题

    用户重复提交表单在某些场合将会造成非常严重的后果.例如,在使用信用卡进行在线支付的时候,如果服务器的响应速度太慢,用户有可能会多次点击提交按钮,而这可能导致那张信用卡上的金额被消费了多次.因此,重复提 ...

  3. [原创]java WEB学习笔记73:Struts2 学习之路-- strut2中防止表单重复提交

    本博客的目的:①总结自己的学习过程,相当于学习笔记 ②将自己的经验分享给大家,相互学习,互相交流,不可商用 内容难免出现问题,欢迎指正,交流,探讨,可以留言,也可以通过以下方式联系. 本人互联网技术爱 ...

  4. struts2视频学习笔记 29-30(Struts 2常用标签,防止表单重复提交)

    课时28 Struts 2常用标签解说 property标签 property标签用于输出指定值: <s:set name="name" value="'kk'&q ...

  5. Struts2笔记——利用token防止表单重复提交

    在一些项目中经常会让用户提交表单,当用户点击按钮提交后,如果再次浏览器刷新,这就会造成表单重复提交,若是提交的内容上传至服务器并请求数据库保存,重复提交的表单可能会导致错误,然后跳转到错误界面,这是一 ...

  6. struts2之防止表单重复提交

    struts.xml配置文件 <?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE struts ...

  7. Struts2 处理表单重复提交

    * 在表单页面中增加一个隐藏域:<s:token></s:token>(需要在表单内)        * 创建一个struts.xml的配置文件,具体配置如下:         ...

  8. Struts2基础学习(八)—Struts2防止表单重复提交

    一.原因      用户重复提交表单在某些场合将会造成非常严重的后果.例如,在使用信用卡进行在线支付的时候,如果服务器的响应速度太 慢,用户有可能会多次点击提交按钮,而这可能导致那张信用卡上的金额被消 ...

  9. Struts2第十三篇【防止表单重复提交】

    回顾防止表单重复提交 当我们学习Session的时候已经通过Session来编写了一个防止表单重复提交的小程序了,我们来回顾一下我们当时是怎么做的: 在Servlet上生成独一无二的token,保存在 ...

随机推荐

  1. [APUE]标准IO库(上)

    一.流和FILE对象 系统IO都是针对文件描述符,当打开一个文件时,即返回一个文件描述符,然后用该文件描述符来进行下面的操作,而对于标准IO库,它们的操作则是围绕流(stream)进行的. 当打开一个 ...

  2. 安卓易学,爬坑不易——腾讯老司机的RecyclerView局部刷新爬坑之路

    针对手游的性能优化,腾讯WeTest平台的Cube工具提供了基本所有相关指标的检测,为手游进行最高效和准确的测试服务,不断改善玩家的体验.目前功能还在免费开放中. 点击地址:http://wetest ...

  3. python与c互相调用

    虽然python开发效率很高,但作为脚本语言,其性能不高,所以为了兼顾开发效率和性能,通常把性能要求高的模块用c或c++来实现或者在c或c++中运行python脚本来处理逻辑,前者通常是python中 ...

  4. IOS FMDB 获取数据库表和表中的数据

    ios开发中,经常会用到数据库sqlite的知识,除了增,删,改,查之外,我们说说如何获取数据库中有多少表和表相关的内容. 前言 跟数据库使用相关的一般的增删改查的语句,这里就不做解释了.在网上有很多 ...

  5. JavaScript特性(attribute)、属性(property)和样式(style)

    最近在研读一本巨著<JavaScript忍者秘籍>,里面有一篇文章提到了这3个概念. 书中的源码可以在此下载.我将源码放到了线上,如果不想下载,可以直接访问在线网址,修改页面名就能访问到相 ...

  6. TFS 测试用例步骤数据统计

    TFS系统集成了一套BI系统,基于SQL Server的Analysis Service进行实现的.通过这几年的深入使用,能够感触到这个数据数据仓库模型是多么的优秀,和微软官方提供的数据仓库示例Adv ...

  7. 笔记:Memory Notification: Library Cache Object loaded into SGA

    笔记:Memory Notification: Library Cache Object loaded into SGA在警告日志中发现一些这样的警告信息:Mon Nov 21 14:24:22 20 ...

  8. CentOS:Yum源的配置

    # cd /etc/yum.repos.d/ # mv CentOS-Base.repo CentOS-Base.repo.bak # wget http://mirrors.163.com/.hel ...

  9. mysql 大表拆分成csv导出

    最近公司有一个几千万行的大表需要按照城市的id字段拆分成不同的csv文件. 写了一个自动化的shell脚本 在/home/hdh 下面 linux-xud0:/home/hdh # lltotal 1 ...

  10. 类型转换器(InitBinder 初始化绑定器)

    单日期格式 导入jar包 创建FirstController.java @Controller public class FirstController { /** * @param binder * ...