【IP限流】⭐️通过切面实现无校验保护接口的防刷逻辑

目录
🍸前言
🍻一、实现方法
🍺二、伪代码实现
🍹三、章末
🍸前言
小伙伴们大家好,上次写了一篇文章记录了最近自己装台式电脑中遇到的问题,以及整体的安装步骤和本地的配置选择,文章链接如下:
【电脑组装】✈️从配置拼装到安装系统组装自己的台式电脑-CSDN博客
这次继续更新平时开发时可能会使用到的常见技术,相信大家在开发时都会用到权限校验,通过此方式可以增强系统安全,比人使最常使用的校验工具就是JWT的token校验,就是通过后端服务器生成token,后续请求需要携带该参数进行校验;但是总会存在一部分接口不需要校验,但是就会面临接口被刷等问题 ,防刷接口也有很多解决方案,本地挑一个常见的 IP 限流,通过记录请求的所属地址,短时间内限制多次请求,这样可以实现简单的流量控制;
🍻一、实现方法
这种实现方式有很多,就拿使用较多的 AOP 切面吧(因为最近了解到切面编程的另一种使用形式),在之前使用较多的方式是定义一个注解,在切面类中使用@Pointcut 标注刚自定义的注解,表示以下逻辑针对该注解起作用,然后在项目中需要使用的地方加上自定义注解即可;还有一种方式是鄙人最近在开发过程中淘到的,起因是要在原有的限流基础上改动一点逻辑,但是由于对项目的不熟悉,翻来翻去也没找到之前限流的入口(以为是自定义注解),最后在aop包下发现一个名字比较符合的类,LimitInterf...,点进去一看,很熟悉,就是切面类逻辑,但是又有一点不同,这里没有标明针对的注解,而是使用路径的方式来控制整个 controller 中的请求方法(怪不得请求层找不到相关注解)
🍺二、伪代码实现
本地简单使用伪代码介绍下这种切面的实现方式,比较简单,看一下定义阶段即可;(为什么不展示完整实现并测试?因为鄙人最近在测试悟空,尤为过瘾不是...尤为紧迫,时间安排不过来...,醉翁之意不在酒,能ctrl C+V即可)

代码结构如下:
1.controller层请求进来后,首先获取该请求的路径,之后获取访问用户的ip,将请求路径拼接ip 作为唯一标识,到redis中查询访问次数,如果达到设置的上限,抛出异常提示已限制;如果是第一次访问,则设置相应的过期时间
2.@Component 注解将当前类声明为组件,项目启动时会自动扫描
@Aspect 注解是切面式编程中的重要注解,标明为切面逻辑类
3.引入redis 作为分布式计数工具,用户每次访问都要记录并且将结果缓存到redis中,下次再访问时先进行是否达到限制
4.注入Servlet工具,获取每次请求的具体路径,用来计数
5.
@Pointcut(value = "execution(* com.test.controller.app.*Controller*.*(..))")这里是指包含test.controller 包下的所有以Controller结尾的类下的所有方法都需要经过该逻辑类校验(适用于统一管理下的切面实现,不用给每个请求方法上加注解)
@Component
@Aspect
@Slf4j
public class InterfaceLimitAspect {@Autowiredprivate RedissonClient redissonClient;@Autowiredprivate HttpServletRequest httpServletRequest;@Pointcut(value = "execution(* com.test.controller.app.*Controller*.*(..))")public void point() {}private final Integer INTERFACELIMITCOUNT = 10;private final Integer INTERFACELIMITTIME = 10;@Before("point()")public void before() {try {String servletPath = httpServletRequest.getServletPath();String ipAddr = IpUtil.getIpAddr(httpServletRequest);RAtomicLong atomicLong = redissonClient.getAtomicLong(servletPath + ":" + ipAddr);if (atomicLong.get() >= INTERFACELIMITCOUNT) {log.info("接口限流:{}", servletPath + ":" + ipAddr);throw new Exception("try later");} else {atomicLong.incrementAndGet();if (atomicLong.get() == 1) {atomicLong.expire(INTERFACELIMITTIME,TimeUnit.HOURS);}}} catch (Exception e) {log.error("接口限流异常", e);}}
}
🍹三、章末
文章到这里就结束了~

相关文章:
【IP限流】⭐️通过切面实现无校验保护接口的防刷逻辑
目录 🍸前言 🍻一、实现方法 🍺二、伪代码实现 🍹三、章末 🍸前言 小伙伴们大家好,上次写了一篇文章记录了最近自己装台式电脑中遇到的问题,以及整体的安装步骤和本地的配置选择,…...
SwiftUI简明概念(3):Path.addArc的clockwise方向问题
一、画个下半圆 SwiftUI中绘制下半圆的一个方法是使用Path.addArc,示例代码如下: var body: some View {Path { path inpath.addArc(center: CGPoint(x: 200, y: 370), radius: 50, startAngle: Angle(degrees: 0), endAngle: Angle(degrees: 180.0), …...
$attrs 和 $listeners
通常情况下,父子组件之间的数据是通过 props 由父向子传递的,当子组件想要修改数据时,则需要通过 $emit 以事件形式交由父组件完成,而这种交互方式只存在于父子组件之间,多层嵌套的时候,处于内层的组件想要…...
智尚招聘求职小程序V1.0.17
微信小程序招聘管理系统。支持多城市、人才版块、招聘会、职场资讯、经纪人入驻等功能。提供全部无加密源码,支持私有化部署。 V1.0.17增加功能 1、增加求职者投简历时检测简历状态功能 更新后无需重新发布前端...
C语言编程-经典易错题1
#include<stdio.h> int main(int argc, char const *argv[]) { unsigned int a6;int b-20; (ab>6)?puts("a>6"):puts("a<6"); return 0; } 这无符号整型问题的答案是输出是 >6 这个问题是考察C语言中整数自动转换原则。 具…...
联宇集团:如何利用CRM实现客户管理精细化与业务流程高效协同
在全球化的浪潮中,跨境电商正成为国际贸易的新引擎。作为领先的跨境电商物流综合服务商,广东联宇物流有限公司(以下称“联宇集团”)以其卓越的物流服务和前瞻的数字化战略,在全球市场中脱颖而出。本文将基于联宇集团搭建CRM系统的实际案例&am…...
如何排查 Windows 无法连接ubuntu远程服务器
当本机连接不上远程服务器,排查问题的思路是确保本机和远程的 sshd 服务都没有问题。 为什么要写这篇文章,一是记录防止忘记,另一方面是 gpt 给的方案太宽泛,需要自己逐一排查。而我们自己遇到的问题多半是有上下文的。这些上下文…...
Win10系统插入带有麦克风的耳机_麦克风不起作用_解决方法_亲测成功---Windows运维工作笔记054
今天我在使用讯飞输入法的时候,想通过讯飞的语音输入法来提高自己的输入效率。 但是这个时候发现一个问题就是我插入我的台式机的是一个带有麦克风的耳机。 但是发现我这个耳机没有办法被电脑识别出麦克风来,所以说就没办法使用讯飞输入法的语音输入功能来直接输入文字了。…...
个人文章汇总(Spring合集:Spring+Mvc+Boot+Cloud)
简述SSH框架和SSM框架的区别 简述Spring、SpringMvc和SpringBoot的区别 Spring:浅谈对Spring的认识 Spring:浅谈对AOP的认识 Spring:依赖注入(IOC)之注解注入 Spring:浅谈对SpringBean的认识 Spring:浅谈对Spring事务的…...
深入理解Java CompletableFuture多线程编排的最佳实践
1. 引言 1.1 多线程编排的必要性 在现代应用程序中,尤其是涉及网络请求、大数据处理或高并发场景时,多线程编排变得尤为重要。传统的顺序执行方式可能导致性能瓶颈,增加响应时间,从而影响用户体验和系统效率。通过多线程编排&am…...
人工智能与机器学习原理精解【29】
文章目录 多层感知机(MLP, Multilayer Perceptron)通用逼近定理(Universal Approximation Theorem)一、定义二、公式三、原理 MLP(多层感知机,Multilayer Perceptron)概述一、数学原理二、公式三…...
【Python】探索 Graphene:Python 中的 GraphQL 框架
人们常说挣多挣少都要开心,这话我相信,但是请问挣少了怎么开心? 随着现代 Web 应用对数据交互需求的不断增长,GraphQL 作为一种数据查询和操作语言,越来越受到开发者的青睐。Graphene 是 Python 语言中实现 GraphQL 的…...
Azure Data Box 80 TB 现已在中国区正式发布
我们非常高兴地宣布,Azure Data Box 80 TB SKU现已在 Azure 中国区正式发布。Azure Data Box 是 Azure 的离线数据传输解决方案,允许您以快速、经济且可靠的方式将 PB 级数据从 Azure 存储中导入或导出。通过硬件传输设备可加速数据的安全传输࿰…...
“表观组学分析:汇智生物的创新技术应用“
🌱 汇智生物 | 专注农业&植物基因组分析 🌱 🎓 教授【优青】团队亲自指导!提供专业实验设计、数据分析、SCI论文辅助等全方位服务。精准高效,为农植物科研保驾护航! 🔬 专业实验外包服务&am…...
【web安全】——sql注入
1.MySQL基础 1.1information_schema数据库详解 简介: 在mysql5版本以后,为了方便管理,默认定义了information_schema数据库,用来存储数据库元数据信息。schemata(数据库名)、tables(表名tableschema)、columns(列名或字段名)。…...
vue基础面试题
1.Vue指令 v-bind:动态绑定数据 v-on:绑定事件监听器 v-for:循环指令,可以循环数组或对象 v-if:根据表达式的真假值,判断是否渲染元素,会销毁并重建 v-show:显示隐藏元素࿰…...
关系型数据库和非关系型数据库的区别
1.常见的主流数据库 关系型数据库: MySql 、达梦 、PostgreSQL 、Oracle 、Sql Server 、Sqlite非关系型数据库: Redis 、MongoDB 、HBase 、 Neo4J 、 CouchDB 2.介绍 关系型数据库最典型的数据结构是表,由二维表及其之间的联系…...
学习之什么是迭代器
什么是迭代器 迭代器的作用:访问容器中的元素 首先要了解什么是Iterablelterable(可迭代的) 字符串、列表、元组、字典都是lterable,都可以放到for循环语句中遍历 lterable类型的定义中一定有一个_iter_方法iter 方法必须返回一个lterator(迭代器) 可以…...
数据结构-3.6.队列的链式实现
队列可以理解为单链表的阉割版,相比单链表而言,队列只有在添加和删除元素上和单链表有区别 一.队列的链式实现: 1.图解: 2.代码: #include<stdio.h> typedef struct LinkNode //链式队列结点 {int data;st…...
Java中去除字符串中的空格
在平时的开发中,在后端经常要获取前端传过来的字符串,有的是用户从输入框中输入的,有的是通过excel表格中获取的。 在这些字符串中,有时候会遇到字符串中有空格、换行符或者制表符,对于这种字符串来说,直接…...
前端导出带有合并单元格的列表
// 导出async function exportExcel(fileName "共识调整.xlsx") {// 所有数据const exportData await getAllMainData();// 表头内容let fitstTitleList [];const secondTitleList [];allColumns.value.forEach(column > {if (!column.children) {fitstTitleL…...
微信小程序 - 手机震动
一、界面 <button type"primary" bindtap"shortVibrate">短震动</button> <button type"primary" bindtap"longVibrate">长震动</button> 二、js逻辑代码 注:文档 https://developers.weixin.qq…...
【项目实战】通过多模态+LangGraph实现PPT生成助手
PPT自动生成系统 基于LangGraph的PPT自动生成系统,可以将Markdown文档自动转换为PPT演示文稿。 功能特点 Markdown解析:自动解析Markdown文档结构PPT模板分析:分析PPT模板的布局和风格智能布局决策:匹配内容与合适的PPT布局自动…...
C# 类和继承(抽象类)
抽象类 抽象类是指设计为被继承的类。抽象类只能被用作其他类的基类。 不能创建抽象类的实例。抽象类使用abstract修饰符声明。 抽象类可以包含抽象成员或普通的非抽象成员。抽象类的成员可以是抽象成员和普通带 实现的成员的任意组合。抽象类自己可以派生自另一个抽象类。例…...
MySQL中【正则表达式】用法
MySQL 中正则表达式通过 REGEXP 或 RLIKE 操作符实现(两者等价),用于在 WHERE 子句中进行复杂的字符串模式匹配。以下是核心用法和示例: 一、基础语法 SELECT column_name FROM table_name WHERE column_name REGEXP pattern; …...
Java多线程实现之Thread类深度解析
Java多线程实现之Thread类深度解析 一、多线程基础概念1.1 什么是线程1.2 多线程的优势1.3 Java多线程模型 二、Thread类的基本结构与构造函数2.1 Thread类的继承关系2.2 构造函数 三、创建和启动线程3.1 继承Thread类创建线程3.2 实现Runnable接口创建线程 四、Thread类的核心…...
HDFS分布式存储 zookeeper
hadoop介绍 狭义上hadoop是指apache的一款开源软件 用java语言实现开源框架,允许使用简单的变成模型跨计算机对大型集群进行分布式处理(1.海量的数据存储 2.海量数据的计算)Hadoop核心组件 hdfs(分布式文件存储系统)&a…...
Aspose.PDF 限制绕过方案:Java 字节码技术实战分享(仅供学习)
Aspose.PDF 限制绕过方案:Java 字节码技术实战分享(仅供学习) 一、Aspose.PDF 简介二、说明(⚠️仅供学习与研究使用)三、技术流程总览四、准备工作1. 下载 Jar 包2. Maven 项目依赖配置 五、字节码修改实现代码&#…...
A2A JS SDK 完整教程:快速入门指南
目录 什么是 A2A JS SDK?A2A JS 安装与设置A2A JS 核心概念创建你的第一个 A2A JS 代理A2A JS 服务端开发A2A JS 客户端使用A2A JS 高级特性A2A JS 最佳实践A2A JS 故障排除 什么是 A2A JS SDK? A2A JS SDK 是一个专为 JavaScript/TypeScript 开发者设计的强大库ÿ…...
MySQL 8.0 事务全面讲解
以下是一个结合两次回答的 MySQL 8.0 事务全面讲解,涵盖了事务的核心概念、操作示例、失败回滚、隔离级别、事务性 DDL 和 XA 事务等内容,并修正了查看隔离级别的命令。 MySQL 8.0 事务全面讲解 一、事务的核心概念(ACID) 事务是…...
