【Session案例】Session防止表单重复提交

本文介绍了一种通过生成唯一表单号来防止表单重复提交的方法,并使用MD5加密确保安全性。该方案结合了客户端和服务端验证机制,有效避免了因重复提交而造成的数据库冗余。

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

1、md5和base64

MD5:将数据转化成固定长度的byte。

Base64:将MD5加密后的byte转化成常见的字母,便于在网上传输。

2、session防止表单重复提交,生成表单号

FormServlet

package com.xiaozhi.controller;

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("/form.jsp").forward(request, response);
	}

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		doGet(request, response);

	}

}

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() + "";
		try {

			MessageDigest md5 = MessageDigest.getInstance("md5");
			byte[] md = md5.digest(token.getBytes());
			BASE64Encoder encoder = new BASE64Encoder();
			return encoder.encode(md);

		} catch (NoSuchAlgorithmException e) {
			throw new RuntimeException(e);
		}
	}
}
form.jsp

<%@ page language="java" 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>
	<form action="${pageContext.request.contextPath}/servlet/DoFormServlet"method="post">
		<input type="hidden" name="token" value="${token}"> 
		用户名:<input type="text" name="username"><br/>
		<input type="submit"value="提交">
	</form>
</body>
</html>
DoFormServlet

package com.xiaozhi.controller;

import java.io.IOException;

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 {
		boolean b = isTokenValue(request);
		if (!b) {
			System.out.println("请不要重复提交");
			return;
		}
		request.getSession(false).removeAttribute("token");
		System.out.println("向数据库中注入数据");
	}

	private boolean isTokenValue(HttpServletRequest request) {
		String client_token = request.getParameter("token");
		if (client_token == null) {

			return false;
		}
		String server_token = (String) request.getSession(false).getAttribute(
				"token");
		if (server_token == null) {

			return false;
		}
		if (!server_token.equals(client_token)) {

			return false;
		}

		return true;
	}

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		doGet(request, response);

	}
}







评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值