最近看到周围小伙伴面阿里被问到,想起去年的某黑历史项目。。。嘛,虽然讲AOP的文章满大街都是,我再加一篇好了。

哈? AOP?

假如用过Python,里面会有一个概念->装饰器,不过那个是装饰器模式,不要和代理模式混了(那你说个卵~)。装饰器模式原则上不会对原函数带来影响,而代理模式像是站在代理函数和调用者之前,具有完全的控制权。不过有一点是类似的,即面向切面的思想,比如说你要在某方法调用前打印日志,调用其他方法,甚至替换掉要执行的函数,都可以使用代理模式。

实现的分类

  • 静态代理: 没什么好说的,把代码写死罢了。或者说,在编译期决定了代理关系。
  • 动态代理: 在程序运行时,运用反射机制动态创建而成,也是这次主要讨论内容。

JDK实现动态代理

简明直观,上代码:

import java.lang.reflect.Proxy;

//定义一个Worker接口
interface WorkerImpl {
    String work();
}

//实现接口
class Worker implements WorkerImpl {
    @Override
    public String work() {
        System.out.println("I'm working....");
        return "test";
    }
}

public class Main {
    public static void main(String args[]) {

                //代理对象
        Worker worker = new Worker();

                //绑定代理
        WorkerImpl handler = (WorkerImpl) Proxy.newProxyInstance(worker.getClass().getClassLoader(), worker.getClass().getInterfaces(), (proxy, method, args1) -> {
            System.out.println("Before method....");

                        //执行原始函数
            Object back = method.invoke(worker, args1);

            System.out.println("After method....");
            return back;
        });

                //调用代理对象
        handler.work();
    }
}

cglib实现

教练,不想每次都传接口,感觉好麻烦。改bytecode吧=>左转找ASM,不过这里有个现成的方案 — 用 cglib ,Spring 等多个项目都是基于此。

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

import java.lang.reflect.Method;


class Worker {
    public String work() {
        System.out.println("I'm working....");
        return "test";
    }
}

class WorkerProxy implements MethodInterceptor {
    @Override
    public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
        System.out.println("Before method...");

        Object result = methodProxy.invokeSuper(o, objects);

        System.out.println("After method...");

        return result;
    }
}

public class Main {

    public static void main(String args[]) {
        Worker worker = new Worker();

        WorkerProxy proxyHandler = new WorkerProxy();

        Enhancer enhancer = new Enhancer();

        //设置代理目标
        enhancer.setSuperclass(worker.getClass());
        //设置回调
        enhancer.setCallback(proxyHandler);
        enhancer.setClassLoader(worker.getClass().getClassLoader());

        Worker proxy = (Worker) enhancer.create();

        proxy.work();
    }
}

于是呢

其实AOP思想也很简单,不过还是很实用的。于是又写了点废话,就当个人加强理解用吧orz。