java中的代理

代理分为两种:静态代理和动态代理
静态代理就不说了,基本上用不上,在SSM中也是动态代理

动态代理

目前我知道的动态代理分为两种:

  1. 基于JDK的动态代理:代理类和实体类要实现同一个接口
  2. 基于cglib的动态代理:代理类要继承实体类,第三方的

最后目的相同,代理实体类,做一些额外的工作

(1)基于JDK的动态代理

接口

public interface ForumService {

	void removeTopic(int topicId);

	void removeForum(int forumId);

}

实现类

public class ForumServiceImpl implements ForumService {

	public void removeTopic(int topicId) {
		System.out.println("模拟删除Topic记录:"+topicId);
	}

	public void removeForum(int forumId) {
		System.out.println("模拟删除Forum记录:"+forumId);
	}
}

代理类

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

public class JdkProxy implements InvocationHandler{

	private ForumService fs;//定义实体类实现的接口,要一致
	
	public JdkProxy(ForumService fs){  //构造方法,赋值给定义的接口变量
		this.fs = fs;
	}
	//方法名随便定义,需要在new的时候执行这个方法,
	public ForumService bind(){
		return (ForumService) Proxy.newProxyInstance(this.getClass().getClassLoader(), new Class[]{ForumService.class},this);
		//看英文应该也明白,代理.新的代理实例化(这个Class载入,new Class[]{共同实现的接口.class},this)
	}
	//下面才是最重要的,执行程序,Cross实现的接口是带有Handler的,这个是头部的意思,相当于在你执行你需要的方法之前需要先执行这个
	public Object invoke(Object arg0, Method method, Object[] obj2) throws Throwable {
		// TODO Auto-generated method stub
		if("removeForum".equals(method.getName())){  //看看你调用的方法是不是removeForum,是就代理执行,不是让它继续往下
			System.out.println("代理删除");
		}else{
			 method.invoke(fs,obj2); //这个是放过,让实体类自己去执行放过的方法
		}
		return null;  //这个就是个形式, method.invoke这个是决定是否继续往下的关键
	}
}


测试

public static void main(String[] args) {
		ForumService target = new ForumServiceImpl();
		ForumService f = new JdkProxy(target).bind();
		f.removeForum(20);
		f.removeTopic(30);

	}

在这里插入图片描述

(2)基于cglib的动态代理

要导入cglib.jar才行
实体类

public class ForumServiceImpl  {

	public void removeTopic(int topicId) {
		System.out.println("模拟删除Topic记录:"+topicId);
	}

	public void removeForum(int forumId) {
		System.out.println("模拟删除Forum记录:"+forumId);
	}
}

代理类

import java.lang.reflect.Method;

import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;

public class CglibProxy implements MethodInterceptor {
	private Enhancer enhancer = new Enhancer();

	public Object getProxy(Class clazz) {
		enhancer.setSuperclass(clazz);  //父类为clazz
		enhancer.setCallback(this); 
		return enhancer.create();   //创建父类
	}
//上面可以说是写死的,不像基于JDK的接口要换
//下面重点,,类带有Interceptor,就是拦截器类型的
	public Object intercept(Object obj, Method method, Object[] args,MethodProxy proxy) throws Throwable {
		if("removeForum".equals(method.getName())) {
			System.out.println("代理删除");			
		}else {
			return proxy.invokeSuper(obj, args);   //方法放行,记住是invokeSuper,不是invoke,
			//区别是一个是实体类,一个是实体类的子类,子类是我们创建的,方法放行后应该去实体类执行
		}
		return null;    //这个就是一个形式,主要是 proxy.invokeSuper决定放不放行
		
	}
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值