使用Jdk动态代理实现自定义拦截器

使用Jdk动态代理实现自定义拦截器

接口:

public interface IUser {
    public String getName();
}

实现类:

public class User implements IUser {
    private String name;

    public User(String name){
        this.name=name;
    }
    @Override
    public String getName () {
        return name;
    }
}

自定义拦截器接口:

public interface Interceptor {
     boolean before(Object proxy, Object target, Method method,Object []args);

     void around (Object proxy,Object target,Method method,Object []args);

     void after(Object proxy, Object target, Method method, Object []args);
}

拦截器实现类: (在调用方法前做了个简单的属性校验)

这里可以实现多个拦截器实现责任链模式,target的代理是proxy1,proxy1的代理是proxy2,proxy2的代理是proxy3,这样就可以实现顺序拦截(好处是可以再责任链上任意位置添加拦截,缺点是代理和反射太多性能不高)

public class MyInterceptor implements Interceptor {
    @Override
    public boolean before (Object proxy, Object target, Method method, Object[] args) {
        System.out.println("before");
        if (checkProperties(target))
            return true;
        return false;
    }

    @Override
    public void around (Object proxy, Object target, Method method, Object[] args) {
        System.out.println("around");
    }

    @Override
    public void after (Object proxy, Object target, Method method, Object[] args) {
        System.out.println("After");
    }

    private boolean checkProperties (Object object) {
        Field[] fields = object.getClass().getDeclaredFields();
        try {
            for (Field field : fields) {
                field.setAccessible(true);
                if (field.get(object).equals(""))
                    return false;
            }
        } catch (Exception e) {

        }
        return true;
    }
}

实现InvocationHandler:

流程如下:
流程图


public class MyInvocationHandler implements InvocationHandler {
    private Object target;
    private Class clazz;

    public MyInvocationHandler(Object t,Class c){
        this.target = t;
        this.clazz = c;
    }

    public static Object bind(Object target,Class clazz){
        return Proxy.newProxyInstance(target.getClass().getClassLoader(),target.getClass().getInterfaces(),new MyInvocationHandler(target,clazz));
    }

    @Override
    public Object invoke (Object proxy, Method method, Object[] args) throws Throwable {
        if(this.clazz==null)
            return method.invoke(target,args);
        Object result=null;
        Interceptor interceptor = (Interceptor) clazz.newInstance();
        if(interceptor.before(proxy,target,method,args)){
            result = method.invoke(target,args);
        }else{
            interceptor.around(proxy,target,method,args);
        }
        interceptor.after(proxy,target,method,args);
        return result;
    }
}

测试:

public class test {
    public static void main(String []args){
        IUser u = new User("");
        IUser proxy = (IUser)MyInvocationHandler.bind(u,MyInterceptor.class);
        proxy.getName();
    }
}

运行结果:

结果

Thanks!