作用
防止用户连点。
依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-pool2</artifactId>
</dependency>
redis 配置
spring:
redis:
# Redis服务器地址
host: 192.168.18.128
# Redis服务器端口号
port: 6379
# 使用的数据库索引,默认是0
database: 0
# 连接超时时间
timeout: 1800000
# 设置密码
#password: "123456"
lettuce:
pool:
# 最大阻塞等待时间,负数表示没有限制
max-wait: -1
# 连接池中的最大空闲连接
max-idle: 5
# 连接池中的最小空闲连接
min-idle: 0
# 连接池中最大连接数,负数表示没有限制
max-active: 20
拦截器
package com.toplion.interceptor;
import com.toplion.annotation.AccessLimit;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.HandlerInterceptor;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.Objects;
import java.util.concurrent.TimeUnit;
@Component
public class LoginInterceptor implements HandlerInterceptor {
@Autowired
private RedisTemplate<String, String> redisTemplate;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
if (!(handler instanceof HandlerMethod)) {
return true;
}
HandlerMethod handlerMethod = (HandlerMethod) handler;
//获取注解
AccessLimit methodAnnotation = handlerMethod.getMethodAnnotation(AccessLimit.class);
if (Objects.isNull(methodAnnotation)) {
return true;
}
//获取注解值
int maxCount = methodAnnotation.maxCount();
int seconds = methodAnnotation.seconds();
//redis设置参数
String ip = request.getRemoteAddr();
String key = request.getServletPath() + ":" + ip;
String count = redisTemplate.opsForValue().get(key);
if (StringUtils.isBlank(count)) {
redisTemplate.opsForValue().set(key, "1", seconds, TimeUnit.SECONDS);
return true;
}
//获取redis中的值并对比
int countNum = Integer.parseInt(count);
if (countNum < maxCount) {
redisTemplate.opsForValue().increment(key);
} else {
//response 返回 json 请求过于频繁请稍后再试
response.setStatus(401);
response.setCharacterEncoding("UTF-8");
response.setContentType("application/json; charset=utf-8");
response.getWriter().write("操作频繁,请稍后重试");
return false;
}
return true;
}
}
添加进拦截器
package com.toplion.config;
import com.toplion.interceptor.LoginInterceptor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
@Configuration
public class InterceptorConfig implements WebMvcConfigurer {
@Autowired
private LoginInterceptor loginInterceptor;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(loginInterceptor);
}
}