【Spring AOP】结合日志面向切面编程 两种写法
概念
这里需要提前了解什么是Spring的AOP(Aspect Oriented Programming)。是在OOP(面向对象)思想的一种拓展思想。简单来说就是将某个代码块嵌入到其它的代码块中。笔者先前学Spring也有学什么IoC啊AOP啊,但实际上没有用过、就那听过学过没啥用的。。没会儿就忘记了。那种也就是个了解,好像知道是个什么事儿?当时还特地去背关于AOP的那几个专有名词?现在想想有点好笑。
不过还是需要提前巩固知道几个词。看完了下面的这三个词的用法就开始进入模拟实战。
切面(Aspect):由切点和通知组成。即使用@Aspect注解的类
切点(Pointcut):可以限定访问修饰符、类全限定名、方法名和参数类型,甚至用于匹配注解
通知(Advice):想要嵌入到其它代码块的代码块。其中包括五种类型。
@Before(目标方法执行前执行)
@After(目标方法执行后执行)
@AfterReturning(目标方法返回结果后不出现异常才执行)
@AfterThrowin(出现异常才执行)
@Around(以上都包括)
引入依赖
<!-- Spring Boot -->
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId>
</dependency><!-- 简化开发 -->
<dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId><optional>true</optional>
</dependency><!-- AOP -->
<dependency><groupId>org.aspectj</groupId><artifactId>aspectjweaver</artifactId>
</dependency>
创建注解
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Log {/*** 描述** @return {String}*/String value();}
业务代码
@Slf4j
@RestController
@RequestMapping("/log")
public class LogController {@Log("AOP测试")@GetMapping("/aspect")public void aspect() {log.info("进入AOP测试方法");for(int i = 0; i < 10; ++i) {log.info("执行业务逻辑{}", i);}log.info("结束AOP测试方法");}}
编写切面
有切点
@Slf4j
@Component
@Aspect
public class LogAspect {@Autowiredprivate ApplicationEventPublisher publisher;/*** 切点* 这里面主要掌握两个东西:* 1、如果使用注解的话就需要获取注解的类全限定名* 2、执行的execution表达式(这是比较重要掌握的) 这里面有四个参数 需要知道的是*也可以表示前缀或者后缀 和SQL中的"%"类似* 一、方法的访问权限修饰符(public/protected/default/private)* 二、方法的返回值类型* 三、类的全限定名(包名.类名)* 四、*(..)的第一个表示方法名;括号内表示参数,而两个点表示接收任何参数类型*/@Pointcut("@annotation(com.chf.annotation.Log) && execution(public * com.chf.controller.*Controller.*(..))")public void logPointcut() {}@SneakyThrows@Around("logPointcut()")public Object around(ProceedingJoinPoint point) {// 获取注解完后解析其内部的属性MethodSignature signature = (MethodSignature) point.getSignature();log.info("获取注解,{}", signature); // void com.chf.controller.LogController.aspect()Method method = signature.getMethod();log.info("获取注解的方法,{}", method);// public void com.chf.controller.LogController.aspect()Log logAnnotation = method.getAnnotation(Log.class);log.info("获取使用注解的value参数,{}", logAnnotation.value()); // AOP测试// 发送异步事件Long startTime = System.currentTimeMillis();Object o;try {o = point.proceed();} finally {// 这里可以使用发布订阅模式发布异步事件 至于使用哪一种发布订阅模式就看业务场景了Long endTime = System.currentTimeMillis();publisher.publishEvent(new LogEvent("事件处理的时间是:" + (endTime - startTime) + "ms"));}return o;}
}
无切点
@Slf4j
@Component
@Aspect
public class LogAspect {@Autowiredprivate ApplicationEventPublisher publisher;@SneakyThrows@Around("@annotation(logAnnotation) && execution(public * com.chf.controller.*Controller.*(..))")public Object around(ProceedingJoinPoint point, Log logAnnotation) {// 获取注解完后解析其内部的属性MethodSignature signature = (MethodSignature) point.getSignature();log.info("获取注解,{}", signature); // void com.chf.controller.LogController.aspect()Method method = signature.getMethod();log.info("获取注解的方法,{}", method);// public void com.chf.controller.LogController.aspect()Log logAnnotation = method.getAnnotation(Log.class);log.info("获取使用注解的value参数,{}", logAnnotation.value()); // AOP测试// 发送异步事件Long startTime = System.currentTimeMillis();Object o;try {o = point.proceed();} finally {Long endTime = System.currentTimeMillis();publisher.publishEvent(new LogEvent("事件处理的时间是:" + (endTime - startTime) + "ms"));}return o;}
}
测试
不了解Spring的发布订阅模式可以看这篇博文:https://blog.csdn.net/m0_65563175/article/details/131899828?spm=1001.2014.3001.5501
相关文章:
【Spring AOP】结合日志面向切面编程 两种写法
概念 这里需要提前了解什么是Spring的AOP(Aspect Oriented Programming)。是在OOP(面向对象)思想的一种拓展思想。简单来说就是将某个代码块嵌入到其它的代码块中。笔者先前学Spring也有学什么IoC啊AOP啊,但实际上没有…...
C#在自动化领域的应用前景与潜力
人机界面(HMI)开发:使用C#开发人机界面软件,实现与自动化设备的交互和监控。C#的图形界面设计能力和丰富的控件库使得开发人员能够创建直观、易用的界面。 数据采集与处理:C#可以与各种传感器、设备进行数据通信和采集…...
string模拟实现:
string模拟实现: 上一篇博客,我们对String类有了一个基本的认识,本篇博客我们来从0~1去模拟实现一个String类,当然我们实现的都是一些常用的接口。 ❓我们这里定义了一个string类型,然后STL标准库里面也有string&#…...
系统与软件安全研究(八)
FUZZ101入门 Detail gcc,clang,llvm都有啥区别GCC (GNU Compiler Collection), Clang, 和 LLVM 都是用于编译代码的工具链。它们在某些方面有相似之处,但也有一些重要的区别。 GCC (GNU Compiler Collection):GCC 是由 GNU 组织开发的,是一个非常流行的开源编译器集合。它…...
jmeter测试rpc接口-使用dubbo框架调用【杭州多测师_王sir】
1.基于SOAP架构。基于XML规范。基于WebService协议。特点:接口地址?wsdl结尾2.基于RPC架构,基于dubbo协议,thrift协议。SpringCloud微服务。3.基于RestFul架构,基于json规范。基于http协议(我们常用的都是这种,cms平台也是) Rest…...
Java8中forEach()里使用return的效果
先总结:使用forEach()处理集合时不能使用break和continue这两个方法,可以使用无返回值的return跳出此次循环,效果同标准for循环的continue。 首先,forEach()先对入参判空,然后使用增强for循环调用action.accept(t)&am…...
MVC配置原理
如果你想保存springboot的mvc配置并且还想自己添加自己的配置就用这个。 视图解析器原理,它会从IOC容器里获取配置好视图解析器的配置类里的视图解析器集合, 然后遍历集合,生成一个一个的视图对象,放入候选 视图里,…...
rabbitmq安装
安装erlang方案二 vi /etc/yum.repos.d/rabbitmq-erlang.repo 文件内容: In /etc/yum.repos.d/rabbitmq-erlang.repo [rabbitmq-erlang] namerabbitmq-erlang baseurlhttps://dl.bintray.com/rabbitmq-erlang/rpm/erlang/22/el/7 gpgcheck1 gpgkeyhttps://dl.bi…...
轻松抓取网页内容!API助力开发者,快速数据采集
在如今这个信息爆炸的时代,人们需要从各种渠道获取数据来支持自己的业务需求。而对于开发者们来说,如何快速、准确地从互联网上抓取所需的数据也成为了一项重要的技能。而抓取网页内容 API 则是一种能够帮助开发者轻松实现数据抓取的工具。 一、什么是抓…...
CSDN 直播:腾讯云大数据 ES 结合 AI 大模型与向量检索的新一代云端检索分析引擎 8月-8号 19:00-20:30
本次沙龙围绕腾讯云大数据ES产品展开,重点介绍了腾讯云ES自研的存算分离技术,以及能与AI大模型和文本搜索深度结合的高性能向量检索能力。同时,本次沙龙还将为我们全方位介绍腾讯云ES重磅推出的Elasticsearch Serverless服务,期待…...
区块链智能合约代码示例
以下是一个简单的区块链智能合约代码示例: pragma solidity ^0.4.17;contract SimpleContract {uint public myData;function setMyData(uint newData) public {myData newData;} }该合约具有以下功能: 定义了一个名为 SimpleContract 的合约。定义了一…...
Spring Boot介绍--快速入门--约定优于配置
文章目录 SpringBoot 基本介绍官方文档Spring Boot 是什么?SpringBoot 快速入门需求/图解说明完成步骤快速入门小结 Spring SpringMVC SpringBoot 的关系总结梳理关系如何理解-约定优于配置 SpringBoot 基本介绍 官方文档 官网: https://spring.io/projects/spring-boot 学习…...
Scons编译lib库
实例目录结构: include文件夹:test.hsrc文件夹:test.cSConscriptSConstruct 如下图所示: SConstruct: #执行当前目录下的SConscript SConscript(SConscript);SConscript: import os from SCons.Script…...
React源码解析18(1)------ React.createElement 和 jsx
1.React.createElement 我们知道在React17版本之前,我们在项目中是一定需要引入react的。 import React from “react” 即便我们有时候没有使用到React,也需要引入。原因是什么呢? 在React项目中,如果我们使用了模板语法JSX&am…...
系列3-常见的高可用MySQL解决方案
高可用主要解决两个问题,如何实现数据共享和同步数据、如何处理failover,数据共享的解决方案一般是SAN,数据同步通过rsync和drbd技术来实现。 1、主从复制解决方案 这是MySQL自身的高可用解决方案,数据同步方法采用的是MySQL rep…...
C#登录后携带cookie爬取数据
前一段时间,公司以前的一个数据采集任务突然之间采集下来的数据都是0了,也就是未登录状态能够获取到的数据,于是猜想肯定是网站的服务升级了,升级了数据接口的逻辑,于是便开始解决此问题。 此采集程序是由.net core开…...
自动驾驶国家新一代人工智能开放创新平台产业化应用
【摘要】:当前,全球新一轮科技革命和产业变革正孕育兴起,自动驾驶作为人工智能最重要的应用载体之一,对于加快交通强国、智能汽车强国建设,具有十分突出的战略意义。我国自动驾驶研发应用,面临技术、资金、应用等诸多挑战,为此,需要打造一套符合我国国情的自动驾驶系统…...
Maven分模块-继承-聚合-私服的高级用法
Maven分模块-继承-聚合-私服的高级用法 JavaWeb知识,介绍Maven的高级用法!!! 文章目录 Maven分模块-继承-聚合-私服的高级用法1. 分模块设计与开发1.1 介绍1.2 实践1.2.1 分析1.2.2 实现 1.3 总结 2. 继承与聚合2.1 继承2.1.1 继承…...
Spring 是如何解决循环依赖问题的?
项目场景: 提示:这里简述项目相关背景: 例如:项目场景:示例:通过蓝牙芯片(HC-05)与手机 APP 通信,每隔 5s 传输一批传感器数据(不是很大) 问题描述 我们都知道,如果在代码中,将两个…...
Spring-2-深入理解Spring 注解依赖注入(DI):简化Java应用程序开发
今日目标 掌握纯注解开发依赖注入(DI)模式 学习使用纯注解进行第三方Bean注入 1 注解开发依赖注入(DI)【重点】 问题导入 思考:如何使用注解方式将Bean对象注入到类中 1.1 使用Autowired注解开启自动装配模式(按类型) Service public class StudentS…...
ffmpeg(四):滤镜命令
FFmpeg 的滤镜命令是用于音视频处理中的强大工具,可以完成剪裁、缩放、加水印、调色、合成、旋转、模糊、叠加字幕等复杂的操作。其核心语法格式一般如下: ffmpeg -i input.mp4 -vf "滤镜参数" output.mp4或者带音频滤镜: ffmpeg…...
Python爬虫(二):爬虫完整流程
爬虫完整流程详解(7大核心步骤实战技巧) 一、爬虫完整工作流程 以下是爬虫开发的完整流程,我将结合具体技术点和实战经验展开说明: 1. 目标分析与前期准备 网站技术分析: 使用浏览器开发者工具(F12&…...
DIY|Mac 搭建 ESP-IDF 开发环境及编译小智 AI
前一阵子在百度 AI 开发者大会上,看到基于小智 AI DIY 玩具的演示,感觉有点意思,想着自己也来试试。 如果只是想烧录现成的固件,乐鑫官方除了提供了 Windows 版本的 Flash 下载工具 之外,还提供了基于网页版的 ESP LA…...
python如何将word的doc另存为docx
将 DOCX 文件另存为 DOCX 格式(Python 实现) 在 Python 中,你可以使用 python-docx 库来操作 Word 文档。不过需要注意的是,.doc 是旧的 Word 格式,而 .docx 是新的基于 XML 的格式。python-docx 只能处理 .docx 格式…...
DBAPI如何优雅的获取单条数据
API如何优雅的获取单条数据 案例一 对于查询类API,查询的是单条数据,比如根据主键ID查询用户信息,sql如下: select id, name, age from user where id #{id}API默认返回的数据格式是多条的,如下: {&qu…...
laravel8+vue3.0+element-plus搭建方法
创建 laravel8 项目 composer create-project --prefer-dist laravel/laravel laravel8 8.* 安装 laravel/ui composer require laravel/ui 修改 package.json 文件 "devDependencies": {"vue/compiler-sfc": "^3.0.7","axios": …...
jmeter聚合报告中参数详解
sample、average、min、max、90%line、95%line,99%line、Error错误率、吞吐量Thoughput、KB/sec每秒传输的数据量 sample(样本数) 表示测试中发送的请求数量,即测试执行了多少次请求。 单位,以个或者次数表示。 示例:…...
适应性Java用于现代 API:REST、GraphQL 和事件驱动
在快速发展的软件开发领域,REST、GraphQL 和事件驱动架构等新的 API 标准对于构建可扩展、高效的系统至关重要。Java 在现代 API 方面以其在企业应用中的稳定性而闻名,不断适应这些现代范式的需求。随着不断发展的生态系统,Java 在现代 API 方…...
微服务通信安全:深入解析mTLS的原理与实践
🔥「炎码工坊」技术弹药已装填! 点击关注 → 解锁工业级干货【工具实测|项目避坑|源码燃烧指南】 一、引言:微服务时代的通信安全挑战 随着云原生和微服务架构的普及,服务间的通信安全成为系统设计的核心议题。传统的单体架构中&…...
若依登录用户名和密码加密
/*** 获取公钥:前端用来密码加密* return*/GetMapping("/getPublicKey")public RSAUtil.RSAKeyPair getPublicKey() {return RSAUtil.rsaKeyPair();}新建RSAUti.Java package com.ruoyi.common.utils;import org.apache.commons.codec.binary.Base64; im…...
