`
jaesonchen
  • 浏览: 311654 次
  • 来自: ...
社区版块
存档分类
最新评论

Cglib动态代理(CallbackFilter)

 
阅读更多
import java.lang.reflect.Method;
import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;
import net.sf.cglib.proxy.Callback;
import net.sf.cglib.proxy.CallbackFilter;

public class BusinessCglibProxyFilter {

	private static Callback callback1 = new MethodInterceptor() {
		
		@Override  
		public Object intercept(Object obj, Method method, Object[] args,  
				MethodProxy proxy) throws Throwable {
			
			System.out.println("before callback1 ..");
			Object result = proxy.invokeSuper(obj, args);
			System.out.println("after callback1 ..");
			return result;  
		}  
	};

	private static Callback callback2 = new MethodInterceptor() {
		
		@Override  
		public Object intercept(Object obj, Method method, Object[] args,  
				MethodProxy proxy) throws Throwable {
			
			System.out.println("before callback2 ..");
			Object result = proxy.invokeSuper(obj, args);
			System.out.println("after callback2 ..");
			return result;  
		}  
	};
	
	private static CallbackFilter callbackFilter = new CallbackFilter() {  
		
		static final int EXECUTE_METHOD = 0;  
		static final int OTHER_METHOD = 1;  

		/* 
		 * accept需要返回一個int类型, 
		 * 该int类型为上文中setCallbacks设置的多个 
		 * Callback处理逻辑的数组的下标
		 */
		@Override  
		public int accept(Method method) {
			
			/* 
			 * Method参数代表代理类的执行方法,  
			 * 以下logic为 判断执行方法名称是否为execute, 
			 * 是则执行callback1,也就是数组下标为0的逻辑,  
			 * 否则执行Other逻辑 
			 */  
			if ("execute".equals(method.getName()))  
				return EXECUTE_METHOD;  
			else  
				return OTHER_METHOD;  
		}  
	};
	
	private BusinessCglibProxyFilter() { }

	//创建代理对象 
	public static Object getCglibProxy(Class<?> clazz) {
		
		//创建一个织入器 
		Enhancer enhancer = new Enhancer();
		//设置父类 
		enhancer.setSuperclass(clazz);  
		//设置需要织入的逻辑
		enhancer.setCallbacks(new Callback[] { callback1, callback2 });
		//设置回调方法过滤
		enhancer.setCallbackFilter(callbackFilter);
		// 创建代理对象  //使用织入器创建子类
		return enhancer.create();
	}
	
	//由于CGLIB可以不需要实现接口来实现动态代理,其原理是通过字节码生成类的一个子类来完成的,
	//那就有可能出现需要动态代理对象不存在一个无参构造函数,
	//那么CGLIB在生成子类并实例化时将会产生错误。
	//创建带参数的代理对象 
	public static Object getCglibProxy(Class<?> clazz, Class<?>[] args, Object[] argsValue) {
		
		//创建一个织入器 
		Enhancer enhancer = new Enhancer();
		//设置父类 
		enhancer.setSuperclass(clazz);  
		//设置需要织入的逻辑
		enhancer.setCallbacks(new Callback[] { callback1, callback2 });
		//设置回调方法过滤
		enhancer.setCallbackFilter(callbackFilter);
		// 创建带参数的代理对象  //使用织入器创建子类
		return enhancer.create(args, argsValue);
	}
	
	public static void main(String[] args) {
		BusinessImpl proxy = (BusinessImpl) BusinessCglibProxyFilter.getCglibProxy(BusinessImpl.class);
		proxy.service();
		proxy.execute();
		//带参数的业务类
		BusinessImpl proxy1 = (BusinessImpl) BusinessCglibProxyFilter.getCglibProxy(BusinessImpl.class, 
				new Class[] {String.class}, new Object[] {"jaesonchen"});
		proxy1.service();
		proxy1.execute();
	}
}

 

  * 在真实开发当中,在使用动态代理进行方法请求拦截时,可能会需要判断调用的方法然后决定拦截的逻辑,   

    也就是同一个代理类在调用不同的方法时拦截的逻辑都不相同,CGLIB提供了CallbackFilter来帮助我们

    实现这一功能。

 

输出为:

before callback2 ..
service.id = default
after callback2 ..
before callback1 ..
execute.id = default
after callback1 ..
before callback2 ..
service.id = jaesonchen
after callback2 ..
before callback1 ..
execute.id = jaesonchen
after callback1 ..

 

 

分享到:
评论

相关推荐

    cglib动态代理相关包

    CGlib是Java编程语言中的一个库,主要用于生成子类,以提供方法拦截和动态代理功能。它是对Bytecode Generation Library(字节码生成库)的一个封装,能够在运行时动态创建新类和对象,广泛应用于AOP(面向切面编程...

    基于Java的cglib库的动态代理测试项目.zip

    基于Java的cglib库的动态代理测试项目 项目概述 该项目主要用于测试和验证cglib库的动态代理功能。cglib是一个强大的Java库,用于生成和操作字节码,特别是在需要动态代理和AOP(面向切面编程)的场景中非常有用...

    cglib-2.2.jar

    CGLIB,全称为Code Generation Library,是一个强大的高性能的代码生成库,它被广泛应用于Java编程领域,尤其是在动态代理和AOP(面向切面编程)框架中。CGLIB是由Eclipse Birt项目开发并维护的一个开源项目,它通过...

    cglib-2.2.2.rar

    CGLib的核心功能是能够在运行时动态创建Java对象的子类,从而实现对目标类的方法拦截,这为实现动态代理提供了便利。在【标题】"cglib-2.2.2.rar"中提到的版本是CGLib的2.2.2版,这是一个稳定且成熟的版本。 CGLib...

    cglib-Root_RELEASE_2_2_3.zip

    CGlib,全称为Code Generation Library,是一个强大的Java代码生成库,广泛用于动态代理、AOP(面向切面编程)框架以及性能优化等场景。在Java世界中,它扮演着一个重要的角色,尤其对于那些需要在运行时动态创建类...

    cglibfull包

    CGLib(Code Generation Library)是一个强大的、高性能的代码生成库,它在Java世界中被广泛应用于动态代理、AOP(面向切面编程)以及ORM(对象关系映射)等领域。CGLib是基于ASM库实现的,能够对运行时的类进行字节...

    hibernate 常见异常

    `cglib-2.1.3.jar`是代码生成库,用于创建Java类的子类,这对于某些动态代理和AOP实现是必要的。如果没有它,可能会出现`net.sf.cglib.proxy.CallbackFilter`相关异常。 `commons-collections-3.1.jar`提供了Java...

Global site tag (gtag.js) - Google Analytics