MvcUriComponentsBuilder 和 ControllerMethodInvocationInterceptor的解读
ControllerMethodInvocationInterceptor实现了CGLIB的MethodInterceptor,所以是CGLIB动态代理的方法拦截器,从命名来看是对Controller的方法做了争强。同时也实现了org.aopalliance.intercept.MethodInterceptor
private static class ControllerMethodInvocationInterceptor implements MethodInterceptor, org.aopalliance.intercept.MethodInterceptor, MvcUriComponentsBuilder.MethodInvocationInfo { private final Class<?> controllerType; @Nullable private Method controllerMethod; @Nullable private Object[] argumentValues; ControllerMethodInvocationInterceptor(Class<?> controllerType) { this.controllerType = controllerType; } @Nullable public Object intercept(Object obj, Method method, Object[] args, @Nullable MethodProxy proxy) { if (method.getName().equals("getControllerType")) { return this.controllerType; } else if (method.getName().equals("getControllerMethod")) { return this.controllerMethod; } else if (method.getName().equals("getArgumentValues")) { return this.argumentValues; } else if (ReflectionUtils.isObjectMethod(method)) { return ReflectionUtils.invokeMethod(method, obj, args); } else { this.controllerMethod = method; this.argumentValues = args; Class returnType = method.getReturnType(); try { return returnType == Void.TYPE ? null : returnType.cast(initProxy(returnType, this)); } catch (Throwable var7) { throw new IllegalStateException("Failed to create proxy for controller method return type: " + method, var7); } } } @Nullable public Object invoke(MethodInvocation inv) throws Throwable { return this.intercept(inv.getThis(), inv.getMethod(), inv.getArguments(), (MethodProxy)null); } public Class<?> getControllerType() { return this.controllerType; } public Method getControllerMethod() { Assert.state(this.controllerMethod != null, "Not initialized yet"); return this.controllerMethod; } public Object[] getArgumentValues() { Assert.state(this.argumentValues != null, "Not initialized yet"); return this.argumentValues; } private static <T> T initProxy(Class<?> controllerType, @Nullable MvcUriComponentsBuilder.ControllerMethodInvocationInterceptor interceptor) { interceptor = interceptor != null ? interceptor : new MvcUriComponentsBuilder.ControllerMethodInvocationInterceptor(controllerType); if (controllerType == Object.class) { return interceptor; } else if (controllerType.isInterface()) { ProxyFactory factory = new ProxyFactory(EmptyTargetSource.INSTANCE); factory.addInterface(controllerType); factory.addInterface(MvcUriComponentsBuilder.MethodInvocationInfo.class); factory.addAdvice(interceptor); return factory.getProxy(); } else { Enhancer enhancer = new Enhancer(); enhancer.setSuperclass(controllerType); enhancer.setInterfaces(new Class[]{MvcUriComponentsBuilder.MethodInvocationInfo.class}); enhancer.setNamingPolicy(SpringNamingPolicy.INSTANCE); enhancer.setCallbackType(MethodInterceptor.class); Class<?> proxyClass = enhancer.createClass(); Object proxy = null; if (MvcUriComponentsBuilder.objenesis.isWorthTrying()) { try { proxy = MvcUriComponentsBuilder.objenesis.newInstance(proxyClass, enhancer.getUseCache()); } catch (ObjenesisException var7) { MvcUriComponentsBuilder.logger.debug("Failed to create controller proxy, falling back on default constructor", var7); } } if (proxy == null) { try { proxy = ReflectionUtils.accessibleConstructor(proxyClass, new Class[0]).newInstance(); } catch (Throwable var6) { throw new IllegalStateException("Failed to create controller proxy or use default constructor", var6); } } ((Factory)proxy).setCallbacks(new Callback[]{interceptor}); return proxy; } } } public interface MethodInvocationInfo { Class<?> getControllerType(); Method getControllerMethod(); Object[] getArgumentValues(); }
参考文档: