《动态代理模式》

动态代理模式

  1. 简介:通过反射创建出代理对象,再通过代理对象调用原方法,可以在这个过程中对目标方法进行增强,aop就是基于这个原理。在spring中动态代理有两种方式,jdk动态代理,和cglib动态代理。如果目标实现了接口,优先使用jdk动态代理。否则使用cglib动态代理,cglib动态代理通过在运行时动态生成目标类的子类,从而实现对目标方法的增强。
  2. jdk动态代理
  • 抽象角色
package com.dhr.study.springAop.jdk;

public interface Rent {

    void house();
}

  • 目标对象
package com.dhr.study.springAop.jdk;

public class RentImpl implements Rent {
    @Override
    public void house() {
        System.out.println("租房子");
    }

}

  • 创建代理对象
    通过Proxy.newProxyInstance()方法生成代理的对象
package com.dhr.study.springAop.jdk;

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

public class TestMain {

    public static void main(String[] args) throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {

        // jdk动态代理实现方式
        RentImpl rent = new RentImpl();
       // 1. new 一个InvocationHandler,实现invoke方法,用来对原始方法的增加
        InvocationHandler invocationHandler = (proxy, method, args1) -> {
            System.out.println("前面");
            Object invoke = method.invoke(rent, args1);
            System.out.println("后面");
            return invoke;
        };
        //2. Proxy.newProxyInstance创建代理对象, 第一个参数 原始累的classloader, 第二个参数 原始对象接口, 第三个参数 handler
        Rent proxy = (Rent)Proxy.newProxyInstance(rent.getClass().getClassLoader(), rent.getClass().getInterfaces(), invocationHandler);
        //3. 执行方法
        proxy.house();
    }
}

  • 执行结果
    在这里插入图片描述
  1. cglib动态代理
    通过Enhancer的create方法创建出代理对象
package com.dhr.study.springAop.cglib;

import com.dhr.study.springAop.jdk.Rent;
import com.dhr.study.springAop.jdk.RentImpl;
import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;

import java.lang.reflect.Method;

public class TestCglib {

    public static void main(String[] args) {
        //1. 创建原始对象
        RentImpl rent = new RentImpl();
        //2. 通过cglib动态创建代理对象
        Enhancer enhancer = new Enhancer();
        enhancer.setClassLoader(rent.getClass().getClassLoader());
        enhancer.setSuperclass(rent.getClass());
        //3. new MethodInterceptor实现intercept,在里面对方法增强
        MethodInterceptor methodInterceptor = new MethodInterceptor() {
            @Override
            public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
                System.out.println("前面");
                Object invoke = method.invoke(rent, objects);
                System.out.println("后面");
                return invoke;

            }
        };
        enhancer.setCallback(methodInterceptor);
        Rent o = (Rent)enhancer.create();
        o.house();
    }
}

  • 执行结果
    在这里插入图片描述
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值