正在显示
6 个修改的文件
包含
171 行增加
和
12 行删除
| 1 | +package com.ruoyi.common.filter; | ||
| 2 | + | ||
| 3 | +import java.io.IOException; | ||
| 4 | +import javax.servlet.Filter; | ||
| 5 | +import javax.servlet.FilterChain; | ||
| 6 | +import javax.servlet.FilterConfig; | ||
| 7 | +import javax.servlet.ServletException; | ||
| 8 | +import javax.servlet.ServletRequest; | ||
| 9 | +import javax.servlet.ServletResponse; | ||
| 10 | +import javax.servlet.http.HttpServletRequest; | ||
| 11 | + | ||
| 12 | +import com.ruoyi.common.enums.HttpMethod; | ||
| 13 | + | ||
| 14 | +/** | ||
| 15 | + * Repeatable 过滤器 | ||
| 16 | + * | ||
| 17 | + * @author ruoyi | ||
| 18 | + */ | ||
| 19 | +public class RepeatableFilter implements Filter | ||
| 20 | +{ | ||
| 21 | + @Override | ||
| 22 | + public void init(FilterConfig filterConfig) throws ServletException | ||
| 23 | + { | ||
| 24 | + | ||
| 25 | + } | ||
| 26 | + | ||
| 27 | + @Override | ||
| 28 | + public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) | ||
| 29 | + throws IOException, ServletException | ||
| 30 | + { | ||
| 31 | + HttpServletRequest req = (HttpServletRequest) request; | ||
| 32 | + if (HttpMethod.PUT.name().equals(req.getMethod()) || HttpMethod.POST.name().equals(req.getMethod())) | ||
| 33 | + { | ||
| 34 | + RepeatedlyRequestWrapper repeatedlyRequest = new RepeatedlyRequestWrapper((HttpServletRequest) request); | ||
| 35 | + chain.doFilter(repeatedlyRequest, response); | ||
| 36 | + } | ||
| 37 | + else | ||
| 38 | + { | ||
| 39 | + chain.doFilter(request, response); | ||
| 40 | + } | ||
| 41 | + } | ||
| 42 | + | ||
| 43 | + @Override | ||
| 44 | + public void destroy() | ||
| 45 | + { | ||
| 46 | + | ||
| 47 | + } | ||
| 48 | +} |
| 1 | +package com.ruoyi.common.filter; | ||
| 2 | + | ||
| 3 | +import java.io.BufferedReader; | ||
| 4 | +import java.io.ByteArrayInputStream; | ||
| 5 | +import java.io.IOException; | ||
| 6 | +import java.io.InputStreamReader; | ||
| 7 | +import java.nio.charset.Charset; | ||
| 8 | +import javax.servlet.ReadListener; | ||
| 9 | +import javax.servlet.ServletInputStream; | ||
| 10 | +import javax.servlet.http.HttpServletRequest; | ||
| 11 | +import javax.servlet.http.HttpServletRequestWrapper; | ||
| 12 | +import com.ruoyi.common.utils.StringUtils; | ||
| 13 | + | ||
| 14 | +/** | ||
| 15 | + * 构建可重复读取inputStream的request | ||
| 16 | + * | ||
| 17 | + * @author ruoyi | ||
| 18 | + */ | ||
| 19 | +public class RepeatedlyRequestWrapper extends HttpServletRequestWrapper | ||
| 20 | +{ | ||
| 21 | + private final byte[] body; | ||
| 22 | + | ||
| 23 | + public RepeatedlyRequestWrapper(HttpServletRequest request) throws IOException | ||
| 24 | + { | ||
| 25 | + super(request); | ||
| 26 | + body = readBytes(request.getReader(), "utf-8"); | ||
| 27 | + } | ||
| 28 | + | ||
| 29 | + @Override | ||
| 30 | + public BufferedReader getReader() throws IOException | ||
| 31 | + { | ||
| 32 | + return new BufferedReader(new InputStreamReader(getInputStream())); | ||
| 33 | + } | ||
| 34 | + | ||
| 35 | + @Override | ||
| 36 | + public ServletInputStream getInputStream() throws IOException | ||
| 37 | + { | ||
| 38 | + final ByteArrayInputStream bais = new ByteArrayInputStream(body); | ||
| 39 | + return new ServletInputStream() | ||
| 40 | + { | ||
| 41 | + | ||
| 42 | + @Override | ||
| 43 | + public boolean isFinished() | ||
| 44 | + { | ||
| 45 | + return false; | ||
| 46 | + } | ||
| 47 | + | ||
| 48 | + @Override | ||
| 49 | + public boolean isReady() | ||
| 50 | + { | ||
| 51 | + return false; | ||
| 52 | + } | ||
| 53 | + | ||
| 54 | + @Override | ||
| 55 | + public void setReadListener(ReadListener listener) | ||
| 56 | + { | ||
| 57 | + | ||
| 58 | + } | ||
| 59 | + | ||
| 60 | + @Override | ||
| 61 | + public int read() throws IOException | ||
| 62 | + { | ||
| 63 | + return bais.read(); | ||
| 64 | + } | ||
| 65 | + }; | ||
| 66 | + } | ||
| 67 | + | ||
| 68 | + /** | ||
| 69 | + * 通过BufferedReader和字符编码集转换成byte数组 | ||
| 70 | + */ | ||
| 71 | + private byte[] readBytes(BufferedReader br, String encoding) throws IOException | ||
| 72 | + { | ||
| 73 | + String str = null, retStr = ""; | ||
| 74 | + while ((str = br.readLine()) != null) | ||
| 75 | + { | ||
| 76 | + retStr += str; | ||
| 77 | + } | ||
| 78 | + if (StringUtils.isNotBlank(retStr)) | ||
| 79 | + { | ||
| 80 | + return retStr.getBytes(Charset.forName(encoding)); | ||
| 81 | + } | ||
| 82 | + return null; | ||
| 83 | + } | ||
| 84 | +} |
| @@ -7,8 +7,9 @@ import org.springframework.beans.factory.annotation.Value; | @@ -7,8 +7,9 @@ import org.springframework.beans.factory.annotation.Value; | ||
| 7 | import org.springframework.boot.web.servlet.FilterRegistrationBean; | 7 | import org.springframework.boot.web.servlet.FilterRegistrationBean; |
| 8 | import org.springframework.context.annotation.Bean; | 8 | import org.springframework.context.annotation.Bean; |
| 9 | import org.springframework.context.annotation.Configuration; | 9 | import org.springframework.context.annotation.Configuration; |
| 10 | +import com.ruoyi.common.filter.RepeatableFilter; | ||
| 11 | +import com.ruoyi.common.filter.XssFilter; | ||
| 10 | import com.ruoyi.common.utils.StringUtils; | 12 | import com.ruoyi.common.utils.StringUtils; |
| 11 | -import com.ruoyi.common.xss.XssFilter; | ||
| 12 | 13 | ||
| 13 | /** | 14 | /** |
| 14 | * Filter配置 | 15 | * Filter配置 |
| @@ -36,11 +37,24 @@ public class FilterConfig | @@ -36,11 +37,24 @@ public class FilterConfig | ||
| 36 | registration.setFilter(new XssFilter()); | 37 | registration.setFilter(new XssFilter()); |
| 37 | registration.addUrlPatterns(StringUtils.split(urlPatterns, ",")); | 38 | registration.addUrlPatterns(StringUtils.split(urlPatterns, ",")); |
| 38 | registration.setName("xssFilter"); | 39 | registration.setName("xssFilter"); |
| 39 | - registration.setOrder(Integer.MAX_VALUE); | 40 | + registration.setOrder(FilterRegistrationBean.HIGHEST_PRECEDENCE); |
| 40 | Map<String, String> initParameters = new HashMap<String, String>(); | 41 | Map<String, String> initParameters = new HashMap<String, String>(); |
| 41 | initParameters.put("excludes", excludes); | 42 | initParameters.put("excludes", excludes); |
| 42 | initParameters.put("enabled", enabled); | 43 | initParameters.put("enabled", enabled); |
| 43 | registration.setInitParameters(initParameters); | 44 | registration.setInitParameters(initParameters); |
| 44 | return registration; | 45 | return registration; |
| 45 | } | 46 | } |
| 47 | + | ||
| 48 | + @SuppressWarnings({ "rawtypes", "unchecked" }) | ||
| 49 | + @Bean | ||
| 50 | + public FilterRegistrationBean someFilterRegistration() | ||
| 51 | + { | ||
| 52 | + FilterRegistrationBean registration = new FilterRegistrationBean(); | ||
| 53 | + registration.setFilter(new RepeatableFilter()); | ||
| 54 | + registration.addUrlPatterns("/*"); | ||
| 55 | + registration.setName("repeatableFilter"); | ||
| 56 | + registration.setOrder(FilterRegistrationBean.LOWEST_PRECEDENCE); | ||
| 57 | + return registration; | ||
| 58 | + } | ||
| 59 | + | ||
| 46 | } | 60 | } |
| @@ -2,11 +2,16 @@ package com.ruoyi.framework.interceptor.impl; | @@ -2,11 +2,16 @@ package com.ruoyi.framework.interceptor.impl; | ||
| 2 | 2 | ||
| 3 | import java.util.HashMap; | 3 | import java.util.HashMap; |
| 4 | import java.util.Map; | 4 | import java.util.Map; |
| 5 | +import java.util.concurrent.TimeUnit; | ||
| 5 | import javax.servlet.http.HttpServletRequest; | 6 | import javax.servlet.http.HttpServletRequest; |
| 6 | -import javax.servlet.http.HttpSession; | 7 | +import org.springframework.beans.factory.annotation.Autowired; |
| 7 | import org.springframework.stereotype.Component; | 8 | import org.springframework.stereotype.Component; |
| 8 | import com.alibaba.fastjson.JSONObject; | 9 | import com.alibaba.fastjson.JSONObject; |
| 10 | +import com.ruoyi.common.filter.RepeatedlyRequestWrapper; | ||
| 11 | +import com.ruoyi.common.utils.StringUtils; | ||
| 12 | +import com.ruoyi.common.utils.http.HttpHelper; | ||
| 9 | import com.ruoyi.framework.interceptor.RepeatSubmitInterceptor; | 13 | import com.ruoyi.framework.interceptor.RepeatSubmitInterceptor; |
| 14 | +import com.ruoyi.framework.redis.RedisCache; | ||
| 10 | 15 | ||
| 11 | /** | 16 | /** |
| 12 | * 判断请求url和数据是否和上一次相同, | 17 | * 判断请求url和数据是否和上一次相同, |
| @@ -23,6 +28,9 @@ public class SameUrlDataInterceptor extends RepeatSubmitInterceptor | @@ -23,6 +28,9 @@ public class SameUrlDataInterceptor extends RepeatSubmitInterceptor | ||
| 23 | 28 | ||
| 24 | public final String SESSION_REPEAT_KEY = "repeatData"; | 29 | public final String SESSION_REPEAT_KEY = "repeatData"; |
| 25 | 30 | ||
| 31 | + @Autowired | ||
| 32 | + private RedisCache redisCache; | ||
| 33 | + | ||
| 26 | /** | 34 | /** |
| 27 | * 间隔时间,单位:秒 默认10秒 | 35 | * 间隔时间,单位:秒 默认10秒 |
| 28 | * | 36 | * |
| @@ -39,8 +47,14 @@ public class SameUrlDataInterceptor extends RepeatSubmitInterceptor | @@ -39,8 +47,14 @@ public class SameUrlDataInterceptor extends RepeatSubmitInterceptor | ||
| 39 | @Override | 47 | @Override |
| 40 | public boolean isRepeatSubmit(HttpServletRequest request) | 48 | public boolean isRepeatSubmit(HttpServletRequest request) |
| 41 | { | 49 | { |
| 42 | - // 本次参数及系统时间 | ||
| 43 | - String nowParams = JSONObject.toJSONString(request.getParameterMap()); | 50 | + RepeatedlyRequestWrapper repeatedlyRequest = (RepeatedlyRequestWrapper) request; |
| 51 | + String nowParams = HttpHelper.getBodyString(repeatedlyRequest); | ||
| 52 | + | ||
| 53 | + // body参数为空,获取Parameter的数据 | ||
| 54 | + if (StringUtils.isEmpty(nowParams)) | ||
| 55 | + { | ||
| 56 | + nowParams = JSONObject.toJSONString(request.getParameterMap()); | ||
| 57 | + } | ||
| 44 | Map<String, Object> nowDataMap = new HashMap<String, Object>(); | 58 | Map<String, Object> nowDataMap = new HashMap<String, Object>(); |
| 45 | nowDataMap.put(REPEAT_PARAMS, nowParams); | 59 | nowDataMap.put(REPEAT_PARAMS, nowParams); |
| 46 | nowDataMap.put(REPEAT_TIME, System.currentTimeMillis()); | 60 | nowDataMap.put(REPEAT_TIME, System.currentTimeMillis()); |
| @@ -48,8 +62,7 @@ public class SameUrlDataInterceptor extends RepeatSubmitInterceptor | @@ -48,8 +62,7 @@ public class SameUrlDataInterceptor extends RepeatSubmitInterceptor | ||
| 48 | // 请求地址(作为存放session的key值) | 62 | // 请求地址(作为存放session的key值) |
| 49 | String url = request.getRequestURI(); | 63 | String url = request.getRequestURI(); |
| 50 | 64 | ||
| 51 | - HttpSession session = request.getSession(); | ||
| 52 | - Object sessionObj = session.getAttribute(SESSION_REPEAT_KEY); | 65 | + Object sessionObj = redisCache.getCacheObject(SESSION_REPEAT_KEY); |
| 53 | if (sessionObj != null) | 66 | if (sessionObj != null) |
| 54 | { | 67 | { |
| 55 | Map<String, Object> sessionMap = (Map<String, Object>) sessionObj; | 68 | Map<String, Object> sessionMap = (Map<String, Object>) sessionObj; |
| @@ -62,9 +75,9 @@ public class SameUrlDataInterceptor extends RepeatSubmitInterceptor | @@ -62,9 +75,9 @@ public class SameUrlDataInterceptor extends RepeatSubmitInterceptor | ||
| 62 | } | 75 | } |
| 63 | } | 76 | } |
| 64 | } | 77 | } |
| 65 | - Map<String, Object> sessionMap = new HashMap<String, Object>(); | ||
| 66 | - sessionMap.put(url, nowDataMap); | ||
| 67 | - session.setAttribute(SESSION_REPEAT_KEY, sessionMap); | 78 | + Map<String, Object> cacheMap = new HashMap<String, Object>(); |
| 79 | + cacheMap.put(url, nowDataMap); | ||
| 80 | + redisCache.setCacheObject(SESSION_REPEAT_KEY, cacheMap, intervalTime, TimeUnit.SECONDS); | ||
| 68 | return false; | 81 | return false; |
| 69 | } | 82 | } |
| 70 | 83 |
-
请 注册 或 登录 后发表评论