zoukankan      html  css  js  c++  java
  • [原创]java WEB学习笔记34:Session 案例 之 解决表单重复提交

    本博客为原创:综合 尚硅谷(http://www.atguigu.com)的系统教程(深表感谢)和 网络上的现有资源(博客,文档,图书等),资源的出处我会标明

    本博客的目的:①总结自己的学习过程,相当于学习笔记 ②将自己的经验分享给大家,相互学习,互相交流,不可商用

    内容难免出现问题,欢迎指正,交流,探讨,可以留言,也可以通过以下方式联系。

    本人互联网技术爱好者,互联网技术发烧友

    微博:伊直都在0221

    QQ:951226918

    -----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

    index.jsp 为表单提交的页面  TokenServlet.java 为表单提交的处理Servlet

    1.重复提交情况:

      ① 在表单提交到一个 Servlet ,而 Servlet 又通过请求转发的方式响应了一个JSP(html) 页面,此时地址栏还保留着 Servelt 的路径。在响应页面点击 "刷新";


      ② 在响应页面没有达到浏览器时候点击 "提交按钮";


      ③ 在已经提交的页面中,点击 "返回" ,再点击 "提交";

    2.不是重复提交的情况:在已经提交表单的页面,点击 "返回" ,再 "刷新" 原表单页面,再 "提交"

    3.如何避免表单的重复提交:


        在表单中做一个标记,提交到 Servlet 时,检查标记是否存在且是否和预定义的标记一致
        若一致,则受理请求,并且销毁标记;
        若不一致,或没有标记,则直接响应提示信息:"重复提交"

    ① 方案一:仅提供一个隐藏域:<input type="hidden" name="token" value="jason"/> ,不可行,原因://清除标记:没有方法清除固定的请求参数

      index.jsp 

     1 <body>
     2     <%
     3         request.setAttribute("token", "tokenValue");
     4     
     5     %>
     6     
     7     <form action="<%= request.getContextPath() %>/tokenServlet" method="post">
     8         
     9     <input type="hidden"  name="token" value="jason"/> 
    10     
    11             
    12             
    13             name:<input type="text" name="name"/>
    14             <input type="submit" value="submit"/>
    15     
    16     </form>
    17 
    18 </body>

      TokenServlet.java

    1 protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    2     
    3         String token = request.getParameter("token");
    4         if("jason".equals(token)){
    5             //清除标记:没有方法清除固定的请求参数
    6         }
    7 
    8 }


    ② 方案二:把标记放入 request 中 , 行不通。因为表单页面刷新后,request 已经被销毁了,再提交表单是一个新的 request

      index.jsp

     1 <body>
     2     <%
     3         request.setAttribute("token", "tokenValue");
     4     %>
     5     
     6     <form action="<%= request.getContextPath() %>/tokenServlet" method="post">
     7         
     8     <input type="hidden"  name="token" /> 
     9     
    10             
    11             
    12             name:<input type="text" name="name"/>
    13             <input type="submit" value="submit"/>
    14     
    15     </form>
    16 
    17 </body>

      TokenServlet.java

     1 protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { 
     2 Object token = request.getAttribute("token");
     3         
     4         if(token != null){
     5             //清除标记:没有方法清除固定的请求参数
     6         }else{
     7             response.sendRedirect( request.getContextPath() + "/token/token.jsp");
     8             return;
     9             
    10         }
    11 }


    ③ 方案三:把标记放进 session 中。可以.通过 隐藏域设置属性域值 方式 

      index.jsp

     1 <%@ page language="java" contentType="text/html; charset=UTF-8"
     2     pageEncoding="UTF-8"%>
     3 <%@ page import="java.util.*" %>
     4 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
     5 <html>
     6 <head>
     7 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
     8 <title>避免表单的重复提交</title>
     9 </head>
    10 <body>
    11     <%
    12         
    13         String tokenValue = new Date().getTime() + "";
    14         session.setAttribute("token", tokenValue );
    15     %>
    16     
    17     <form action="<%= request.getContextPath() %>/tokenServlet" method="post">
    18        <!-- 隐藏域 --> 
    19     <input type="hidden"  name="token" value="<%= tokenValue %>"/> 
    20     
    21             
    22             
    23             name:<input type="text" name="name"/>
    24             <input type="submit" value="submit"/>
    25     
    26     </form>
    27 
    28 </body>
    29 </html>

      TokenServlet.java

     1 package com.jason.token.servlet;
     2 
     3 import java.io.IOException;
     4 
     5 import javax.servlet.ServletException;
     6 import javax.servlet.annotation.WebServlet;
     7 import javax.servlet.http.HttpServlet;
     8 import javax.servlet.http.HttpServletRequest;
     9 import javax.servlet.http.HttpServletResponse;
    10 import javax.servlet.http.HttpSession;
    11 
    12 
    13 @WebServlet("/tokenServlet")
    14 public class TokenServlet extends HttpServlet {
    15     private static final long serialVersionUID = 1L;
    16 
    17     
    18     protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    19         
    20         //1.获取session
    21          HttpSession session = request.getSession();
    22         
    23          //2.获取设置好的属性域值
    24          Object token = session.getAttribute("token");
    25          
    26          //3.获取隐藏域的值
    27          String tokenValue = request.getParameter("token");
    28          
    29          //4.处理,若 token不为空,且token 和tokenValue相同
    30         if(token != null && token.equals(tokenValue)){
    31             //5.去除标记
    32             session.removeAttribute("token");
    33         }else{
    34             //6.重定向到提示页面
    35             response.sendRedirect( request.getContextPath() + "/token/token.jsp");
    36             return;
    37         }
    38         //7.去除标记后,重定向到 成功页面
    39         response.sendRedirect( request.getContextPath() + "/token/success.jsp");
    40         
    41     }
    42 
    43 }

      success.jsp

    <%@ page language="java" contentType="text/html; charset=UTF-8"
        pageEncoding="UTF-8"%>
    <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
    <html>
    <head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
    <title>Insert title here</title>
    </head>
    <body>
    
    
        <h4>成功</h4>
    
    </body>
    </html> 

      token.jsp

     1 <%@ page language="java" contentType="text/html; charset=UTF-8"
     2     pageEncoding="UTF-8"%>
     3 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
     4 <html>
     5 <head>
     6 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
     7 <title>Insert title here</title>
     8 </head>
     9 <body>
    10     <h4> 重复提交了表单  </h4>
    11 </body>
    12 </html>

    4.总结
      1)使用 重定向方式 可以解决一部分的表单提交问题。

      2)通过session 结合 属性域 与 隐藏域的方式 实现防止表单重复提交。

  • 相关阅读:
    2017微软秋招A题
    UVA 494 Kindergarten Counting Game
    loss function与cost function
    coderforces 721b
    coderforces719b
    PyQt4打包exe文件
    PyQt4 UI设计和调用 使用eric6
    PyQt4 进度条和日历 代码
    PyQt4 颜色选择,字体选择代码
    PyQt4调用UI文件
  • 原文地址:https://www.cnblogs.com/jasonHome/p/5551342.html
Copyright © 2011-2022 走看看