SpringAOP

AOP
AOP(Aspect Oriented Programming),即面向切面编程,可以说是OOP(Object Oriented Programming,面向对象编程)的补充和完善。
AOP技术恰恰相反,它利用一种称为“横切”的技术,剖解开封装的对象内部,并将那些影响了多个类的公共行为封装到一个可重用模块,并将其命名为“Aspect”,即切面。所谓“切面”,简单说就是那些与业务无关,却为业务模块所共同调用的逻辑或责任封装起来,便于减少系统的重复代码,降低模块之间的耦合度,并有利于未来的可操作性和可维护性。
AOP把软件系统分为两个部分:核心关注点和横切关注点。业务处理的主要流程是核心关注点,与之关系不大的部分是横切关注点。

名词解释
1.横切关注点:影响应用多处的功能(安全、事务、日志)
2.切面(aspect):类是对物体特征的抽象,切面就是对横切关注点的抽象。即切面是通知和切点的结合。通知和切点共同定义了切面的全部内容——它是什么,在何时和在何处完成其功能。
3.连接点(joinpoint):被拦截到的点,因为Spring只支持方法类型的连接点,其实就是方法和方法之间调用的过程。所以Spring中连接点指的就是被拦截到的方法,实际上连接点还可以是字段或者构造器。也即在应用执行过程中能够插入切面的一个点。。
4.切入点(pointcut):对连接点进行拦截的定义,指定一个通知将被引发的一些列连接点的集合。即如果说通知定义了切面的“什么”和“何时”的话,那么切点就定义了“何处”。因此,切点其实就是定义了需要执行在哪些连接点上执行通知。
5.通知(advice):切面的工作被称为通知,所谓通知指的就是指拦截到连接点之后要执行的代码,即切面是什么以及何时使用,通知分为前置、后置、异常、最终、环绕通知五类。
前置通知(Before):在目标方法被调用之前调用通知功能
后置通知(After):在目标方法完成之后调用通知,此时不会关心方法的输出是什么
返回通知(After-returning):在目标方法成功执行之后调用通知
异常通知(After-throwing):在目标方法抛出异常后调用通知
环绕通知(Around):通知包裹了被通知的方法,在被通知的方法调用之前和之后执行自定义的行为
后置通知和返回通知的区别:后置通知是不管方法是否有异常,都会执行该通知;而返回通知是方法正常结束时才会执行。
6.目标对象:代理的目标对象
7.引入(Introduction):引入允许我们向现有的类添加新方法或属性。
8.织入(Weaving):织入是把切面应用到目标对象并创建新的代理对象的过程。切面在指定的连接点被织入到目标对象中。在目标对象的生命周期中有很多个点可以进行织入:
编译期:切面在目标类编译时被织入。这种方式需要特殊的编译器。AspectJ的织入编译器就是以这种方式织入切面的。
类加载期:切面在目标类加载到JVM时被织入。这种方式需要特殊的类加载器,它可以在目标类被引入应用之前增强该目标类的字节码。 AspectJ 5的加载时织入就支持这种方式织入切面。
运行期:切面在应用运行的某个时刻被织入。一般情况下,在织入切面时,AOP容器会为目标对象动态的创建一个代理对象。Spring AOP就是以这种方式织入切面的。
注意:因为Spring基于动态代理,所以Spring只支持方法连接点。

1.导入依赖jar包

<!--springIoc的依赖包-->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context</artifactId>
      <version>5.2.0.RELEASE</version>
    </dependency>

    <!--AOP切面依赖包-->
    <dependency>
      <groupId>org.aspectj</groupId>
      <artifactId>aspectjrt</artifactId>
      <version>1.9.1</version>
    </dependency>
     <dependency>
      <groupId>org.aspectj</groupId>
      <artifactId>aspectjweaver</artifactId>
      <version>1.9.1</version>
    </dependency>

2.UserMapper.java

@Component
public class UserMapper {
    public void saveUser(){
        System.out.println("执行添加操作!");
    }
}

3.Transcation.java


@Component
@Aspect//定义它是一个切面
public class Transcation {
    @Pointcut("execution(* *.*.*(..))")
    public void abc(){

    }

    @After("abc()") //任意返回类型 任意包中的任意类中的任意方法的任意参数 或者括号里面:execution(* *.*.*(..))
    public void after(){
        System.out.println("我负责提交事务!");
    }

    @Before("abc()")
    public void before(){
        System.out.println("我会在之前执行!");
    }

    @Around("abc()")
    public void around(ProceedingJoinPoint pjp) throws Throwable {
        System.out.println("我是环绕之前...");
        pjp.proceed();
        System.out.println("我是环绕之后...");
    }

    @AfterReturning("abc()")
    public void afterReturn(){
        System.out.println("最终会被执行的");
    }

    @AfterThrowing("abc()")   //在方法抛出异常之后执行 如果try catch了,则不会执行
    public void afterThrow(){
        System.out.println("出异常了!");
    }
}

4.applicationContext.xml

<?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:context="http://www.springframework.org/schema/context"
       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/context
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/aop
        http://www.springframework.org/schema/aop/spring-aop.xsd">

    <context:annotation-config/>
    <context:component-scan base-package="advice,target"/>

    <!--AOP的自动扫描切面-->
    <aop:aspectj-autoproxy/>
</beans>

5.TestUserMapper.java

public class TestUserMapper {
    public static void main(String[] args) {
        ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
        UserMapper userMapper = applicationContext.getBean("userMapper", UserMapper.class);
        userMapper.saveUser();
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值