创建TokenForm注解,标记需要防重提交页面(View) import java.lang.annotation.Documented; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; @Target(ElementType.METHOD) @Retention(RetentionPolicy.RUNTIME) @Documented public @interface TokenForm { //如果create为true,表示是一个跳转到增加页面的请求 //boolean create() default false; //如果是remove为true,表示是一个增加提交的请求 boolean remove() default false; }
|
创建拦截器 import java.util.ArrayList; import java.util.List; import java.util.UUID; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import javax.servlet.http.HttpSession; import org.chu.annotation.TokenForm; import org.springframework.web.method.HandlerMethod; import org.springframework.web.servlet.HandlerInterceptor; import org.springframework.web.servlet.ModelAndView; public class TokenInterceptor implements HandlerInterceptor { @Override public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { //第一步:如果是一个增加页面的请求,就创建一个Token List<String> tokenPool=null; HandlerMethod hm = (HandlerMethod) handler; TokenForm tokenForm = hm.getMethodAnnotation(TokenForm.class); //判断注解是否为空 if(tokenForm!=null) { HttpSession session = request.getSession(); if(session.getAttribute("tokenPool")==null) { tokenPool = new ArrayList<>(); }else { tokenPool=(List<String>) session.getAttribute("tokenPool"); } //只要进入或者提交都要创建一个新的Token放在session里面 String sessionToken = UUID.randomUUID().toString(); //将创建的Token放在会话的tokenPool里面 tokenPool.add(sessionToken); //将创建的Token放在会话中返回页面 session.setAttribute("sessionToken", sessionToken); session.setAttribute("tokenPool", tokenPool); //remove为true,表示一个提交增加的请求 if(tokenForm.remove()) { String formToken = request.getParameter("formToken"); List<String> resultTokenPool = (List<String>) session.getAttribute("tokenPool"); boolean flag = false; for (String token : resultTokenPool) { if(token.equals(formToken)) { resultTokenPool.remove(token); flag = true; break; } } //在提交页面表单中添加<input type="hidden" name="formToken" value="${sessionScope.sessionToken }"> if(flag==false) { response.sendRedirect(request.getParameter("token.invoke")); return false; } } } return true; } @Override public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception { // TODO Auto-generated method stub } @Override
|
在配置文件(config)中加入拦截器 @Override public void addInterceptors(InterceptorRegistry registry) { TokenInterceptor tokenInterceptor = new TokenInterceptor(); registry.addInterceptor(tokenInterceptor ) //拦截所有请求 .addPathPatterns("/**") //排除登录不拦截 .excludePathPatterns("/user/login") //排除注销不拦截 .excludePathPatterns("/user/undo"); }
|