​在实际项目使用中,必须要考虑服务的安全性,当服务部署到互联网以后,就要考虑服务被恶意请求和暴力攻击的情况,下面的教程,通过Spring Boot提供的HandlerInterceptor和Redis 针对 Url + ip在一定时间内访问的次数来将ip禁用,可以根据自己的业务需求进行相应的修改,以达到自己的目的。

首先创建一个自定义的拦截器类,也是最核心的代码。

/**
* @ProjectName: cdkj-framework
* @Package: com.cdkjframework.core.spring.filter
* @ClassName: FilterHandlerInterceptor
* @Description: 拦截过滤
* @Author: xiaLin
* @Date: 2022/6/22 13:36
* @Version: 1.0
*/
public class FilterHandlerInterceptor implements HandlerInterceptor { /**
* 日志
*/
private LogUtils logUtils = LogUtils.getLogger(FilterHandlerInterceptor.class); /**
* redis锁
*/
private final RedisLettuceLock redisLettuceLock; /**
* IP头部变量(可能通过Nginx代理后)
*/
private static final String HEADER_IP = "X-Real-IP"; /**
* 锁IP请求URL地址KEY
*/
private static final String LOCK_IP_URL_KEY = "lock_ip_"; /**
* IP请求URL地址时间
*/
private static final String IP_URL_REQ_TIME = "ip_url_times_"; /**
* 极限时间
*/
private static final long LIMIT_TIMES = 5; /**
* IP锁定时间 秒
*/
private static final int IP_LOCK_TIME = 60; /**
* 构建函数
*/
public FilterHandlerInterceptor(RedisLettuceLock redisLettuceLock) {
this.redisLettuceLock = redisLettuceLock;
} /**
* 预处理
*
* @param request 请求
* @param response 响应
* @param o 参数
* @return 返回结果
* @throws Exception 异常信息
*/
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object o) throws Exception {
String ip = request.getHeader(HEADER_IP);
if (StringUtils.isNullAndSpaceOrEmpty(ip)) {
ip = request.getRemoteAddr();
}
logUtils.info("request 请求地址 Uri={},ip={}", request.getRequestURI(), ip);
if (ipIsLock(ip)) {
logUtils.info("ip访问被禁止={}", ip);
ResponseBuilder builder = ResponseBuilder.failBuilder("ip访问被禁止");
returnJson(response, builder);
return false;
}
if (!addRequest(ip, request.getRequestURI())) {
ResponseBuilder builder = ResponseBuilder.failBuilder("ip访问被禁止");
returnJson(response, builder);
return false;
}
return true;
} @Override
public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception { } @Override
public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception { } /**
* IP 是否已锁
*
* @param ip IP 地址
* @return 返回是否成功
*/
private Boolean ipIsLock(String ip) {
if (redisLettuceLock.lock(LOCK_IP_URL_KEY + ip)) {
return true;
}
return false;
} /**
* 添加请求信息
*
* @param ip IP 地址
* @param uri 请求路径
* @return 返回是否成功
*/
private Boolean addRequest(String ip, String uri) {
String key = IP_URL_REQ_TIME + ip + uri;
if (RedisUtils.syncExists(key)) {
long time = RedisUtils.syncIncr(key, IntegerConsts.ONE);
if (time >= LIMIT_TIMES) {
redisLettuceLock.lock(LOCK_IP_URL_KEY + ip, IP_LOCK_TIME, ip);
return false;
}
} else {
redisLettuceLock.lock(key, (long) IntegerConsts.ONE, IntegerConsts.ONE);
}
return true;
} /**
* 返回结果
*
* @param response 响应
* @param builder 返回结果
* @throws Exception 异常信息
*/
private void returnJson(HttpServletResponse response, ResponseBuilder builder) throws Exception {
ResponseUtils.out(response, builder);
}
}

  最后将上面自定义的拦截器通过WebMvcConfigurer下的registry.addInterceptor添加一下,就生效了。

/**
* @ProjectName: cdkj-framework
* @Package: com.cdkjframework.core.spring.filter
* @ClassName: WebMvcFilterConfigurerAdapter
* @Description: java类作用描述
* @Author: xiaLin
* @Date: 2022/6/22 13:37
* @Version: 1.0
*/
@RequiredArgsConstructor
public class WebMvcFilterConfigurerAdapter implements WebMvcConfigurer { /**
* redis锁
*/
private final RedisLettuceLock redisLettuceLock; /**
* 过虑句柄拦截器
*
* @return 返回拦截器
*/
@Bean
private FilterHandlerInterceptor filterHandlerInterceptor() {
return new FilterHandlerInterceptor(redisLettuceLock);
} /**
* 添加 拦截器
*
* @param registry 拦截器注册
*/
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(filterHandlerInterceptor()).addPathPatterns("/**");
}
}

  自己可以写一个for循环来测试改功能,这里就不具体详细介绍了。

文章中的工具类可参考:https://gitee.com/cdkjframework/common/tree/1.0.2/

Spring Boot 防止接口被恶意刷新、暴力请求的更多相关文章

  1. spring boot rest 接口集成 spring security(2) - JWT配置

    Spring Boot 集成教程 Spring Boot 介绍 Spring Boot 开发环境搭建(Eclipse) Spring Boot Hello World (restful接口)例子 sp ...

  2. spring boot rest 接口集成 spring security(1) - 最简配置

    Spring Boot 集成教程 Spring Boot 介绍 Spring Boot 开发环境搭建(Eclipse) Spring Boot Hello World (restful接口)例子 sp ...

  3. Spring Boot Web应用开发 CORS 跨域请求支持:

    Spring Boot Web应用开发 CORS 跨域请求支持: 一.Web开发经常会遇到跨域问题,解决方案有:jsonp,iframe,CORS等等CORS与JSONP相比 1. JSONP只能实现 ...

  4. 46. Spring Boot中使用AOP统一处理Web请求日志

    在之前一系列的文章中都是提供了全部的代码,在之后的文章中就提供核心的代码进行讲解.有什么问题大家可以给我留言或者加我QQ,进行咨询. AOP为Aspect Oriented Programming的缩 ...

  5. Spring boot CommandLineRunner接口使用例子

    前言 Spring boot的CommandLineRunner接口主要用于实现在应用初始化后,去执行一段代码块逻辑,这段初始化代码在整个应用生命周期内只会执行一次. 如何使用CommandLineR ...

  6. spring boot: 设计接口站api的版本号,支持次版本号(spring boot 2.3.2)

    一,为什么接口站的api要使用版本号? 1,当服务端接口的功能发生改进后, 客户端如果不更新版本,    则服务端返回的功能可能不能使用,    所以在服务端功能升级后,     客户端也要相应的使用 ...

  7. spring boot:给接口增加签名验证(spring boot 2.3.1)

    一,为什么要给接口做签名验证? 1,app客户端在与服务端通信时,通常都是以接口的形式实现, 这种形式的安全方面有可能出现以下问题: 被非法访问(例如:发短信的接口通常会被利用来垃圾短信) 被重复访问 ...

  8. 寻找写代码感觉(三)之使用 Spring Boot 编写接口

    一.前言 项目配置完之后,接着就是写接口了,那咱们就开始吧. 二.项目配置补充知识点 上篇文章写的是关于项目属性配置的一些知识,这里针对上次遗忘内容进行补充如下: 2.1.获取配置文件的值 在appl ...

  9. spring boot:使接口返回统一的RESTful格式数据(spring boot 2.3.1)

    一,为什么要使用REST? 1,什么是REST? REST是软件架构的规范体系,它把资源的状态用URL进行资源定位, 以HTTP动作(GET/POST/DELETE/PUT)描述操作 2,REST的优 ...

  10. spring boot 统一接口异常返回值

    创建业务 Exception 一般在实际项目中,推荐创建自己的 Exception 类型,这样在后期会更容易处理,也比较方便统一,否则,可能每个人都抛出自己喜欢的异常类型,而造成代码混乱 Servic ...

随机推荐

  1. Day29 派生, 封装 , 多态, 反射

    Day29 派生, 封装 , 多态, 反射 内容概要 派生方法的实践 面向对象之封装 面向对象之多态 面向对象之反射 反射的实践案例 内容详细 1.派生方法的实践 #需求展示 import json ...

  2. 打印菱形-java

    public class WeekendDemo01 { /** 打印菱形 * * * *** * ***** * *** * * */ public static void main(String[ ...

  3. linux全新机器环境搭建流程梳理

    软件解压后安装基础指令(复制用):./configure && make && make install ./configure --prefix=/usr/local ...

  4. Zabbix与乐维监控对比分析(二)——Agent管理、自动发现、权限管理

    上期我们详细介绍了Zabbix与乐维监控的架构与性能对比分析,透过架构与性能对比分析,用户可以对乐维监控之所以能成为"Zabbix企业版"有一个初步的认知.本篇是Zabbix对比乐 ...

  5. 【Java框架】SSM-Spring总结:IOC、DI、AOP、JDBC、事务管理、实际案例

    〇.概述 1.常用资料 2.组成 一.控制反转与依赖注入 (一)Spring概述 1.介绍 以IOC和AOP为内核的框架 通过IOC实现控制,使用spring创建对象,与DI描述同一个概念 DI是对象 ...

  6. 【Java SE进阶】Day06 线程、同步

    一.线程 1.多线程原理 流程图 内存图解说明 创建线程的方式 继承Thread类 实现 Runnable接口 2.继承Thead类 3.实现Runnable接口 实现接口,重写run方法 最终均需要 ...

  7. 【每日一题】【归并排序/堆排序&虚拟头结点】148. 排序链表-211220/220217【出栈时不断容易产生环状链表!】

    给你链表的头结点 head ,请将其按 升序 排列并返回 排序后的链表 . 进阶: 你可以在 O(n log n) 时间复杂度和常数级空间复杂度下,对链表进行排序吗? 方法1:归并排序+使用辅助函数 ...

  8. 【大数据面试】【框架】Hive:架构、计算引擎、比较、内外部表、by、函数、优化、数据倾斜、动静态分区

    一.组成 1.架构 源数据原本是存在dubby数据库,存在MySQL可以支持多个客户端 客户端.数据存储(HDFS).MR计算引擎 2.计算引擎的选择 MR引擎:基于磁盘,计算时间长,但一定能算出结果 ...

  9. 现代 CSS 高阶技巧,不规则边框解决方案

    本文是 CSS Houdini 之 CSS Painting API 系列第四篇. 现代 CSS 之高阶图片渐隐消失术 现代 CSS 高阶技巧,像 Canvas 一样自由绘图构建样式! 现代 CSS ...

  10. 深入解读MySQL InnoDB存储引擎Update语句执行过程

    参考b站up 戌米的论文笔记 https://www.bilibili.com/video/BV1Tv4y1o7tA/ 书籍<mysql是怎样运行的> 极客时间<mysql实战45讲 ...