JDK、CGLIB、Spring 三种实现代理的区别(三)Spring的ProxyFactory

转:https://blog.csdn.net/sunnycoco05/article/details/78901449

之前两篇文章中我们说到了JDK proxy和CGLIB实现动态代理的方式,这回说说Spring的方式。Spring中代理对象可通过xml配置方式获得,也可通过ProxyFactory手动编程方式创建对象。我们主要讲手动编程的方式。Spring中的代理对象其实是JDK Proxy和CGLIB Proxy 的结合。


下面我们使用ProxyFactory的方式创建代理对象,顺便看看和JDK的proxy以及CGLIB中的proxy联系。
还是使用前两节中的例子。创建需要代理的类(MyTarget)、接口(PeopleService)及其实现(EnglishService),分别看看对接口和类的代理:

public class MyTarget {
    public void printName() {
        System.err.println("name:Target-");
    }
}

 

public interface PeopleService {
    public void sayHello();

    public void printName(String name);
}

 

public class EnglishService implements PeopleService {
    @Override
    public void sayHello() {
        System.err.println("Hi~");
    }

    @Override
    public void printName(String name) {
        System.err.println("Your name:" + name);
    }
}

 

下面创建一个MethodInterceptor实现方法调用的前后拦截,这里的拦截只是进行简单的打印信息。
这里需要用到额外的包 aopalliance.jar和aspectjweaver。(这里的MethodInterceptor 对比cglib)

import org.aopalliance.intercept.MethodInterceptor;

import org.aopalliance.intercept.MethodInvocation;

public class AroundInteceptor implements MethodInterceptor {

    @Override
    public Object invoke(MethodInvocation invocation) throws Throwable {
        System.err.println(invocation.getMethod().getName() + "调用之前");
        Object res = invocation.proceed();
        System.err.println(invocation.getMethod().getName() + "调用之后");
        return res;
    }
}

使用Spring aop包中的ProxyFactory创建代理,并通过addAdvice
增加一个环绕方式的拦截:

package com.spring;

import org.springframework.aop.framework.ProxyFactory;
import org.testng.annotations.Test;

import com.cglib.MyTarget;
import com.proxy.api.PeopleService;
import com.proxy.impl.EnglishService;
import com.spring.aop.AroundInteceptor;

public class ProxyFactoryTest {
    @Test
    public void classProxy() {
        //代理对象未指定接口,使用CGLIB生成代理类
        ProxyFactory factory = new ProxyFactory();
        factory.setTarget(new MyTarget());
        factory.addAdvice(new AroundInteceptor());
        MyTarget targetProxy = (MyTarget) factory.getProxy();
        targetProxy.printName();
        System.err.println(targetProxy.getClass().getName());
    }

    @Test
    public void interfaceProxy() {
        //代理对象指定接口PeopleService,目标类为实现PeopleService的EnglishService,使用JDK proxy生成代理类
        ProxyFactory factory = new ProxyFactory();
        factory.setInterfaces(new Class[] { PeopleService.class });
        factory.addAdvice(new AroundInteceptor());
        factory.setTarget(new EnglishService());
        PeopleService peopleProxy = (PeopleService) factory.getProxy();
        peopleProxy.sayHello();
        System.err.println(peopleProxy.getClass().getName());
    }
}

运行结果分别为:

 

 

 

 

posted @ 2020-11-15 20:41  不死码农  阅读(377)  评论(0编辑  收藏  举报