浏览 3469 次
锁定老帖子 主题:动态代理Proxy的递归
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
|
|
---|---|
作者 | 正文 |
发表时间:2008-07-29
现在我写两个Handler来实现不同的切面功能: handler_1 和handler_2 看如下代码: 1 接口 public interface IService { void foo(); } 2 实现 public class ServiceImpl implements IService{ public void foo() { System.out.println("Business really goes here"); } } 3 切面 public class handler_1 implements InvocationHandler { private Object stub; public handler_1(Object stub) { this.stub = stub; } public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { Object result = null; System.out.println("before handler_1"); method.invoke(stub, args); System.out.println("after handler_1"); return result; } } public class handler_2 implements InvocationHandler { private Object stub; public handler_2(Object stub) { this.stub = stub; } public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { Object result = null; System.out.println("before handler_2"); method.invoke(stub, args); System.out.println("after handler_2"); return result; } } 4 客户代码 public static void main(String[] args) { // TODO code application logic here ServiceImpl si = new ServiceImpl(); handler_1 h1 = new handler_1(si); handler_2 h2 = new handler_2(si); Proxy p1 = (Proxy) Proxy.newProxyInstance(IService.class.getClassLoader(), new Class[]{IService.class}, h1); //利用得到的p1代理实例来获取第二个实例,并指定其处理程序为h2 @SuppressWarnings("static-access") Proxy p2 = (Proxy) p1.newProxyInstance(IService.class.getClassLoader(), new Class[]{IService.class}, h2); IService service_1 = (IService) p1; IService service_2 = (IService) p2; service_1.foo(); service_2.foo(); } Guess what,最终得到的这个p_2的动态代理实例到底采用的那个handler切面呢? 是h2的还是h1+h2的? 引用 init:
deps-jar: Compiling 1 source file to F:\aop\build\classes compile: run: before handler_1 Business really goes here after handler_1 before handler_2 Business really goes here after handler_2 成功生成(总时间:0 秒) 可以使用如下方法: 引用 IService service= (IService) Proxy.newProxyInstance(IService.class.getClassLoader(), new Class[]{IService.class}, h1);
IService service= (IService) Proxy.newProxyInstance(IService.class.getClassLoader(), new Class[]{IService.class}, service); 声明:ITeye文章版权属于作者,受法律保护。没有作者书面许可不得转载。
推荐链接
|
|
返回顶楼 | |
发表时间:2008-07-31
创意不错, 只是楼主的代码写错了, 没有达到初始目的.
这段是编译不过的. 引用 IService service= (IService) Proxy.newProxyInstance(IService.class.getClassLoader(), new Class[]{IService.class}, h1);
IService service= (IService) Proxy.newProxyInstance(IService.class.getClassLoader(), new Class[]{IService.class}, service); 楼主的main方法和下面的普通使用Proxy的过程是一样的, 所以, 你没有达到你想要的测试效果. public static void main(String[] args) { ServiceImpl si = new ServiceImpl(); handler_1 h1 = new handler_1(si); // 对 new ServiceImpl() 的代理 Proxy p1 = (Proxy) Proxy.newProxyInstance(IService.class.getClassLoader(), new Class[]{IService.class}, h1); IService service_1 = (IService) p1; service_1.foo(); handler_2 h2 = new handler_2(si); // 还是对 new ServiceImpl() 的代理, 而不是对一个被代理过的对象再次代理. Proxy p2 = (Proxy) Proxy .newProxyInstance(IService.class.getClassLoader(), new Class[]{IService.class}, h2); IService service_2 = (IService) p2; service_2.foo(); } 修改过的代码: public static void main(String[] args) { ServiceImpl si = new ServiceImpl(); handler_1 h1 = new handler_1(si); Proxy p1 = (Proxy) Proxy.newProxyInstance(IService.class.getClassLoader(), new Class[] { IService.class }, h1); IService service_1 = (IService) p1; service_1.foo(); // 一次普通的代理 System.out.println("----------"); handler_2 h2 = new handler_2(service_1); // 对代理生成的代理对象 进行再次代理 Proxy p2 = (Proxy) Proxy.newProxyInstance(IService.class.getClassLoader(), new Class[] { IService.class }, h2); IService service_2 = (IService) p2; service_2.foo(); // 代理 代理 } 测试结果如下: before handler_1 Business really goes here after handler_1 ---------- // 下面的结果比较搞. 不过也在情理之中. before handler_2 before handler_1 Business really goes here after handler_1 after handler_2 |
|
返回顶楼 | |
发表时间:2008-07-31
感谢兄弟纠正,其实俺最后的那段代码就是这个意思,并且是可以执行的。
所谓代理的代理就是如此 但是这样的解决方法比较粗糙,应用开发人员如果想要一次织入多个独立的advice不得不写多次重复的代码,而且执行顺序是写死后不能灵活配置的。所以我打算利用跟Servlet filter或者Spring中InterceptorChain相似的链模型来解决这个问题 代码稍后附上 |
|
返回顶楼 | |
发表时间:2008-08-01
准备直接利用org.aopalliance.intercept的MethodInterceptor
但是看不到源代码不知道里面具体是怎么实现有序列表的 |
|
返回顶楼 | |