1:【定义注解】

 package com.jspxcms.ext.interceptor;
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)
public @interface Token { boolean save() default false; boolean remove() default false; }

2:定义拦截器

 package com.jspxcms.ext.interceptor;

 import java.lang.reflect.Method;
import java.util.UUID; import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; import org.apache.log4j.Logger;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter; import com.jspxcms.core.support.CmsException; public class TokenInterceptor extends HandlerInterceptorAdapter {
private static final Logger LOG = Logger.getLogger(TokenInterceptor.class); @Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
if (handler instanceof HandlerMethod) {
HandlerMethod handlerMethod = (HandlerMethod) handler;
Method method = handlerMethod.getMethod();
Token annotation = method.getAnnotation(Token.class);
if (annotation != null) {
boolean needSaveSession = annotation.save();
if (needSaveSession) {
request.getSession(true).setAttribute("token", UUID.randomUUID().toString());
}
boolean needRemoveSession = annotation.remove();
if (needRemoveSession) {
if (isRepeatSubmit(request)) {
LOG.warn("please don't repeat submit,url:"+ request.getServletPath());
throw new CmsException("不能重复提交申请页面!");
// return false;
}
request.getSession(true).removeAttribute("token");
}
}
return true;
} else {
return super.preHandle(request, response, handler);
}
} private boolean isRepeatSubmit(HttpServletRequest request) {
String serverToken = (String) request.getSession(true).getAttribute("token");
if (serverToken == null) {
return true;
}
String clinetToken = request.getParameter("token");
if (clinetToken == null) {
return true;
}
if (!serverToken.equals(clinetToken)) {
return true;
}
return false;
}
}

3:spring配置

 <?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.2.xsd
http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.2.xsd"
default-lazy-init="true"> <context:annotation-config/>
<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter">
<property name="webBindingInitializer">
<bean class="com.jspxcms.common.web.BindingInitializer"/>
</property>
<property name="customArgumentResolvers">
<list>
<bean class="com.jspxcms.common.web.PageableArgumentResolver" />
</list>
</property>
</bean> <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
</bean> <mvc:annotation-driven />
<mvc:interceptors>
<bean class="com.jspxcms.core.support.ForeInterceptor"/>
<mvc:interceptor>
<mvc:mapping path="/**"/>
<bean class="com.jspxcms.ext.interceptor.TokenInterceptor"></bean>
</mvc:interceptor>
</mvc:interceptors> <bean id="viewResolver" class="com.jspxcms.common.freemarker.FreeMarkerViewResolver">
<property name="contentType" value="text/html; charset=UTF-8"/>
<property name="cacheUnresolved" value="false"/>
<property name="redirectHttp10Compatible" value="false"/>
</bean>
</beans>

4:方法使用

     @Token(save=true)
@RequestMapping( value = "/expertJoinForm.jspx" )
public String expertJoinForm(HttpServletRequest request,
HttpServletResponse response, org.springframework.ui.Model modelMap ) {
User user = Context.getCurrentUser( request );
if( user == null ) {
String id = request.getParameter( "id" );
Response resp = new Response( request, response, modelMap );
Site site = Context.getCurrentSite( request );
GlobalRegister registerConf = site.getGlobal().getRegister();
String orgId = request.getParameter( "orgId" );
if( orgId == null || orgId.trim().equals( "" ) ) {
orgId = "1";
}
if( id != null && id != "1" ) {
Org org = orgService.get( Integer.parseInt( id ) );
List<Org> orgList = new ArrayList<Org>();
orgList.add( org );
modelMap.addAttribute( "orgList", orgList );
}
else {
List<Org> orgList = orgService.findList( null, 1, false, null, null );
modelMap.addAttribute( "orgList", orgList );
}
Org org = orgService.get( Integer.parseInt( orgId ) );
modelMap.addAttribute( "org", org );
if( registerConf.getMode() == GlobalRegister.MODE_OFF ) {
return resp.warning( "register.off" );
}
Map<String, Object> data = modelMap.asMap();
ForeContext.setData( data, request );
return "/1/hongchuang/sys_member_register.html";
}else{
CmsAdvisor advisor=new CmsAdvisor();
modelMap.addAttribute( "advisor", advisor);
Map<String, Object> data = modelMap.asMap();
ForeContext.setData( data, request );
return "/1/hongchuang/expertJoinForm1.html";
}
} /**
* 前台申请加入专家功能
* @author DIXIN
* @since 0727
* @param advisor
* @param request
* @param response
* @param modelMap
* @return
*/
@Token(remove=true)
@RequestMapping( value = "/saveExpertJoinForm.jspx" )
public String saveExpertJoinForm(CmsAdvisor advisor, HttpServletRequest request, HttpServletResponse response, org.springframework.ui.Model modelMap ) {
Response resp = new Response( request, response, modelMap );
advisorService.save( advisor);
Map<String, Object> data = modelMap.asMap();
ForeContext.setData( data, request );
return "/1/hongchuang/expertJoinForm2.html";
}

5:页面使用

需要放在form里面

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

拦截器springmvc防止表单重复提交【3】自己实际项目的更多相关文章

  1. 拦截器springmvc防止表单重复提交【1】

    [参考博客:http://www.cnblogs.com/hdwpdx/archive/2016/03/29/5333943.html] springmvc 用拦截器+token防止重复提交 首先,防 ...

  2. 拦截器springmvc防止表单重复提交【3】3秒后自动跳回首页【重点明白如何跳转到各自需要的页面没有实现 但是有思路】

    [1]定义异常类 [重点]:异常类有个多参数的构造函数public CmsException(String s, String... args),可以用来接受多个参数:如(“异常信息”,“几秒跳转”, ...

  3. 拦截器springmvc防止表单重复提交【2】

    [参考博客:http://my.oschina.net/mushui/blog/143397] 原理:在新建页面中Session保存token随机码,当保存时验证,通过后删除,当再次点击保存时由于服务 ...

  4. springmvc防止表单重复提交demo

    原理:在去某个页面直接生成一个随机数(这里使用的是UUID)并放入session中,用户提交表单时将这个随机数传入服务端与session中的值进行比较,如果不不存在或不相等,则认为是重复提交:如果相等 ...

  5. SpringMVC防止表单重复提交

    最近公司上线,有同志进行攻击,表当防重复提交也没有弄,交给我 ,本人以前也没弄过,知道大概的思路,但是那样实在是太麻烦了,虽然后面试过使用过滤器加拦截器实现,不过还是有点小麻烦. 后来在网上搜索后发现 ...

  6. spring boot 学习(七)小工具篇:表单重复提交

    注解 + 拦截器:解决表单重复提交 前言 学习 Spring Boot 中,我想将我在项目中添加几个我在 SpringMVC 框架中常用的工具类(主要都是涉及到 Spring AOP 部分知识).比如 ...

  7. 12、Struts2表单重复提交

    什么是表单重复提交 表单的重复提交: 若刷新表单页面, 再提交表单不算重复提交. 在不刷新表单页面的前提下: 多次点击提交按钮 已经提交成功, 按 "回退" 之后, 再点击 &qu ...

  8. java struts2入门学习--防止表单重复提交.OGNL语言学习

    一.知识点回顾 防止表单重复提交核心思想: 客户端和服务器端和写一个token,比较两个token的值相同,则非重复提交;不同,则是重复提交. 1.getSession三种方式比较: request. ...

  9. 防止Web表单重复提交的方法总结

    在Web开发中,对于处理表单重复提交是经常要面对的事情.那么,存在哪些场景会导致表单重复提交呢?表单重复提交会带来什么问题?有哪些方法可以避免表单重复提交? 表单重复提交的场景 1.场景一:服务端未能 ...

随机推荐

  1. SetWindowText与SetWindowTextW

    SetWindowTextW用于宽字符SetWindowText  根据定义的宏使用宽字符或者ansi 注意: _T 是自动进行 unicode/ansi版本匹配. 如 _T("aa&quo ...

  2. pt-osc原理

    pt-osc原理 1.检查设置环境 测试db是否可连通,并且验证database是否存在 SET SESSION innodb_lock_wait_timeout=1 //InnoDB事务等待行锁的超 ...

  3. nginx日志分割总结

    nginx日志自己不会进行分个,所有日志都会累积的记录在 access.log,error.log 中,当请求量大,一天就能到几百兆,如果不进行分给,对日志的查看和写入性能都有影响. 1. 编写脚本n ...

  4. Block作为返回值时的使用

    昨天使用一个小例子简单说明了下Block作为参数时的使用. 今天再来复习一下Block作为返回值使用时的情况,先贴一小段热门第三方框架Masonry的官方sample code: [view1 mas ...

  5. 谷歌浏览器和火狐浏览器设置跨域和https、http混用 Chrome

    谷歌浏览器和火狐浏览器设置跨域和https.http混用 Chrome    添加启动项: 右键点击Chrome快捷方式,在目标一栏后添加启动项 允许跨域: --disable-web-securit ...

  6. LeetCode——Add Strings

    LeetCode--Add Strings Question Given two non-negative integers num1 and num2 represented as string, ...

  7. 解决com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: Specified key was too long; max key length is 767 bytes异常

    错误截图: 解决方法: 用root进入mysql终端,执行以下命令: alter database hive character set latin1;

  8. C#抽象类和接口

    抽象类和接口有什么区别?有了抽象类为什么还要接口? 接口和抽象类的相同点是都不能实例化,不同点是接口中的方法都没有方法体,而抽象类则不然,除了抽象方法没有方法体外,其他方法都有方法体. 原因是:在C# ...

  9. MSSQL2005数据库显示单一用户模式,无法进行任何操作

    MSSQL2005数据库显示单一用户模式,无法进行任何操作 经查询,使用exec sp_who进行查看链接线程,发现仍然有链接不断进行请求,将链接踢出,然后通过命令修复即可恢复 处理步骤: exec ...

  10. LeetCode第[22]题(Java):Generate Parentheses

    题目:制造括号序列 难度:Medium 题目内容: Given n pairs of parentheses, write a function to generate all combination ...