spring aop实际开发中怎么用,Spring Boot整合AOP,spring boot加spring mvc一起使用aop,项目中使用aop

前言:本文不介绍 AOP 的基本概念、动态代理方式实现 AOP,以及 Spring 框架去实现 AOP。本文重点介绍 Spring Boot 项目中如何使用 AOP,也就是实际项目开发中如何使用 AOP 去实现相关功能。

如果有需要了解 AOP 的概念、动态代理实现 AOP 的,请查看我的另外一篇文章:

一篇文章带你深入了解 AOP


正文开始:


Spring Boot中实际应用AOP

1、之前介绍的实现 AOP 的方式中是有 XML 文件设置。但在 Spring Boot 中,没有 XML 文件,那怎么设置 AOP?

2、实际应用中:MVC三层架构,现需要在控制器中统一进行日志的输出(有各种各样的控制器),那怎么实现?(也就是说实际应用中如何实现?)

1、Cal 接口、CalIml 接口实现类 还是跟 Spring框架实现AOP 中一样。之前的两个依赖不要,添加这个依赖:

<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-aop</artifactId>
</dependency>

2、控制器中需要打印日志,比如:调控制器中的哪个方法(接口)、方法有哪些参数、返回值。当然,你肯定可以在每个方法中写,但显然这不现实。这里用 AOP 方法将打印日志抽离出来,然后需要的时候嵌入到每个方法中

//以下代码仅是为了测试,代码不规范,请注意。@RestController
@RequestMapping("/aop")
public class AopSpringBootTestHandler {@GetMapping("/findAll")public List<Account> findAll() {return Arrays.asList(new Account(1, "张三", 25), new Account(2, "李四", 26));}@GetMapping("/findById/{id}")public Account findById(@PathVariable Integer id) {return new Account(1, "张三", 25);}@GetMapping("/add")public boolean add() {return true;}@GetMapping("/update")public boolean update() {return true;}@GetMapping("/delete/{id}")public boolean delete(@PathVariable Integer id) {return true;}
}

自定义注解

3、自定义注解(比如:创建一个 annotation 的包,然后创建一个 LogAnnotation(可自定义,比如这里是打印日志的注解))

为什么要这个自定义注解?----> 首先你要让 AOP 知道你调了哪些方、哪些方法需要让 AOP 进行处理,所以就要让 AOP 知道这些方法,怎么知道? ----> 通过自定义注解

其次并不是所有的方法都需要进行 AOP 处理,所以通过 注解 标记。

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface LogAnnotation {//使用注解时,给注解中添加值String value() default "";
}

说明:@Target、@Retention、@Documented 都是元注解(描述注解的注解)

@Target 表示该注解的使用目标,其中 @Target(ElementType.METHOD) 表示只能使用在方法上:

@Retention(RetentionPolicy.RUNTIME) 表示在运行时使用该注解。

@interface 标志这是一个注解。

String value() default ""; 固定写法,表示在使用注解的时候,可以添加值,默认为空:

**使用自定义注解:**需要进行 AOP 处理的方法,标记即可

4、标记完后,同理,需要切面类,执行非业务代码(比如这里是输出日志):

@Component
@Aspect
public class CreateAspectUtil {/*我们利用自定义注解标记了哪些方法需要进行AOP处理,那真正需要处理的时候,怎么找到这些标记?通过 Pointcut(切入点)找到这些标记所以这个方法就是为了找到标记,必须是空方法体*/@Pointcut("@annotation(com.example.test.aopspringboottest.annotation.LogAnnotation)")public void logPointCut() {}/*找到标记后,怎么执行日志?1、跟之前一样,有@Before前置通知、@After后置通知等等@Around注解就是将各种通知统一到一起,然后将找标记的方法放进去2、连接点 ProceedingJoinPoint 是 joinPoint 的子接口,只是ProceedingJoinPoint中有这个proceed()方法,为了获取方法的返回值*/@Around("logPointCut()")public Object around(ProceedingJoinPoint joinPoint) throws Throwable {String methodName = joinPoint.getSignature().getName();String methodArgs = Arrays.toString(joinPoint.getArgs());System.out.println(methodName + "方法的参数是:" + methodArgs);return joinPoint.proceed(); //返回目标方法(也就是业务代码)中的返回值}
}

演示: 启动启动类后,直接访问:

没加标记的就不会打印日志。

注意:现在还要求输出自定义注解中的值, 怎么办?----> 通过反射获取注解即可

既然获取注解,注解是添加在方法上的,所以先通过反射获取方法,怎么获取?----> 只有一个连接点,所以还是通过连接点:

@Around("logPointcut()")
public Object around(ProceedingJointPoint jointPoint) throws Throwable {//通过连接点获取到方法的签名MethodSignature methodSignature = (MethodSignature)joinPoint.getSignature();//通过方法签名获取到方法Method method = methodSignature.getMethod();//拿到方法后,拿注解:把自定义注解的运行时类给它LogAnnotation annotation = method.getAnnotation(LogAnnotation.class);if (annotation != null) {//拿注解中的值,通过里面的value方法String value = annotation.value();//这个value就是注解里面的内容System.out.println(value);}
}

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

web架构师编辑器内容-改进字体下拉菜单

前面说到我们可以通过面板配置来更新画布上面的一些属性&#xff0c;如果我们有这样一个需求&#xff1a;在右侧面板配置里面需要查看字体的样式效果我们应该怎么做呢&#xff1f; 我们一开始字体的渲染&#xff1a; const fontFamilyArr [{value: "SimSun","…

在数字电路中,为什么说避免输入信号的缓慢变化,对缓慢变化的信号需要使用施密特触发器输入的器件进行驱动?

在数字电路中,避免输入信号的缓慢变化(如按键复位信号)是非常重要的,因为缓慢变化的信号可能会导致数字逻辑电路的不确定状态和错误操作。施密特触发器(Schmitt Trigger)是一种特殊的电路,它可以解决这个问题。 缓慢变化信号的问题: 噪声敏感性:当输入信号缓慢变化时…

vue事件绑定

vue提供了v-on事件绑定指令&#xff0c;用来辅助程序员为DOM元素绑定事件监听&#xff0c;语法格式如下&#xff1a; v-on&#xff1a;指令可以简写为 注意&#xff1a;原生DOM对象有onclick&#xff0c;oninput&#xff0c;onkeyup等原生事件&#xff0c;替换为vue的事件绑定…

设计模式之-3种常见的工厂模式简单工厂模式、工厂方法模式和抽象工厂模式,每一种模式的概念、使用场景和优缺点。

文章目录 前言一、3种模式的概念、使用场景和优缺点简单工厂模式&#xff08;Simple Factory Pattern&#xff09;&#xff1a;工厂方法模式&#xff08;Factory Method Pattern&#xff09;&#xff1a;抽象工厂模式&#xff08;Abstract Factory Pattern&#xff09;&#xf…

PYQT的使用入门

上一章节&#xff1a;VSCode安装PYQT5-CSDN博客 vscode导航栏右键&#xff0c;新建ui文件

<软考高项备考>《论文专题 - 23 整合管理(1) 》

1 论文基础情况 1.1 各过程写作要点 过程定义、作用写作要点、思路制定项目章程制定项目章程是编写一份正式批准项目并授权项目经理在项目活动中使用组织资源的文件的过程。作用:①明确项目与组织战略目标之间的直接联系&#xff1b;②确立项目的正式地位;③展示组织对项目的…

Python高级语法与正则表达式

Python提供了 with 语句的写法&#xff0c;既简单又安全。 文件操作的时候使用with语句可以自动调用关闭文件操作&#xff0c;即使出现异常也会自动关闭文件操作。 # 1、以写的方式打开文件 with open(1.txt, w) as f:# 2、读取文件内容f.write(hello world) 生成器的创建方…

【Netty】编解码器

目录 Java的编解码Netty编解码器概念解码器(Decoder)编码器(Encoder)编码解码器Codec Java的编解码 编码&#xff08;Encode&#xff09;称为序列化&#xff0c; 它将对象序列化为字节数组&#xff0c;用于网络传输、数据持久化或者其它用途。 解码&#xff08;Decode&#x…

Go中的Context是什么?

在 Go 编程语言&#xff08;通常称为 Golang&#xff09;中&#xff0c;术语 "上下文 "指的是上下文包及其定义的上下文类型。上下文包用于跨 API 边界和进程间传输截止日期、取消信号和其他请求范围值。 上下文包的主要目的是管理并发或分布式系统中操作的生命周期…

Python量化投资——金融数据最佳实践: 使用qteasy+tushare搭建本地金融数据仓库并定期批量更新【附源码】

用qteasytushare实现金融数据本地化存储及访问 目的什么是qteasy什么是tushare为什么要本地化使用qteasy创建本地数据仓库qteasy支持的几种本地化仓库类型配置本地数据仓库配置tushare 的API token 配置本地数据源 —— 用MySQL数据库作为本地数据源下载金融历史数据 数据的定期…

基于多反应堆的高并发服务器【C/C++/Reactor】(中)

在这篇文章中虽然实现了能够和多客户端建立连接&#xff0c;并且同时和多个客户端进行通信。 基于多反应堆的高并发服务器【C/C/Reactor】&#xff08;上&#xff09;-CSDN博客https://blog.csdn.net/weixin_41987016/article/details/135141316?spm1001.2014.3001.5501但是有…

nginx安装letsencrypt证书

1.安装推荐安装letsencrypt证书的客户端工具 官方推荐通过cerbot客户端安装letsencrypt 官方推荐使用snap客户端安装cerbot客户端 apt install snapd snap install --classic certbot 建立certbot软链接&#xff1a;ln -s /snap/bin/certbot /usr/bin/certbot 2.开始安装letse…

速盾网络:高防IP的好处

随着互联网的快速发展&#xff0c;网络安全问题日益突出&#xff0c;越来越多的企业和个人开始关注网络安全防护。其中&#xff0c;高防IP作为一种高效的防御手段&#xff0c;越来越受到用户的青睐。本文将介绍速盾网络高防IP的好处&#xff0c;帮助您了解其优势和应用场景。一…

SuperMap Hi-Fi 3D SDK for Unity基础开发教程

作者&#xff1a;kele 一、背景 众所周知&#xff0c;游戏引擎&#xff08;Unity&#xff09;功能强大&#xff0c;可以做出很多炫酷的游戏和动画效果&#xff0c;这部分功能的实现往往不仅仅是靠可视化界面就能够实现的&#xff0c;还需要代码开发。SuperMap Hi-Fi SDKS for …

清风数学建模笔记-插值算法

内容&#xff1a;插值算法 概念&#xff1a; 二.种类 1.牛顿插值法&#xff0c;拉格朗日插值法&#xff0c;两者容易出现龙格现象 2.分段线性插值&#xff1a;与上面两种相比要更好一些,原理是两线之间构成一条直线&#xff0c;在这条直线上插值&#xff0c;除此之外还有分段…

【华为OD题库-104】猴子吃桃-java

题目 题目描述: 孙悟空喜欢吃蟠桃&#xff0c;一天他乘守卫蟠桃园的天兵天将离开了而偷偷的来到王母娘娘的蟠桃园偷吃蟠桃。 已知蟠桃园有棵蟠桃树&#xff0c;第i棵蟠桃树上有Ni个蟠桃&#xff0c;天兵天将将在H(不小于蟠桃树棵数)小时后回来。 孙悟空可以决定他吃蟠桃的速度K…

读算法霸权笔记01_数学杀伤性武器

1. 数学应用助推数据经济&#xff0c;但这些应用的建立是基于不可靠的人类所做的选择 1.1. 房地产危机&#xff0c;大型金融机构倒闭&#xff0c;失业率上升&#xff0c;在幕后运用着神奇公式的数学家们成为这些灾难的帮凶 1.2. 数学逐渐不再关注全球金融市场动态&#xff0c…

【小白专用】HTML相对路径表示方法

一. HTML相对路径(Relative Path) 同一个目录的文件引用 如果源文件和引用文件在同一个目录里&#xff0c;直接写引用文件名即可。 我们现在建一个源文件info.html&#xff0c;在info.html里要引用index.html文件作为超链接。 假设info.html路径是&#xff1a;c:/Inetpub/ww…

用Python处理PDF:拆分与合并PDF文档

PDF文档在信息共享和数据保存方面被广泛使用&#xff0c;处理PDF文档也成为常见需求。其中&#xff0c;合并和拆分PDF文档能够帮助我们更有效地管理PDF文档&#xff0c;使文档内容分布更合理。通过合并&#xff0c;可以将相关文档整合成一个文件&#xff0c;以便更好地组织和提…

深度学习(Deep Learning) 简介

深度学习&#xff08;Deep Learning&#xff09; 深度学习在海量数据情况下的效果要比机器学习更为出色。 多层神经网络模型 神经网络 有监督机器学习模型 输入层隐藏层 (黑盒)输出层 概念: 神经元 Neuron A^(n1)网络权重 Weights W^n偏移 bias b^n 激活函数: ReLUtan…