快速了解Spring AOP的概念及使用

news2024/11/18 17:49:59

文章目录

  • 1. AOP概念
    • 1.1 什么是AOP?
    • 1.2 什么是Spring AOP?
  • 2. Spring AOP的使用
    • 2.1 引入Spring AOP依赖
    • 2.2 编写AOP程序
  • 3. Spring AOP详解
    • 3.1 Spring AOP核心概念
      • 1. 切点(Pointcut)
      • 2. 连接点(Join Point)
      • 3. 通知(Advice)
      • 4. 切面(Aspect)
    • 3.2 切⾯优先级 @Order

1. AOP概念

1.1 什么是AOP?

AOP全称Aspect Oriented Programming(⾯向切⾯编程),它和面向对象编程(OOP)是不同的,OOP是一种以对象为核心的编程思想,AOP是一种以切面为核心的编程思想
切面可以特指某一特定的问题,如日志记录、事务管理、安全性和错误处理等。
而AOP通过将横切关注点从应用程序的核心逻辑中分离出来,减少了代码冗余和复杂性。简单的来说,AOP就是一种思想,对某一类事情的集中处理。

1.2 什么是Spring AOP?

AOP是一种思想,那Spring AOP就是一种实现的方式,当然不是唯一的实现方式,还有AspectJ、CGLIB等。
当要进行网站用户是否登录判断,如图:
在这里插入图片描述
如果业务模块中只有一个业务,会有人说,这不是多此一举吗?是的,是多此一举,但是一个业务模块中往往会有着许多许多的业务,那么就可以看出来AOP的强大了,大大的降低代码的耦合性,并且会很好的维护。

2. Spring AOP的使用

直接介绍概念不免略显空洞,但Spring AOP使用起来却很简单,我们可以先使用一下,然后在介绍那令人头大的概念。

2.1 引入Spring AOP依赖

在创建项目时,无法自动引入Spring AOP依赖,只能手动复制到pom.xml文件中,如果你有代码可以直接复制,没有的话,也可以从Maven仓库中复制,直接搜索找到对应版本即可。
也可以复制我的:

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

2.2 编写AOP程序

切面类UserAspect.java:

package com.example.springaopdemo.aop;

import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;
@Aspect //告诉spring切面类
@Component
@Slf4j
public class UserAspect {
    //切点
    @Pointcut("execution(* com.example.springaopdemo.controller.UserController.*(..))")
    public void Pointcut(){

    }
    //前置通知
    @Before("Pointcut()")
    public void BeforeAdvice(){
        log.info("执行了前置通知");
    }
    //后置通知
    @After("Pointcut()")
    public void AfterAdvice(){
        log.info("执行了后置通知");
    }
    //环绕通知
    @Around("Pointcut()")
    public Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable {
        log.info("进入环绕通知");
        Object object = null;
        object = joinPoint.proceed();
        log.info("退出环绕通知");
        return object;
    }
}

业务类UserController.java:

package com.example.springaopdemo.controller;

import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RequestMapping("/user")
@RestController
@Slf4j
public class UserController {
    @RequestMapping("/sayHi")
    public String sayHi(){
        log.info("执行了sayHi方法  ");
        return "hi";
    }
    @RequestMapping("/sayHello")
    public String sayHello(){
        log.info("执行了sayHello方法  ");
        return "hello";
    }
}

参考业务类ArticleController.java:

package com.example.springaopdemo.controller;

import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
@RequestMapping("/art")
@Slf4j
public class ArticleController {
    @RequestMapping("/showArt")
    public String showArt(){
        log.info("执行了showArt方法");  
        return "100篇";
    }
}


访问user/sayHi:
在这里插入图片描述
访问user/sayHello:
在这里插入图片描述
访问art/showArt:
在这里插入图片描述
上面就是Spring AOP的简单使用,可以看到访问不同接口的结果不同,为什么前两个接口又可以调用切口类中的方法呢?那些注解的作用是什么?什么又是切口类?调用顺序为什么又是这样?下面慢慢介绍。

注解:

  1. @Aspect:告诉Spring这是一个切口类。
  2. @Pointcut:定义一个切点。里面的参数后面介绍。
  3. @Before:前置通知。目标方法前执行。
  4. @After:后置通知。目标方法后执行。
  5. @Around:环绕通知。在⽬标⽅法的前后都会被执⾏. 后⾯的表达式表⽰对哪些⽅法进⾏增强。

在这里插入图片描述

3. Spring AOP详解

3.1 Spring AOP核心概念

分为四部:

  1. 切点(Pointcut)。
  2. 连接点(Join Point)。
  3. 通知(Advice)。
  4. 切面(Aspect)。

其中切面中包括切点和通知。
切点包括连接点。

1. 切点(Pointcut)

在这里插入图片描述

切点又称切入点,里面定义了一组规则,告诉程序哪些方法需要进行功能增强。
使用@Pointcut注解,注解具有切点表达式,可以匹配访问修饰符,类,方法,参数等。
execution() 是最常⽤的切点表达式, ⽤来匹配⽅法, 语法为:

 execution(<访问修饰符> <返回类型> <包名.类名.⽅法(⽅法参数)> <异常>)

访问修饰符可以写public,也可以省略,也可以使用 * 替代,* 表示不做限制,也可以替代包,类,方法,参数,都表示任意的意思。
但是替代参数时,只能替代一个任意参数,而 . . 可以替代任意参数。
替代包时,也只能替代一层包,而 . . 可以替代任意层包。

这样就可以分析上面这段代码了,限制任意访问修饰符(省略了),* 任意返回类型,然后com.example.springaopdemo.controller包下的UserController类中的任意方法,任意参数可以调用这个切点。
这也就是,UserController类中的接口调用时,为和会打印了那些通知日志,而ArticleController类中的接口调用时没有的原因。

2. 连接点(Join Point)

满⾜切点表达式规则的⽅法, 就是连接点。也就是可以被AOP控制的⽅法
以程序举例, 所有 com.example.springaopdemo.controller.UserController 路径下的⽅法, 都是连接点。
连接点是满足切点表达式的方法,而切点可以看作所有连接点的集合。
比如:学校中,教数学的老师们,教数学就是切点表达式,教数学的老师都是一个连接点,教数学的所有老师就构成了切点。

3. 通知(Advice)

通知就是具体要做的工作,要统一解决的问题。在连接点处执行的代码逻辑,通知分为:

  1. 前置通知(Before):连接点方法执行前执行,一般没有返回值。
  2. 后置通知(After):连接点方法执行后执行,一般没有返回值。
  3. 环绕通知(Around):可以同时在方法调用前、调用后和返回时执行。有返回值。
  4. 返回通知(AfterReturning):在方法返回时执行。
  5. 异常通知(AfterThrowing):在方法抛出异常时执行。

所以上面接口调用时,打印的日志才是那种形式。
在AOP⾯向切⾯编程当中, 我们把这部分重复的代码逻辑抽取出来单独定义, 这部分代码就是通知的内容。

4. 切面(Aspect)

切面是一个普通的Java类,它包含了一个或多个通知方法。
切面通过使用Spring AOP的代理机制来将通知方法与目标对象的方法绑定在一起。
当目标对象的方法被调用时,相关的通知方法也会被执行。
切⾯(Aspect) = 切点(Pointcut) + 通知(Advice)

3.2 切⾯优先级 @Order

当一个项目中定义了多个切面类,并且多个多个切面类的多个切入点都匹配到同一个目标方法,那么多个切面类的通知方法执行顺序是什么样的呢?
创建两个新的切面类:
UserAspect2.java:

package com.example.springaopdemo.aop;

import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;
@Aspect //告诉spring切面类
@Component
@Slf4j
public class UserAspect2 {
    //切点
    @Pointcut("execution(* com.example.springaopdemo.controller.UserController.*(..))")
    public void Pointcut(){

    }
    @Before("Pointcut()")
    public void BeforeAdvice(){
        log.info("执行了前置通知->UserAspect2");
    }
    @After("Pointcut()")
    public void AfterAdvice(){
        log.info("执行了后置通知->UserAspect2");
    }
}

UserAspect3.java:

package com.example.springaopdemo.aop;

import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;
@Aspect //告诉spring切面类
@Component
@Slf4j
public class UserAspect3 {
    //切点
    @Pointcut("execution(* com.example.springaopdemo.controller.UserController.*(..))")
    public void Pointcut(){

    }
    @Before("Pointcut()")
    public void BeforeAdvice(){
        log.info("执行了前置通知->UserAspect3");
    }
    @After("Pointcut()")
    public void AfterAdvice(){
        log.info("执行了后置通知->UserAspect3");
    }
}

调用一个接口:
在这里插入图片描述
根据结果看出,执行顺序是按照类型排序:

@Before 通知:字⺟排名靠前的先执⾏。
@After 通知:字⺟排名靠前的后执⾏。

这样有时并无法满足我们的需要,是否可以更好的控制执行顺序?
那么,就需要用到**@Order**注解。
在这里插入图片描述
再次调用刚才的接口:
在这里插入图片描述
根据结果看出,@Order 注解标识的切⾯类, 执⾏顺序如下:

@Before 通知:数字越⼩先执⾏。
@After 通知:数字越⼤先执⾏。

在这里插入图片描述

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

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

相关文章

Linux系统编程 day06 进程间通信

进程间通信 1. 进程间通信的概念2. 匿名管道pipe3. 命名管道FIFO4. 内存映射区 1. 进程间通信的概念 在Linux的环境下&#xff0c;进程地址空间是相互独立的&#xff0c;每个进程有着各自不同的用户地址空间。一个进程不能访问另一个进程中的内容&#xff0c;要进行数据交换必…

[MySQL--基础]函数、约束

hello! 这里是欧_aita的频道。 今日语录:不管你觉得自己能做什么&#xff0c;或者你觉得你不能做什么&#xff0c;你都是对的。 祝福语&#xff1a;愿你的程序像太阳一样明亮&#xff0c;给世界带来温暖和光明。 大家可以在评论区畅所欲言&#xff0c;可以指出我的错误&#xf…

雷达公式实现(matlab)

雷达公式实现 代码来源&#xff1a;《雷达系统分析与设计(MATLAB版)(第三版)》 function [snr] radar_eq(pt,freq,g,sigma,b,nf,loss,range) % This program implements Eq.(1.63) %% Inputs:% pt——峰值功率&#xff0c;W% freq——雷达中心频率&#xff0c;Hz% g——天线…

Javaweb之Vue组件库Element之Form表单的详细解析

4.3.4 Form表单 4.3.4.1 组件演示 Form 表单&#xff1a;由输入框、选择器、单选框、多选框等控件组成&#xff0c;用以收集、校验、提交数据。 表单在我们前端的开发中使用的还是比较多的&#xff0c;接下来我们学习这个组件&#xff0c;与之前的流程一样&#xff0c;我们首…

AI 重构工业制造的故事 我们从大模型开始讲起

在数字化浪潮的推动下&#xff0c;工业制造领域正经历着一场前所未有的变革。人工智能&#xff08;AI&#xff09;作为这场变革的关键推动者之一&#xff0c;正以惊人的速度颠覆传统制造业。而大模型作为AI时代最先进的科技工具之一&#xff0c;或将成为引领这场变革的利器&…

零基础学Python第三天||写一个简单的程序

通过对四则运算的学习&#xff0c;已经初步接触了Python中内容&#xff0c;如果看官是零基础的学习者&#xff0c;可能有点迷惑了。难道敲几个命令&#xff0c;然后看到结果&#xff0c;就算编程了&#xff1f;这也不是那些能够自动运行的程序呀&#xff1f; 的确。到目前为止…

C语言错误处理之“非局部跳转<setjmp.h>头文件”

目录 前言 setjmp宏 longjmp函数 使用方法&#xff1a; 实例&#xff1a;测试setjmp与longjmp的使用 前言 通常情况下&#xff0c;函数会返回到它被调用的位置&#xff0c;我们无法使用goto语句改变它的返回的方向&#xff0c;因为goto语句只能跳转到同一函数内的某个标号…

数字档案馆档案咨询工作内容有哪些

档案咨询通常是指关于如何管理、存储、保护档案资料的问题。随着电子档案的日渐兴起&#xff0c;数字档案馆室的建设也是如火如荼&#xff0c;随之数字档案馆档案咨询的工作也逐渐增多。以下就是专久智能关于数字档案馆档案咨询工作内容有哪些的简要介绍&#xff1a; 1. 提供档…

软著项目推荐 深度学习动物识别 - 卷积神经网络 机器视觉 图像识别

文章目录 0 前言1 背景2 算法原理2.1 动物识别方法概况2.2 常用的网络模型2.2.1 B-CNN2.2.2 SSD 3 SSD动物目标检测流程4 实现效果5 部分相关代码5.1 数据预处理5.2 构建卷积神经网络5.3 tensorflow计算图可视化5.4 网络模型训练5.5 对猫狗图像进行2分类 6 最后 0 前言 &#…

【3D程序软件】SideFX与上海道宁一直为设计师提供程序化 3D动画和视觉效果工具,旨在创造高质量的电影效果

Houdini是一个 从头开始构建的程序系统 使艺术家能够自由工作 创建多次迭代 并与同事快速共享工作流程 Houdini FX为 视觉特效艺术家创作故事片 广告或视频游戏 凭借其基于程序节点的工作流程 Houdini FX可让 您更快地创建更多内容 从而缩短时间并 在所有创意任务中…

微信可以添加多少好友?

不知道有没有小伙伴好奇&#xff0c;微信到底可以添加多少好友&#xff1f;正好这个话题也上热搜了&#xff0c;我们就来了解一下。 有网友表示&#xff0c;自己的微信好友数量有10004个&#xff0c;已经不能再添加新的微信好友了。 一个微信号&#xff0c;可以添加的好友上限…

数字阅读用户规模持续增长 5.3亿人享受数字化阅读便利

近日,鲁迅长孙周令飞在接受采访时表示,自己“现在90%的时间刷视频,10%的时间看书”,引发网友热议。不少网友表示,鲁迅的孙子都花90%的时间刷视频,难怪现在没人看书了,其实这并不奇怪,也并不表明没人看书,而是读屏与读书并重的时代,纸质阅读与数字阅读共同构成了日常的阅读模式。…

51单片机项目(17)——基于51单片机的双机通信系统

1.功能设计 本次实现的功能如下&#xff1a; 发送端通过串口向接收端循环发送字符0~F&#xff0c;并且实时显示在数码管上 接收端通过串口接收数据&#xff0c;将接收到的数据实时显示在数码管上。 &#xff08;需要完整工程的移步至最后 包括发送端代码 接收端代码 仿真图…

脚本绑邦引流脚本拓客软件短视频获客直播间截流抖音快手小红书自动引流关注点赞私信评论截流涨粉

一、引流脚本是什么&#xff1f; 引流脚本是一种自动化的工具&#xff0c;可以帮助你在各​种短视频、​社交媒体平台上进行批量关注、点赞、私信、评论等操作&#xff0c;从而吸引更多的流量和粉丝。通过引流脚本&#xff0c;你可以自动化地执行各种操作&#xff0c;解放双手…

概要设计检查单、需求规格说明检查单

1、概要设计检查表 2、需求规格说明书检查表 概要&#xff08;结构&#xff09;设计检查表 工程名称 业主单位 承建单位 检查依据 1、设计方案、投标文件&#xff1b;2、合同&#xff1b;3、信息系统相关技术标准及安全规范&#xff1b; 检查类目 检查内容 检查…

智能优化算法应用:基于回溯搜索算法无线传感器网络(WSN)覆盖优化 - 附代码

智能优化算法应用&#xff1a;基于回溯搜索算法无线传感器网络(WSN)覆盖优化 - 附代码 文章目录 智能优化算法应用&#xff1a;基于回溯搜索算法无线传感器网络(WSN)覆盖优化 - 附代码1.无线传感网络节点模型2.覆盖数学模型及分析3.回溯搜索算法4.实验参数设定5.算法结果6.参考…

Helm3部署kubeview资源可视化工具

一、KubeView 介绍 KubeView 是一个 Kubernetes 集群可视化工具和可视化资源管理器。它提供了跨命名空间的 Kubernetes 对象的完整概述&#xff0c;以及它们如何通过直观的 UI 和资源对象相互连接。它允许用户在集群内部运行命令&#xff0c;并查看集群内部的资源使用情况、容器…

后端整合Swagger+Knife4j接口文档

后端整合SwaggerKnife4j接口文档 接口文档介绍 什么是接口文档&#xff1a;写接口信息的文档&#xff0c;条接口包括&#xff1a; 请求参数响应参数 错误码 接口地址接口名称请求类型请求格式备注 为什么需要接口文档 who用&#xff1f;后端提供&#xff0c;前后端都需要使用…

不同酿酒风格生产的葡萄酒有什么不同?

霞多丽适合大多数风格的葡萄酒制作&#xff0c;从干燥的静止葡萄酒&#xff0c;到起泡酒&#xff0c;再到甜美的晚收&#xff0c;甚至是植物酿酒。最广泛影响霞多丽葡萄酒最终结果的两个酿酒决定是是否使用乳酸发酵和用于葡萄酒的橡木影响程度。 通过乳酸发酵&#xff08;或MLF…