网易首页 > 网易号 > 正文 申请入驻

几行代码,轻松搞定 SpringBoot 接口恶意刷新和暴力请求!

0
分享至

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

首先工程为框架搭建,不再详细叙述。

直接上核心代码。

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


* @package: com.technicalinterest.group.interceptor
* @className: IpUrlLimitInterceptor
* @description: ip+url重复请求现在拦截器
* @author: Shuyu.Wang,公众号Java精选,有惊喜!
* @since: 0.1
@Slf4j
public class IpUrlLimitInterceptor implements HandlerInterceptor {

private RedisUtil getRedisUtil() {
return SpringContextUtil.getBean(RedisUtil.class);
}

private static final String LOCK_IP_URL_KEY="lock_ip_";

private static final String IP_URL_REQ_TIME="ip_url_times_";

private static final long LIMIT_TIMES=5;

private static final int IP_LOCK_TIME=60;

@Override
public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception {
log.info("request请求地址uri={},ip={}", httpServletRequest.getRequestURI(), IpAdrressUtil.getIpAdrress(httpServletRequest));
if (ipIsLock(IpAdrressUtil.getIpAdrress(httpServletRequest))){
log.info("ip访问被禁止={}",IpAdrressUtil.getIpAdrress(httpServletRequest));
ApiResult result = new ApiResult(ResultEnum.LOCK_IP);
returnJson(httpServletResponse, JSON.toJSONString(result));
return false;
}
if(!addRequestTime(IpAdrressUtil.getIpAdrress(httpServletRequest),httpServletRequest.getRequestURI())){
ApiResult result = new ApiResult(ResultEnum.LOCK_IP);
returnJson(httpServletResponse, JSON.toJSONString(result));
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 {

/**
* @Description: 判断ip是否被禁用
* @author: shuyu.wang
* @date: 2019-10-12 13:08
* @param ip
* @return java.lang.Boolean
*/
private Boolean ipIsLock(String ip){
RedisUtil redisUtil=getRedisUtil();
if(redisUtil.hasKey(LOCK_IP_URL_KEY+ip)){
return true;
}
return false;
}
/**
* @Description: 记录请求次数
* @author: shuyu.wang
* @date: 2019-10-12 17:18
* @param ip
* @param uri
* @return java.lang.Boolean
*/
private Boolean addRequestTime(String ip,String uri){
String key=IP_URL_REQ_TIME+ip+uri;
RedisUtil redisUtil=getRedisUtil();
if (redisUtil.hasKey(key)){
long time=redisUtil.incr(key,(long)1);
if (time>=LIMIT_TIMES){
redisUtil.getLock(LOCK_IP_URL_KEY+ip,ip,IP_LOCK_TIME);
return false;
}
}else {
redisUtil.getLock(key,(long)1,1);
}
return true;
}

private void returnJson(HttpServletResponse response, String json) throws Exception {
PrintWriter writer = null;
response.setCharacterEncoding("UTF-8");
response.setContentType("text/json; charset=utf-8");
try {
writer = response.getWriter();
writer.print(json);
} catch (IOException e) {
log.error("LoginInterceptor response error ---> {}", e.getMessage(), e);
} finally {
if (writer != null) {
writer.close();
}
}
}

}

代码中的使用的是分布式锁的形式,这样可以最大程度保证线程安全和功能的实现效果。代码中设置的是1S内同一个接口通过同一个ip访问5次,就将该ip禁用1个小时,根据自己项目需求可以自己适当修改,实现自己想要的功能;

另外,推荐下 Spring boot 的用户权限管理系统开源项目: https://gitee.com/yoodb/jing-xuan

redis分布式锁的关键代码:


* @package: com.shuyu.blog.util
* @className: RedisUtil
* @description:
* @author: Shuyu.Wang 公众号:Java精选,有惊喜!
* @since: 0.1
@Component
@Slf4j
public class RedisUtil {

private static final Long SUCCESS = 1L;

@Autowired
private RedisTemplate redisTemplate;
// =============================common============================

/**
* 获取锁
* @param lockKey
* @param value
* @param expireTime:单位-秒
* @return
*/
public boolean getLock(String lockKey, Object value, int expireTime) {
try {
log.info("添加分布式锁key={},expireTime={}",lockKey,expireTime);
String script = "if redis.call('setNx',KEYS[1],ARGV[1]) then if redis.call('get',KEYS[1])==ARGV[1] then return redis.call('expire',KEYS[1],ARGV[2]) else return 0 end end";
RedisScript redisScript = new DefaultRedisScript<>(script, String.class);
Object result = redisTemplate.execute(redisScript, Collections.singletonList(lockKey), value, expireTime);
if (SUCCESS.equals(result)) {
return true;
}
} catch (Exception e) {
e.printStackTrace();
}
return false;
}

/**
* 释放锁
* @param lockKey
* @param value
* @return
*/
public boolean releaseLock(String lockKey, String value) {
String script = "if redis.call('get', KEYS[1]) == ARGV[1] then return redis.call('del', KEYS[1]) else return 0 end";
RedisScript redisScript = new DefaultRedisScript<>(script, String.class);
Object result = redisTemplate.execute(redisScript, Collections.singletonList(lockKey), value);
if (SUCCESS.equals(result)) {
return true;
}
return false;
}

}

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

@Configuration
@Slf4j
public class MyWebAppConfig extends WebMvcConfigurerAdapter {
@Bean
IpUrlLimitInterceptor getIpUrlLimitInterceptor(){
return new IpUrlLimitInterceptor();

@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(getIpUrlLimitInterceptor()).addPathPatterns("/**");
super.addInterceptors(registry);
}
}

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

作者:wang_shuyu https://blog.csdn.net/wang_shuyu/article/details/102531940

公 众号“Java精选”所发表内容注明来源的,版权归原出处所有(无法查证版权的或者未注明出处的均来自网络,系转载,转载的目的在于传递更多信息,版权属于原作者。 如有侵权,请联系,笔者会第一时间删除处理!

最近有很多人问,有没有读者交流群!加入方式很简单,公众号Java精选,回复“加群”,即可入群!

(微信小程序):3000+道面试题,包含Java基础、并发、JVM、线程、MQ系列、Redis、Spring系列、Elasticsearch、Docker、K8s、Flink、Spark、架构设计等,在线随时刷题!

------ 特别推荐 ------

特别推荐:专注分享最前沿的技术与资讯,为弯道超车做好准备及各种开源项目与高效率软件的公众号,「大咖笔记」,专注挖掘好东西,非常值得大家关注。点击下方公众号卡片关注

文章有帮助的话,在看,转发吧!

特别声明:以上内容(如有图片或视频亦包括在内)为自媒体平台“网易号”用户上传并发布,本平台仅提供信息存储服务。

Notice: The content above (including the pictures and videos if any) is uploaded and posted by a user of NetEase Hao, which is a social media platform and only provides information storage services.

相关推荐
热点推荐
苹果大降价!

苹果大降价!

中国经营报
2024-05-21 07:37:45
19岁女孩最后的人生:相亲、订婚、投河自杀 | 深度报道

19岁女孩最后的人生:相亲、订婚、投河自杀 | 深度报道

北青深一度
2024-05-22 16:07:43
还得是亲爸!汪小菲决定接送俩娃上下学,俩娃再也不会厌学了!

还得是亲爸!汪小菲决定接送俩娃上下学,俩娃再也不会厌学了!

娱圈小愚
2024-05-23 10:38:14
2024年养老金调整,企退人员的上调金额,都是如何计算的?

2024年养老金调整,企退人员的上调金额,都是如何计算的?

碎月导师
2024-05-17 07:00:02
庚欣:赖清德“台独自白”,美国怎么想?

庚欣:赖清德“台独自白”,美国怎么想?

直新闻
2024-05-22 22:42:43
揭秘捞女圈潜规则,想捞大哥必须先和马仔满分……

揭秘捞女圈潜规则,想捞大哥必须先和马仔满分……

新青年大院NEWYOUTH
2024-05-22 20:14:49
大润发等待救援

大润发等待救援

蓝鲸财经
2024-05-23 10:35:29
许可馨:中国没有公平可言法律只是权贵玩物。她为何对祖国不满?

许可馨:中国没有公平可言法律只是权贵玩物。她为何对祖国不满?

兰子记
2024-05-17 20:07:53
总局收视榜:《哈尔滨》垫底,《庆余年2》被碾压,第一当之无愧

总局收视榜:《哈尔滨》垫底,《庆余年2》被碾压,第一当之无愧

糊咖娱乐
2024-05-22 09:04:59
结束2年任期?曝曼联确定解雇滕哈格!否决穆帅回归,新帅或3选1

结束2年任期?曝曼联确定解雇滕哈格!否决穆帅回归,新帅或3选1

我爱英超
2024-05-23 00:00:56
又一家民企暴雷了,新一轮暴雷潮要来了?

又一家民企暴雷了,新一轮暴雷潮要来了?

地产人才官
2024-05-22 17:15:35
不老传奇!詹姆斯21季20次进最佳阵 继续刷新自己保持的历史纪录

不老传奇!詹姆斯21季20次进最佳阵 继续刷新自己保持的历史纪录

直播吧
2024-05-23 08:03:14
日本外科医生,见证了200个老人死亡,发现:老死反而是最幸福

日本外科医生,见证了200个老人死亡,发现:老死反而是最幸福

坦然风云
2024-05-22 20:39:56
章子怡抵达戛纳,不受前夫新恋情影响,开心给粉丝签名和合影留念

章子怡抵达戛纳,不受前夫新恋情影响,开心给粉丝签名和合影留念

话娱论影
2024-05-22 22:37:25
突然!从反华到亲华,从友好到“断交”,这个国家变脸也太快了

突然!从反华到亲华,从友好到“断交”,这个国家变脸也太快了

新财迷
2024-05-23 09:47:53
70岁奶奶满头白发偏要尝试公主裙,售货员说不适合她,她还是要买

70岁奶奶满头白发偏要尝试公主裙,售货员说不适合她,她还是要买

大脸猫做局
2024-05-22 21:27:36
15分钟完成着陆!嫦娥六号施展绝技,加媒称:美西方应与中国合作

15分钟完成着陆!嫦娥六号施展绝技,加媒称:美西方应与中国合作

探索日记
2024-05-21 23:23:54
520案大S晕倒细节曝出!台媒:21号就康复出院了,跟个没事人一样

520案大S晕倒细节曝出!台媒:21号就康复出院了,跟个没事人一样

花花lo先森
2024-05-23 11:57:56
英超官方确认,阿森纳的冠军颁奖拱门将被回收♻️

英超官方确认,阿森纳的冠军颁奖拱门将被回收♻️

直播吧
2024-05-23 00:02:34
再见,国米!张康阳时代落幕,奢靡生活依旧:2350万的超跑继续开

再见,国米!张康阳时代落幕,奢靡生活依旧:2350万的超跑继续开

叁炮体育
2024-05-22 19:15:40
2024-05-23 14:36:49
Java精选
Java精选
一场永远也演不完的戏
1548文章数 3855关注度
往期回顾 全部

科技要闻

英伟达狂飙 黄仁勋说要开启"新的工业革命"

头条要闻

岛内关注东部战区联合演训:围岛军演比想象中更快出现

头条要闻

岛内关注东部战区联合演训:围岛军演比想象中更快出现

体育要闻

张氏父子的一场大梦

娱乐要闻

大S儿子被学校退学,张兰称孙子没人管

财经要闻

英伟达Q1收入猛增三倍、利润翻五倍!

汽车要闻

上汽大通大家7超混/大家9超混将于6月7日正式上市

态度原创

本地
旅游
家居
健康
公开课

本地新闻

强制措施展铁腕 “交叉执行”勇亮剑

旅游要闻

日本航空飞机在羽田机场地面与其他飞机发生接触

家居要闻

化实为虚 理性与柔美的交互

在中国,到底哪些人在吃“伟哥”?

公开课

近视只是视力差?小心并发症

无障碍浏览 进入关怀版