0
点赞
收藏
分享

微信扫一扫

session 防止表单重复提交


防止表单重复提交应该现在前台做一遍,再在后台做一遍。这样双重安全而且减轻服务器负担。

代码:

package flying.form;

import java.io.IOException;

import java.security.MessageDigest;

import java.security.NoSuchAlgorithmException;

import java.util.Random;

import javax.servlet.ServletException;

import javax.servlet.http.HttpServlet;

import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;

import sun.misc.BASE64Encoder;

//防止表单重复提交

public class ​FormServlet​ extends HttpServlet {


    public void doGet(HttpServletRequest request, HttpServletResponse response)

            throws ServletException, IOException {

        //产生随机数(表单号)

        TokenProcessor tp = TokenProcessor.getInstance();

        String token = tp.generateToken();


        request.getSession().setAttribute("token",token);


        request.getRequestDispatcher("/​WEB-INF​/form.jsp").forward(request,response);


    }


    public void doPost(HttpServletRequest request, HttpServletResponse response)

            throws ServletException, IOException {


    }

}

//产生随机数,相当于表单的令牌

class TokenProcessor{ //令牌


    private TokenProcessor() {}

    private static final TokenProcessor instance = new TokenProcessor();


    public static TokenProcessor getInstance() {

        return instance;


    }


    public String generateToken() {

        String token = System.currentTimeMillis()+new Random().nextInt()+"";


        //随机数长短不一,获取数据摘要,数据摘要始终只有128位

        try {

            MessageDigest md = MessageDigest.getInstance("md5");

            byte[] md5 = md.digest(token.getBytes());


            //base64编码,因为MD5返回乱码,所以用base64编码。base64把数据三个字节变成四个字节:六位一组截取数据的,前面补俩零,这样三个字节24位就会变成32位。base64中的数据从0-63共64种情况。

            BASE64Encoder encoder = new BASE64Encoder();

            return encoder.encode(md5);


        } catch (NoSuchAlgorithmException e) {

            // TODO Auto-generated catch block

            throw new RuntimeException(e);

        }

    }

}





package flying.form;

import java.io.IOException;

import java.io.PrintWriter;

import javax.servlet.ServletException;

import javax.servlet.http.HttpServlet;

import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;

public class ​DoFormServlet​ extends HttpServlet {


    public void doGet(HttpServletRequest request, HttpServletResponse response)

            throws ServletException, IOException {


    }


    public void doPost(HttpServletRequest request, HttpServletResponse response)

            throws ServletException, IOException {

        boolean b = isTokenValid(request);

        if(!b) {

            response.getWriter().write("<script type='text/javascript'>alert('Form repeat!');</script>");

            return;

        }


        request.getSession().removeAttribute("token");


        //doSomething

        response.getWriter().write("Success");

    }


    //判断表单号是否有效

    private boolean isTokenValid(HttpServletRequest request) {

        String client_token = request.getParameter("token");

        if(client_token==null) {

            return false;

        }

        String server_token = (String)request.getSession().getAttribute("token");

        if(server_token==null) {//已经提交过一次,被服务器删掉了session

            return false;

        }


        return client_token.equals(server_token);


    }

}




<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>


<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">

<html>

<head>

<title>My JSP 'form.jsp' starting page</title>

</head>

<body>

    <form action="/form/servlet/DoFormServlet" method="post">

        <input type="hidden" name="token" value="${token }">

        用户名:<input    type="text" name="username"><br />

        <input type="submit" value="提交">

    </form>

</body>

</html>


举报

相关推荐

0 条评论