开发者社区> 小忽悠> 正文

温故知新——Spring AOP(二)

简介: 上一篇我们介绍Spring AOP的注解的配置,也叫做Java Config。今天我们看看比较传统的xml的方式如何配置AOP。整体的场景我们还是用原来的,“我穿上跑鞋”,“我要去跑步”。
+关注继续查看

上一篇我们介绍Spring AOP的注解的配置,也叫做Java Config。今天我们看看比较传统的xml的方式如何配置AOP。整体的场景我们还是用原来的,“我穿上跑鞋”,“我要去跑步”。Service层的代码我们不变,还是用原来的,如下:

@Service
public class MyService {
    public void gotorun() {
        System.out.println("我要去跑步!");
    }
}

再看看上一篇中的MyAspect代码,里边都是使用注解配置的,我们AOP相关的配置全部删除掉,只留下“我床上跑鞋“这样一个方法,如下:

public class MyAspect {
    public void putonshoes() {
        System.out.println("我穿上跑步鞋。");
    }
}

类中没有任何的注解,我们将全部通过xml的方式配置AOP。首先,我们要在xml中引入aop的schema,如下:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:aop="http://www.springframework.org/schema/aop"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd
       http://www.springframework.org/schema/aop
       https://www.springframework.org/schema/aop/spring-aop.xsd">

</beans>

有了aop的schema,我们就可以使用Spring的aop的标签了,我们先将MyAspect实例化,因为我们的通知方法”我穿上跑鞋“在这个类中,如下:

<bean id="myAspect" class="com.example.springaopdemo.aspect.MyAspect" />

其中,id我们配置为myAspect。然后,我们就要配置<aop:config>了,这个标签说明这是一段aop配置,具体的aop内容都在这个标签内,如下:

<aop:config proxy-target-class="true">
    ……
</aop:config>

其中,我们还可以配置proxy-target-class这个属性,还记得这个属性是什么意思吗?对了,它代表着是否使用CGLIB代理,由于我们项目引入的依赖是spring-boot-starter-aop,默认是使用CGLIB的,所以这里配置不配置都可以。

然后在里边我们配置切面<aop:aspect>,它标识着这是一个切面配置,在标签里还要指定我们的切面的bean,也就是myAspect,如下:

<aop:aspect id="aopAspect" ref="myAspect">
    ……
</aop:aspect>

切面的id叫做aopAspect,ref指定我们切面的bean,就是前面实例化的myAspect。好了,切面就配置好了,然后就是切点和通知。切点和通知的配置一定要在<aop:aspect>内,说明这个切点和通知属于当前这个切面的。

先来看看切点<aop:pointcut>的配置吧,如下:

<aop:pointcut id="pointcut" 
     expression="execution(* com.example.springaopdemo.service.*.*(..))">
</aop:pointcut>

是不是很熟悉,我们看到了匹配方法的表达式。同样,我们要给切点定义一个id叫做pointcut,然后expression就是匹配的表达式,这个和上一篇是一样的,没有区别。在这里,我们还是匹配service包下的所有类的所有方法。好了,到这里切点就配置完成了。

最后,再来看看通知,通知是和<aop:pointcut>并列的,都在<aop:aspect>内,具体如下:

<aop:before method="putonshoes" pointcut-ref="pointcut"></aop:before>

通知的5种类型,分别对应着5个不同的标签,在这里我们还是使用前置通知<aop:before>,在标签的内部,要指定它对应的切点,pointcut-ref="pointcut",切点我们指定前面配置的,id是pointcut。然后就要指定方法method了,这个方法是哪个类中的方法呢?还记得我们再配置<aop:aspect>时指定的bean吗?ref指定了myAspect,那么method指定的方法就是myAspect这个bean中的方法。这里我们配置putonshoes方法。

好了,到这里,aop的配置就全部配置完了,我们看一下全貌吧,

<bean id="myAspect" class="com.example.springaopdemo.aspect.MyAspect" />

<aop:config proxy-target-class="true">
    <aop:aspect id="aspect" ref="myAspect">
        <aop:pointcut id="pointcut" 
             expression="execution(* com.example.springaopdemo.service.*.*(..))">
        </aop:pointcut>
        <aop:before method="putonshoes" pointcut-ref="pointcut"></aop:before>
    </aop:aspect>
</aop:config>

最后,我们在SpringBoot的启动类中,使用@ImportResource("spring-aop.xml") 引入这个xml文件,如下:

@SpringBootApplication
@ImportResource("spring-aop.xml")
public class SpringAopDemoApplication {
    public static void main(String[] args) {
        SpringApplication.run(SpringAopDemoApplication.class, args);
    }
}

测试类的程序和上一篇是一致,没有变化,如下:

@SpringBootTest
class SpringAopDemoApplicationTests {
    @Autowired
    private MyService myService;

    @Test
    public void testAdvice() {
        myService.gotorun();
    }
}

运行一下看看结果,

我穿上跑步鞋。
我要去跑步!

没有问题,符合预期。

在上一篇中,我们可以使用简单的配置,也就是不配置切点,在通知中直接配置匹配表达式,如果忘记的同学可以翻一翻上一篇的内容。在xml的aop配置中,也是可以省略掉切点pointcut的配置的,我们在通知中,直接配置表达式,如下:

<aop:config proxy-target-class="true">
    <aop:aspect id="aspect" ref="myAspect">
        <aop:before method="putonshoes" 
             pointcut="execution(* com.example.springaopdemo.service.*.*(..))">
        </aop:before>
    </aop:aspect>
</aop:config>

是不是比前面的配置看起来清爽一些了。小伙伴们自己运行一下吧,结果是没有问题的。

好了,Spring AOP的Java Config和Schema-based 两种的方式的配置都介绍完了。我们拓展一下思维,Spring的事务管理也是AOP吧,在方法执行之前打开事务,在方法执行后提交事务。但是大家有没有留意,Spring的事务配置和咱们的AOP配置是不一样的,这是为什么呢?咱们下一篇再聊吧。

版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。

相关文章
【XML入门】一篇文章让你从没听过到熟练运用
今天我们继续来学习【Java Web】部分的XML,XML相比其他部分来时还是非常简单的。我们在以后写大项目时候也会经常用到,所以说还是蛮重要的。
6 0
SpringMVC面试题大总结
Spring MVC是一个基于Java的实现了MVC设计模式的请求驱动类型的轻量级Web框架,通过把Model,View,Controller分离,将web层进行职责解耦,把复杂的web应用分成逻辑清晰的几部分,简化开发,减少出错,方便组内开发人员之间的配合。
6 0
zookeeper技术分享
ZooKeeper是一个分布式的,开放源码的分布式应用程序协调服务,是Google的Chubby一个开源的实现。 ZooKeeper的目标就是封装好复杂易出错的关键服务,将简单易用的接口和性能高效、功能稳定的系统提供给用户。 ZooKeeper包含一个简单的原语集,提供Java和C的接口。 ZooKeeper代码版本中,提供了分布式独享锁、选举、队列的接口,代码在$zookeeper_home\src\recipes。其中分布锁和队列有Java和C两个版本,选举只有Java版本。
5 0
Android CheckedTextView 使用+实例
CheckedTextView是什么 主要XML属性 在点击事件里判断状态设置状态 第一次点击无效 实例 1.主界面CheckedTextViewActivity.java 2.主布局activity_textview_ctv.xml 3.复选框Adapter 4.复选框adapter对应布局 5.单选框adapter 6.单选框adapter对应布局 7.逻辑处理从adapter放在主界面处
8 0
Vue3 的 Reactive 响应式到底是什么
​Vue 3 除了令人钦佩的性能改进,还带来了一些新功能。可以说,最重要的介绍是 `Composition API` 。在本文的第一部分中,我们将概括 Vue3 创建新 API 的动机:即,更好的组织和重用代码。在第二部分中,我们将重点讨论使用新API时较少讨论的方面,例如响应式特性。我将响应式特性其称为按需响应。
10 0
Android 打包AAB+PAD(java篇)(下)
Play Core API 集成 安装时分发 快速跟进式分发和按需分发 查看状态 获取有关资源包的下载信息 安装 监控下载状态 下载内容较大 获取资源包 取消请求 移除资源包 获取多个资源包的位置 相关推荐 Android aab打包 Android App Bundle 已取代 APK
8 0
云服务器部署后台过程记录
现做毕业设计,使用前后端分离的设计模式,后端完成后为方便后续调用以及维护,将后端打包后部署到ECS云服务器上,在此介绍部署流程及一些问题。
5 0
微信小游戏开发实战15-关卡编辑器的制作以及关卡分享功能的实现
**微信小游戏开发实战系列的第15篇,点击上方的#微信小游戏开发实战话题可以查看本系列的所有内容。 本节主要内容有游戏中的关卡编辑器的实现思路以及如何利用分享功能将自己制作的关卡与好友分享。
4 0
阿里云ecs服务器使用体验
配置后端开发环境redis和mysql环境
4 0
iOS逆向 01:初识汇编
iOS逆向 01:初识汇编
5 0
+关注
小忽悠
在技术的海洋里遨游
82
文章
0
问答
文章排行榜
最热
最新
相关电子书
更多
OceanBase 入门到实战教程
立即下载
阿里云图数据库GDB,加速开启“图智”未来.ppt
立即下载
实时数仓Hologres技术实战一本通2.0版(下)
立即下载