JDK和CGLIB代理模式

1. 什么是代理模式

法官(调用者)→律师(代理对象)→被代理人(真实对象)
客户(调用)→外包公司(代理)→开发工程师(真实)
法官经过律师访问被代理人,那么调用者调用对象之前产生一个代理对象,而代理对象需要和真实对象建立代理关系(律师委托合同),所以代理分为以下两个步骤:
1.代理对象和真实对象建立代理关系(合同关系)
2.实现代理对象的代理逻辑方法(律师组织辩论/公司组织开发)

代理对象的作用:在真实对象被访问之前或者之后,加入对应的逻辑(大小事务包干,鞍前马后)

1.1 jdk动态代理

JDK自带的功能,必须使用接口,属于java.lang.reflect.*包下

  1. 依赖于接口实现,必须借助一个接口才能产生代理对象
  2. 建立代理关系,生成代理对象Proxy.newProxyInstance()
  3. 实现代理逻辑方法invoke()
    流程:
    1.定义接口和实现类
    2.代理逻辑类实现java.lang.reflect.InvocationHandler接口
	//定义接口
	public interface HelloWorld {
		public void sayHelloWorld();
	}
	
	//提供实现类
	public class HelloWorldImpl implements HelloWorld {
	@override
	public void sayHelloWorld() {
		sout("Hello World");
	}
	
	//开始动态代理
	//JDK中代理逻辑类需要实现InvocationHandler接口
	public class JdkProxyExample implements InvocationHandler {
		//真实对象
		private Object target = null;
		/**
		*step1:
		*建立代理对象和真实对象的代理关系,并返回代理对象
		*@return 代理对象
		*/
		public Object bind(Object target) {
			this.target = target;
			return Proxy.newProxyInstance(target.getClass().getClassLoader(), 
					target.getClass().getInterfaces(), this);
		}

		/**
		*step2:
		*代理逻辑方法
		*@param proxy 代理对象, method 当前调度方法, args 当前方法参数,
		*@return 代理结果返回
		*/
		@override
		public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
			sout("进入代理逻辑方法");
			sout("调用真实对象之前的服务");
			Object obj = method.invoke(target, args);//相当于调用sayHelloWorld()
			sout("调用真实对象之后的服务");
			return obj;
		}
	}

测试JDK动态代理

	public void testJdkProxy() {
		JdkProxyExample jdk = new JdkProxyExample();
		//因为挂在HelloWorld下,所以声明代理对象HelloWorld proxy
		HelloWorld proxy = (HelloWorld)jdk.bind(new HelloWorldImpl());
		//proxy已经是一个代理对象,会进入代理逻辑方法
		proxy.sayHelloWorld();
	}

1.2 cglib动态代理

不能提供接口的环境,则采用第三方技术,要求一个非抽象类(的被代理人)

  1. 实现MethodInterceptor接口
  2. 建立代理关系,生成代理对象Enhancer
  3. 实现代理逻辑方法inercept()
	public class ReflectServiceImpl {
	    public void sayHello(String name){
	        System.err.println("Hello " + name);
	    }
	}

	//开始动态代理
	public class CglibProxyExample implements MethodInterceptor {
		/**
		*step1: 建立代理关系
		*生成CGLIB代理对象
		*@param cls:非抽象类 真实对象
		*@return 类的CGLIB代理对象
		*/
		public Object getProxy(Class cls){
			//CGLIB enhancer增强类对象
			Enhancer enhancer = new Enhancer();
			//设置增强类型
			enhancer.setSuperclass(cls);
			//定义代理逻辑对象为当前对象,要求当前对象实现MethodInterceptor方法
			enhancer.setCallback(this);//该方法设置哪个类为代理类,则这个类就需要实现MethodIntercetor的intercept方法
			return enhancer.create();
		}

		/**
		*step2:代理逻辑方法
		*@param proxy 代理对象, args 方法参数, methodproxy方法代理
		*@return 代理逻辑返回
		*/
		@override
		public Object intercept(Object proxy, Method method, Object[] args, MethodProxy methodProxy) throws Throwable {
			sout("调用真实对象之前的服务");
			Object result = methodProxy.invoke(proxy, args);
			sout("调用真实对象之后的服务");
			return result;
		}
	}

测试CGLIB动态代理

	public void testCGLIBProxy() {
		CglibProxyExample cpe = new CglibProxyExample();
		ReflectServiceImpl obj = (ReflectServiceImpl ) cpe.getProxy(ReflectServiceImpl.class);
		obj.sayHello("hello, world");
	}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值