API接口防刷实现(重复调用)

API接口 - 限制重复调用(防刷)

  • 环境
  • 代码实现
    • 实现方式
    • 定义注解
    • 注解应用

在这里插入图片描述

环境

JDK 8
SpringBoot

代码实现

实现方式

定义注解,通过切面的方式,检测重复调用。

定义注解

import cn.nhd.fsl.entity.system.Prevent;
import cn.nhd.fsl.enums.PreventStrategyEnums;
import cn.nhd.fsl.exception.FslServiceException;
import com.alibaba.fastjson.JSON;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;import java.lang.reflect.Method;
import java.util.Base64;
import java.util.concurrent.TimeUnit;/*** 防刷切面实现类*/
@Aspect
@Component
public class PreventAop {private static Logger log = LoggerFactory.getLogger(PreventAop.class);@Autowiredprivate RedisTemplate<String, String> redisTemplate;private final String redisKey = "fsl:system:resubmit:";/*** 切入点*/@Pointcut("@annotation(cn.nhd.fsl.entity.system.Prevent)")public void pointcut() {}/*** 处理前** @return*/@Before("pointcut()")public void joinPoint(JoinPoint joinPoint) throws Exception {String requestStr = JSON.toJSONString(joinPoint.getArgs()[0]);if (StringUtils.isEmpty(requestStr) || requestStr.equalsIgnoreCase("{}")) {throw new FslServiceException("[防刷]入参不允许为空");}MethodSignature methodSignature = (MethodSignature) joinPoint.getSignature();Method method = joinPoint.getTarget().getClass().getMethod(methodSignature.getName(),methodSignature.getParameterTypes());Prevent preventAnnotation = method.getAnnotation(Prevent.class);String methodFullName = method.getDeclaringClass().getName() + method.getName();entrance(preventAnnotation, requestStr,methodFullName);return;}/*** 入口** @param prevent* @param requestStr*/private void entrance(Prevent prevent, String requestStr,String methodFullName) throws Exception {PreventStrategyEnums strategy = prevent.strategy();switch (strategy) {case DEFAULT:defaultHandle(requestStr, prevent,methodFullName);break;default:throw new FslServiceException("无效的策略");}}/*** 默认处理方式** @param requestStr* @param prevent*/private void defaultHandle(String requestStr, Prevent prevent,String methodFullName) throws Exception {String base64Str = toBase64String(requestStr);long expire = Long.parseLong(prevent.value());String resp = redisTemplate.opsForValue().get(redisKey+methodFullName+base64Str);if (StringUtils.isEmpty(resp)) {redisTemplate.opsForValue().set(redisKey+methodFullName+base64Str, requestStr, expire, TimeUnit.SECONDS);} else {String message = !StringUtils.isEmpty(prevent.message()) ? prevent.message() :expire + "秒内不允许重复请求";throw new FslServiceException(message);}}/*** 对象转换为base64字符串** @param obj 对象值* @return base64字符串*/private String toBase64String(String obj) throws Exception {if (StringUtils.isEmpty(obj)) {return null;}Base64.Encoder encoder = Base64.getEncoder();byte[] bytes = obj.getBytes("UTF-8");return encoder.encodeToString(bytes);}
}
import cn.nhd.fsl.enums.PreventStrategyEnums;import java.lang.annotation.*;/*** 接口防刷注解* 使用:* 在相应需要防刷的方法上加上* 该注解,即可** @author: min.wang*/
@Documented
@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface Prevent {/*** 限制的时间值(秒)** @return*/String value() default "60";/*** 提示*/String message() default "";/*** 策略** @return*/PreventStrategyEnums strategy() default PreventStrategyEnums.DEFAULT;
}

注解应用

@Prevent(message = "10秒内不允许重复调多次", value = "10")

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/3250450.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

打造超酷的 React 迷你日历组件,只需几步!

你好&#xff0c;我是小白Coding日志&#xff0c;一个热爱技术的程序员。在这里&#xff0c;我分享自己在编程和技术世界中的学习心得和体会。希望我的文章能够给你带来一些灵感和帮助。欢迎来到我的博客&#xff0c;一起在技术的世界里探索前行吧&#xff01; 前言 现在市面…

基于Linux的USB-wifi配置流程

目录 内核配置 配置 CFG80211 配置usb 配置 Netlink 配置DHCP 工作流程 1.连接到无线网络 2.设置网络接口&#xff1a; 3.验证连接&#xff1a; 4. 接收数据&#xff1a; 最近daisy一直忙活这个linux的wifi驱动和bluze蓝牙驱动&#xff0c;相比较蓝牙&#xff0c;WiFi的驱动和内…

面对垃圾邮件的骚扰,U-Mail邮件安全网关来帮你

在近几年的时间里&#xff0c;企业面临垃圾邮件的威胁成指数级增长&#xff0c;据第三方统计&#xff0c;垃圾邮件占电子邮件总通讯量的60%以上。与此同时&#xff0c;垃圾邮件的类型以及发送手段也愈加复杂化、多样化&#xff0c;电子邮件也一跃成为病毒或恶意软件的主要传播渠…

金蝶官宣:法大大电子签章“星空旗舰版”来了!

融合了数字签名、实名认证、AI、区块链、大数据等能力的法大大电子签章“星空旗舰版”来了&#xff01;通过与金蝶云星空旗舰版的集成产品打造&#xff0c;法大大携手金蝶共同面向客户提供高质量的产品综合解决方案服务。以下内容转载自金蝶云生态&#xff1a; 产品与解决方案 …

kkfileView

目录 一、基本特性 二、安装与部署 三、项目接入使用 四、项目地址与文档 五、应用场景 六、前端使用 kkFileView是一个基于Spring Boot框架构建的文件文档在线预览解决方案&#xff0c;它提供了广泛的文件类型支持、易部署性、跨平台服务、二次开发友好等多种特性。以下是对…

Nginx(详解)

1. 什么是Nginx&#xff1f; Nginx是一款轻量级的Web 服务器/反向代理服务器及电子邮件&#xff08;IMAP/POP3&#xff09;代理服务器&#xff0c;在BSD-like 协议下发行。其特点是占有内存少&#xff0c;并发能力强&#xff0c;事实上nginx的并发能力在同类型的网页服务器中表…

“点点通“餐饮点餐小程序-计算机毕业设计源码11264

"点点通"餐饮点餐小程序 XXX专业XX级XX班&#xff1a;XXX 指导教师&#xff1a;XXX 摘要 随着中国经济的飞速增长&#xff0c;消费者的智能化水平不断提高&#xff0c;许多智能手机和相关的软件正在得到更多的关注和支持。其中&#xff0c;微信的餐饮点餐小程序更…

C#知识|账号管理系统-账号信息管理界面[1]:账号分类选择框、Panel面板设置

哈喽,你好啊,我是雷工! 前一节实现了多条件查询后端代码的编写, 接下来继续学习账号信息管理界面的功能编写,本节主要记录账号分类选择框和Panel的设置, 以下为学习笔记。 01 功能说明 本节实现以下功能: ①:账号分类选择框只能选择,无法自由输入; ②:账号分类框默认…

11款常用的Python虚拟环境管理器,最受推崇的居然是最后一个

文章目录 1. venv2. virtualenv3. Pipenv4. pyenv5. Conda6. Poetry7. PDM8. Huak9. Pixi10. Rye11. uv《Python从入门到精通&#xff08;第3版&#xff09;&#xff08;软件开发视频大讲堂&#xff09;》编辑推荐内容简介作者简介目录 以下文章来源于Python学研大本营 &#x…

Elasticsearch:如何选择向量数据库?

作者&#xff1a;来自 Elastic Elastic Platform Team 向量数据库领域是一个快速发展的领域&#xff0c;它正在改变我们管理和搜索数据的方式。与传统数据库不同&#xff0c;向量数据库以向量的形式存储和管理数据。这种独特的方法可以实现更精确、更相关的搜索&#xff0c;并允…

ROS2从入门到精通2-3:详解机器人3D物理仿真Gazebo与案例分析

目录 0 专栏介绍1 什么是Gazebo?2 Gazebo架构2.1 Gazebo前后端2.2 Gazebo文件格式2.3 Gazebo环境变量3 Gazebo安装与基本界面4 搭建自己的地图4.1 编辑地图4.2 保存地图4.3 加载地图5 常见问题0 专栏介绍 本专栏旨在通过对ROS2的系统学习,掌握ROS2底层基本分布式原理,并具有…

Java面试八股之Redis怎么实现消息队列

Redis怎么实现消息队列 Redis实现消息队列主要依赖于其内置的数据结构&#xff0c;如List、Pub/Sub&#xff08;发布/订阅&#xff09;和Stream。下面将分别介绍这三种方式及其特点&#xff1a; 1. List实现消息队列 Redis的List是一个双向链表&#xff0c;支持快速的头部和…

ARM架构(二)—— arm v7/v8/v9寄存器介绍

1、ARM v7寄存器 1.1 通用寄存器 V7 V8开始 FIQ个IRQ优先级一样&#xff0c; 通用寄存器&#xff1a;31个 1.2 程序状态寄存器 CPSR是程序状态毒存器&#xff0c;保存条件标志位&#xff0c;中断禁止位&#xff0c;当前处理器模式等控制和状态位。每种异常模式下还存在SPSR&…

Unity扩展SVN命令

可以直接在unity里右键文件提交和查看提交记录 顶部菜单栏上回退和更新整个unity工程 SvnForUnity.CS 记得要放在Editor文件夹下 using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.IO; using UnityEditor; using Unity…

互联网行业的产品方向(二)

数字与策略产品 大数据时代&#xff0c;数据的价值越来越重要。大多数公司开始对内外全部数据进行管理与挖掘&#xff0c;将业务数据化&#xff0c;数据资产化&#xff0c;资产业务化&#xff0c;将数据产品赋能业务&#xff0c;通过数据驱动公司业务发展&#xff0c;支撑公司战…

PyTorch使用细节

model.eval() &#xff1a;让BatchNorm、Dropout等失效&#xff1b; with torch.no_grad() &#xff1a; 不再缓存activation&#xff0c;节省显存&#xff1b; 这是矩阵乘法&#xff1a; y1 tensor tensor.T y2 tensor.matmul(tensor.T)y3 torch.rand_like(y1) torch.matm…

19_Shell练习题

19_Shell练习题 一、获取并打印空行行号 awk /^$/{print NR} test.txt二、求一列的和 awk -v sum0 { sum$2 } END{ print sum } test.txt三、检查文件是否存在 #!/bin/bashecho "请输入要查询文件的全路径名称&#xff1a;" read -p "例如&#xff1a;/temp…

(MLLMs)多模态大模型论文分享(1)

Multimodal Large Language Models: A Survey 摘要&#xff1a;多模态语言模型的探索集成了多种数据类型&#xff0c;如图像、文本、语言、音频和其他异构性。虽然最新的大型语言模型在基于文本的任务中表现出色&#xff0c;但它们往往难以理解和处理其他数据类型。多模态模型…

Volatility:分析MS10-061攻击

1、概述 # 1&#xff09;什么是 Volatility Volatility是开源的Windows&#xff0c;Linux&#xff0c;MaC&#xff0c;Android的内存取证分析工具。基于Python开发而成&#xff0c;可以分析内存中的各种数据。Volatility支持对32位或64位Wnidows、Linux、Mac、Android操作系统…

AI算不出9.11和9.9哪个大?六家大模型厂商总结了这些原因

大模型“答对”或“答错”其实是个概率问题。关于“9.11和9.9哪个大”&#xff0c;这样一道小学生难度的数学题难倒了一众海内外AI大模型。7月17日&#xff0c;第一财经报道了国内外“12个大模型8个都会答错”这道题的现象&#xff0c;大模型的数学能力引发讨论。 “从技术人员…