SpringAop动态代理和AspectJ静态代理

一、SpringAop动态代理(运行时增强)

SpringAop如何使用代理取决于代理的对象是否实现了接口,如果实现接口,则默认使用jdk动态代理,当然也可以让其强制使用cglib代理。如果没有实现了接口,则必须使用cglib代理。总之spring会自动在JDK动态代理和CGLIB之间进行转换转换。通过注解@EnableAspectJAutoProxy

1、jdk代理

java 复制代码
package com.example.springboottest.proxy;

public interface ProxyService {
    public abstract void targetMethod();
}
java 复制代码
package com.example.springboottest.proxy;

public class JdkProxyServiceImpl implements ProxyService {
    @Override
    public void targetMethod() {
        System.out.println("目标方法执行");
    }
}
java 复制代码
package com.example.springboottest.proxy;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

public class ProxyHandler implements InvocationHandler {

    private Object proxyObj;

    public ProxyHandler(Object proxyObj) {
        this.proxyObj = proxyObj;
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        Object returnParam = null;
        try{
            System.out.println("before前置通知");
            returnParam =  method.invoke(proxyObj,args);
            System.out.println("afterReturning返回通知");
        }catch (Exception e){
            System.out.println("afterThrowing异常通知");
        }finally {
            System.out.println("after后置通知");
        }
        return returnParam;
    }

    public static void main(String[] args) {
        ProxyService jdkProxyService = new JdkProxyServiceImpl();
        ProxyService proxyService = (ProxyService) Proxy.newProxyInstance(
                jdkProxyService.getClass().getClassLoader(),
                jdkProxyService.getClass().getInterfaces(),
                new ProxyHandler(jdkProxyService));
        proxyService.targetMethod();
    }
}

2、cglib代理

java 复制代码
package com.example.springboottest.proxy;

public class CglibServiceImpl {

    public void targetMethod(){
        System.out.println("目标方法执行");
    }
}
java 复制代码
package com.example.springboottest.proxy;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

public class ProxyHandler implements InvocationHandler {

    private Object proxyObj;

    public ProxyHandler(Object proxyObj) {
        this.proxyObj = proxyObj;
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        Object returnParam = null;
        try{
            System.out.println("before前置通知");
            returnParam =  method.invoke(proxyObj,args);
            System.out.println("afterReturning返回通知");
        }catch (Exception e){
            System.out.println("afterThrowing异常通知");
        }finally {
            System.out.println("after后置通知");
        }
        return returnParam;
    }

    public static void main(String[] args) {
        ProxyService jdkProxyService = new JdkProxyServiceImpl();
        ProxyService proxyService = (ProxyService) Proxy.newProxyInstance(
                jdkProxyService.getClass().getClassLoader(),
                jdkProxyService.getClass().getInterfaces(),
                new ProxyHandler(jdkProxyService));
        proxyService.targetMethod();
    }
}

二、Aspectj静态代理(编译时增强)

AspectJ的底层技术是静态代理 ,即用一种 AspectJ 支持的特定语言编写切面,通过一个命令来编译,生成一个新的 代理类,该代理类增强了业务类,这是在编译时增强,相对于上面的运行时增强,编译时增强的性能更好。

三、区别

  • 静态代理在编译期就确定了代理类,而动态代理需要靠反射机制动态生成代理类,即AspectJ在编译时就增强了目标对象,Spring AOP的动态代理则是在每次运行时动态的增强,生成AOP代理对象。
  • 生成代理对象的时机不同,相对来说AspectJ的静态代理方式具有更好的性能,但是AspectJ需要特定的编译器进行处理,而Spring AOP则无需特定的编译器处理。

baijiahao.baidu.com/s?id=174110...

相关推荐
布吉岛的石头7 小时前
微服务网关统一鉴权、限流、日志实战
java·spring·微服务
wxin_VXbishe9 小时前
springboot新能源车充电站管理系统小程序-计算机毕业设计源码29213
java·c++·spring boot·python·spring·django·php
代码漫谈9 小时前
一文学习 SpringBoot 的 application.yml 配置,基于 Spring Boot 3.2.x
java·spring boot·spring·配置文件
2301_7717172110 小时前
最近在刷牛客:使用Spring AOP实现性能监控时
java·后端·spring
手握风云-11 小时前
Spring AI:让大模型住进 Spring 生态(四)
java·后端·spring
敖正炀13 小时前
boot-boost 项目架构设计文档
spring boot·spring
ffqws_15 小时前
Spring @Transactional 注解详解:从入门到避坑
java·数据库·后端·spring
RuoyiOffice16 小时前
SpringBoot+Vue3 企业假期余额系统设计:账户、流水、预占、销假退回与到期清零全链路拆解
spring boot·后端·spring·vue·hr·企业管理软件·ruoyioffice
张小洛16 小时前
Spring 常用类深度剖析(工具篇 05):Assert:用断言代替 if-throw,代码更清爽
spring·log4j·参数校验·validate·assert·spring 常用类·代码简化
晚风_END1 天前
Linux|操作系统|最新版openzfs编译记录
linux·运维·服务器·数据库·spring·中间件·个人开发