其他分享
首页 > 其他分享> > Spring02:AOP

Spring02:AOP

作者:互联网

Spring02 AOP

面向切面编程

对业务逻辑的各个部分进行隔离

不通过修改源代码方式,在主干功能里面添加新功能

1.代理模式

1.1 静态代理

Client:客户

Proxy:代理角色 实现接口

Host:被代理角色 实现接口

Client通过Proxy调用某Host方法,Proxy可以增加功能

1.2 动态代理

代理类动态生成:

1.1 JDK动态代理

java.lang.reflect包提供Proxy类InvocationHandler接口,生成JDK动态代理类和动态代理对象。

定义MyInvocationHandler类,实现InvocationHandler接口

public class ProxyInvocationHandler implements InvocationHandler {

    //代理接口
    private Object target;

    public void setTarget(Object target) {
        this.target = target;
    }

    //生成代理类
    /*newProxyInstance方法
	第一参数,类加载器
	第二参数,增强方法所在的类,这个类实现的接口,支持多个接口 
	Class[] interfaces = {UserDao.class};
	第三参数,实现这个接口 InvocationHandler,创建代理对象,写增强的部分
	*/
    public Object getProxy(){
        return Proxy.newProxyInstance(this.getClass().getClassLoader(),target.getClass().getInterfaces(),this);
    }

    //处理代理实例
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        Object result = method.invoke(target,args);
        return result;
    }

}
//使用者
public class Client {
    public static void main(String[] args) {
        //被代理者
        Host host = new Host();
        //建立代理
        ProxyInvocationHandler p = new ProxyInvocationHandler();
        p.setTarget(host);
        //动态生成代理类
        Rent proxy = (Rent) p.getProxy();
        proxy.rent();
    }
}

1.2 CGLIB 动态代理

没有接口

创建子类的代理对象,增强类的方法

2.AOP

2.1 基本

2.2 AOP操作

基于 AspectJ 实现 AOP 操作:

引入依赖:

切入点表达式:对哪个类里面的哪个方法进行增强

execution([权限修饰符] [返回类型] [类全路径] [方法名称]([参数列表]) )
例 1:对 com.atguigu.dao.BookDao 类里面的 add 进行增强
execution(* com.atguigu.dao.BookDao.add(..))
例 2:对 com.atguigu.dao.BookDao 类里面的所有的方法进行增强
execution(* com.atguigu.dao.BookDao.* (..))
例 3:对 com.atguigu.dao 包里面所有类,类里面所有方法进行增强
execution(* com.atguigu.dao.*.* (..))

2.2.1 AspectJ 注解

1.创建类、增强类

2.开启注解扫描

<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:component-scan base-package="com.fremont.aop1"></context:component-scan>
    <!-- 开启 Aspect 生成代理对象-->
    <aop:aspectj-autoproxy></aop:aspectj-autoproxy>
</beans>

3.使用注解创建对象

增强类上面添加注解 @Aspect,添加通知类型注解,使用切入点表达式配置

public class UserProxy {

    //前置通知,切入到对应方法
    @Before(value = "execution(* com.fremont.aop1.User.add())")
    public void before() {
        System.out.println("before........");
    }

    //后置通知(返回通知)
    @AfterReturning(value = "execution(* com.fremont.aop1.User.add())")
    public void afterReturning() {
        System.out.println("afterReturning.........");
    }

    //最终通知
    @After(value = "execution(* com.fremont.aop1.User.add())")
    public void after() {
        System.out.println("after.........");
    }

    //异常通知
    @AfterThrowing(value = "execution(* com.fremont.aop1.User.add())")
    public void afterThrowing() {
        System.out.println("afterThrowing.........");
    }

    //环绕通知
    @Around(value = "execution(* com.fremont.aop1.User.add())")
    public void around(ProceedingJoinPoint proceedingJoinPoint) throws
            Throwable {
        System.out.println("环绕之前.........");
        //被增强的方法执行
        proceedingJoinPoint.proceed();
        System.out.println("环绕之后.........");
    }
}

相同切入点抽取:

@Pointcut(value = "execution(* com.fremont.aop1.User.add())")
public void point(){}
//使用
@Before(value = "point()")
public void before() {
 	System.out.println("before.........");
}

增强类优先级:

增强类上面添加注解 @Order(数字值),数字类型值越小优先级越高

4.完全注解开发

创建配置类

@Configuration
@ComponentScan(basePackages = {"com.fremont"})
@EnableAspectJAutoProxy(proxyTargetClass = true)
public class ConfigAop {
}

2.2.2 AspectJ 配置xml

创建类、配置xml:bean

配置切入点:

<!--配置 aop 增强-->
<aop:config>
    <!--切入点-->
    <aop:pointcut id="p" expression="execution(* com.fremont.aopxml.Book.buy(..))"/>
    <!--配置切面-->
    <aop:aspect ref="bookProxy">
        <!--增强作用在具体的方法上-->
        <aop:before method="before" pointcut-ref="p"/>
    </aop:aspect>
</aop:config>

标签:void,代理,Spring02,add,AOP,execution,com,public
来源: https://www.cnblogs.com/fremontxutheultimate/p/14801521.html