防止表单的重复提交(服务端)
2013-07-18 09:41
351 查看
表单页面由servlet程序生成,servlet为每次产生的表单页面分配一个唯一的随机标识号,并在FORM表单的一个隐藏字段中设置这个标识号,同时在当前用户的Session域中保存这个标识号。
当用户提交FORM表单时,负责处理表单提交的serlvet得到表单提交的标识号,并与session中存储的标识号比较,如果相同则处理表单提交,处理完后清除当前用户的Session域中存储的标识号。
在下列情况下,服务器程序将拒绝用户提交的表单请求:
存储Session域中的表单标识号与表单提交的标识号不同
当前用户的Session中不存在表单标识号
用户提交的表单数据中没有标识号字段
当用户提交FORM表单时,负责处理表单提交的serlvet得到表单提交的标识号,并与session中存储的标识号比较,如果相同则处理表单提交,处理完后清除当前用户的Session域中存储的标识号。
在下列情况下,服务器程序将拒绝用户提交的表单请求:
存储Session域中的表单标识号与表单提交的标识号不同
当前用户的Session中不存在表单标识号
用户提交的表单数据中没有标识号字段
//产生表单(没学jsp的做法) public class FormServlet extends HttpServlet { public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { response.setContentType("text/html;charset=UTF-8"); response.setCharacterEncoding("UTF-8"); PrintWriter out = response.getWriter(); //获取随即数 String token = TokenProcessor.getInstance().generateToken(); //由于一会儿还要用到随机数,就将其存入Session中 request.getSession().setAttribute("token", token); out.print("<form action='/day07/servlet/FormSubmitServlet' method='post'>"); //将随机数一隐藏提交的方式提交 out.print("<input type='hidden' name='token' value='"+token+"'>"); out.print("<input type='text' name='username'>"); out.print("<input type='submit' value='提交'>"); out.print("</form>"); } public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { doGet(request, response); } } //单例设计模式 class TokenProcessor{ //1. 把构造方法私有 private TokenProcessor(){}; //2. 自己产生一个类的对象 public static final TokenProcessor instance = new TokenProcessor(); //3. 定义一个方法返回上面产生的对象 public static TokenProcessor getInstance(){ return instance; } public String generateToken(){ //产生随机数,加上当前时间会更唯一 String token = System.currentTimeMillis() + "" + new Random().nextInt(99999999); //数据指纹的算法 数据摘要 md5 try { //用MD5得到消息摘要 MessageDigest md = MessageDigest.getInstance("md5"); //用MessageDigest对象的digest方法返回MD5数组 //任何数据MD5后都是128位 长 16字节 byte md5[] = md.digest(token.getBytes()); //由于直接用数组中的数据进行查码表,有的数字码表会没有,这样就会出现乱码,所以用到base64编码 //任何数据base64编码后都会产出字母如: SABDSSDSD BASE64Encoder encoder = new BASE64Encoder(); //返回这个数当做令牌 return encoder.encode(md5); } catch (NoSuchAlgorithmException e) { throw new RuntimeException(e); } } } //防止重复提交 public class FormSubmitServlet extends HttpServlet { public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { //定义方法判断用户带过来的令牌是否有效 boolean b = isToken(request); //用户带过来的令牌无效,阻止提交 if(!b){ System.out.println("你是重复提交!!"); return; } //用户带过来的令牌有效,处理提交,删除标记 request.getSession().removeAttribute("token"); String username = request.getParameter("username"); //把用户提交的数据保存到数据库中 System.out.println("处理提交请求,把" + username + "保存到数库中!!"); } //判断用户带过来的令牌是否有效 private synchronized boolean isToken(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){ return false; } //判断客户机 的与服务端的是否一致 if(!client_token.equals(server_token)){ return false; } //以上都符合返回真 return true; } public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { doGet(request, response); } }
相关文章推荐
- 客户端服务端防止用户重复提交表单
- js防止表单重复提交验证与.NET服务端验证冲突解决方案
- 使用session在服务端防止表单重复提交
- struts2如何防止表单重复提交
- JAVAWeb_利用Session防止表单重复提交:10-客户端防表单重复提交和服务器端session防表单重复提交
- JavaWeb学习总结(十三)——使用Session防止表单重复提交
- FORM表单防止页面重复提交
- 防止表单重复提交
- 防止form表单重复提交
- 防止表单重复提交的处理
- JavaWeb防止表单重复提交
- Struts2防止表单重复提交
- 防止表单重复提交
- Struts2中防止表单重复提交的两种方式
- 1111struts2防止表单重复提交
- Struts2防止表单重复提交
- 如何防止用户重复提交表单
- jquery防止重复提交表单
- token防止表单重复提交
- 防止表单重复提交的八种简单有效的策略