一、概述
框架中后端服务两种重复提交策略实现方式
1、基于token方式: 该种方式在请求页面信息时需要在session中预置uuid,并且需要在页面中隐藏该uuid值,在在页面执行保存请求中携带uuid值,后端拦截器中判断请求中携带的uuid和session中的uuid是否相等,且有一方的uuid不存在都判断为重复提交
2、基于组装请求唯一标志方式:将请求携带的参数params、url、当前会话的sessionId组装为唯一标志,即 redisKey = params+url+sessionId, 以此标志redisKey 存储在redis中并设过期时间为8s ,如果相同的请求发生重复提交,则redisKey 一定相同,从而可判断重复提交行为
两种实现方式比较(框架中均采用了,在不同的场景下使用)
-
基于token方式的有点是:判断更加精确,基于在页面中嵌入的uuid来判断, 无法被篡改;缺点是:一个页面不能多次提交(注意多次提交和重复提交的区别,多次提交是正常业务操作),除非增加更换uuid的机制
-
组装请求唯一标志方式的优点是:页面中没有嵌入唯一性标志,所以该种方式支持多次提交,例如修改页面,可能在很短的时间内做重复修改;缺点是:受redisKey 失效时间控制,判断不是严格精确
总结:基于token方式重复提交验证适用于新增页面,且新增成功后页面发生跳转;组装请求唯一标志方式适用于修改页面且可多次重复提交修改,页面操作成功后是否发生跳转均可
框架中前端重复提控制方式
-
前端主要基于控制提交按钮是否可用来阻断提交操作,在点击按钮后立即使按钮变为不可用,在异步请求回调中再使按钮变为可用
二、后端服务重复提交验证 – 基于token方式
1、概要:
这是通过token方式控制表单重复提交的。利用拦截器拦截,@ControllerService注解监控返回值
2、使用步骤:
1)在进入页面的Controller方法上添加@PutSessionValue注解,该注解是往页面 session中加入token值,待在页面获取
2)在表单提交目的Controller方法上添加@CheckRepeatToken,改注解作用是判 断该用户的token值是否存在重复提交,如果有,发返回007错误码
3、注意事项:
1)在需要验证重复提交的ajax设为同步提交:async:false,避免异步发起多个相同请求
2)全局异常拦截方法中需判断是否存在5xx 异常,如果存在则把token在放回session中,
如果后端发生异常,则把token继续维护到session,因为前端页面嵌入的uuid依然存在且没有发生改变
4、技术实现
重复提交验证拦截器声明
|
向session添加uuid标志注解
|
自定义token拦截方式注解
|
向session添加uuid拦截器
|