JDK的Proxy实现代理要求被代理的目标对象必须实现一个接口,而如果目标对象没有实现接口则不能使用Proxy来代理。不过我们也可以借助cglib来实现代理,这样目标对象不必实现接口.
要代理的对象:com.spring305.test.aopCglib.UserDao.java
- public class UserDao {
- private String name;
- public String getName() {
- return name;
- }
- public void setName(String name) {
- this.name = name;
- }
- public UserDao(String name) {
- this.name = name;
- }
- public UserDao() {
- // TODO Auto-generated constructor stub
- }
- public void print1() {
- System.out.println(UserDao.class.toString() + " print1()");
- }
- public void print2() {
- System.out.println(UserDao.class.toString() + " print2()");
- }
- }
com.spring305.test.aopCglib.CglibFactory.java
- import net.sf.cglib.proxy.Enhancer;
- import net.sf.cglib.proxy.MethodInterceptor;
- import net.sf.cglib.proxy.MethodProxy;
- import java.lang.reflect.Method;
- public class CglibFactory implements MethodInterceptor {
- private Object target;
- public Object createUserDao(Object target) {
- this.target = target;
- //用enhancer类来创建代理对象
- Enhancer enhancer = new Enhancer();
- //设置父类,即为目标类
- enhancer.setSuperclass(this.target.getClass());
- // cglib创建的代理对象,其实就是继承了要代理的目标类,然后对目标类中所有非final方法进行覆盖,但在覆盖方法时会添加一些拦截代码。
- // 注册回调器,回调下面intercept
- enhancer.setCallback(this);
- //返回创建的代理对象
- return enhancer.create();
- }
- @Override
- //参数依次代表:代理对象本身,被拦截到的方法,方法的参数,方法的代理对象
- //切面,指横切性关注点的抽象,与类相似,但是两者的关注点不同,类是对物体特征的抽象
- //连接点:指那些被拦截到的点,spring只支持方法类型的连接点
- //切入点:指我们要对连接点进行拦截的定义
- //通知:拦截到连接点后做的事情即为通知
- //Target,目标对象:代理的目标对象
- //织入:将aspectJ应用到target对象,并导致proxy对象创建的过程
- //引入:在不修改类代码前提下,引入可以在运行期为类动态地添加一些方法或者field
- public Object intercept(Object proxy, Method method, Object[] args,
- MethodProxy methodProxy) throws Throwable {//环绕通知
- UserDao udi = (UserDao) target;
- Object result = null;
- if (udi.getName() != null) {
- // 前置通知 advice()
- try {
- result = methodProxy.invoke(target, args);
- // 后置通知 afterAdvice()
- } catch (Exception e) {
- e.printStackTrace();
- // 例外通知 exceptionAdvice
- } finally {
- // 最终通知 finalyAdvice
- }
- }
- return result;
- }
- }
测试:
- @Test
- public void cglibTest(){
- CglibFactory test = new CglibFactory();
- //UserDao dao = (UserDao)test.createUserDao(new UserDao());
- UserDao dao = (UserDao)test.createUserDao(new UserDao("aa"));
- dao.print1();
- dao.print2();
- }