@[TOC]

看Feign的源码一定要看这个类

RefectiveFeign是Feign的具体实现类,它可以生成动态代理对象

动态代理对象的创建

RefectiveFeign的newInstance()方法创建RPC动态代理的实例

RefectiveFeign的newInstance方法:

  @Override
  public <T> T newInstance(Target<T> target) {
    Map<String, MethodHandler> nameToHandler = targetToHandlersByName.apply(target);
    Map<Method, MethodHandler> methodToHandler = new LinkedHashMap<Method, MethodHandler>();
    List<DefaultMethodHandler> defaultMethodHandlers = new LinkedList<DefaultMethodHandler>();

    for (Method method : target.type().getMethods()) {
      if (method.getDeclaringClass() == Object.class) {
        continue;
      } else if(Util.isDefault(method)) {
        DefaultMethodHandler handler = new DefaultMethodHandler(method);
        defaultMethodHandlers.add(handler);
        methodToHandler.put(method, handler);
      } else {
        methodToHandler.put(method, nameToHandler.get(Feign.configKey(target.type(), method)));
      }
    }
    InvocationHandler handler = factory.create(target, methodToHandler);
    T proxy = (T) Proxy.newProxyInstance(target.type().getClassLoader(), new Class<?>[]{target.type()}, handler);

    for(DefaultMethodHandler defaultMethodHandler : defaultMethodHandlers) {
      defaultMethodHandler.bindTo(proxy);
    }
    return proxy;
  }
  1. 解析远程接口的方法,每个方法创建一个MethodHandler方法处理器,nameToHandler的key是方法名,value是方法对应的MethodHandler
  2. 创建methodToHandler,key是method,value是方法对应的MethodHandler
  3. 创建调用处理器InvocationHandler
  4. 通过调用Proxy.newProxyInstance()创建一个动态代理实例

方法解析器的创建

方法解析器的创建通过SynchronousMethodHandler的 create方法完成的,在此之前需要通过Contract调用parseAndValidatateMetadata方法返回方法元数据列表,默认Contract是用的Spring MVC的SpringMvcContract

public MethodHandler create(Target<?> target, MethodMetadata md,
                                RequestTemplate.Factory buildTemplateFromArgs,
                                Options options, Decoder decoder, ErrorDecoder errorDecoder) {
      return new SynchronousMethodHandler(target, client, retryer, requestInterceptors, logger,
                                          logLevel, md, buildTemplateFromArgs, options, decoder,
                                          errorDecoder, decode404, closeAfterDecode);
    }

调用处理器的创建

调用处理器的创建是通过InvocationHandlerFactory 的create方法,默认类是通过Default的create方法创建,也就是创建FeignInvocationHandler的实例。

static final class Default implements InvocationHandlerFactory {

    @Override
    public InvocationHandler create(Target target, Map<Method, MethodHandler> dispatch) {
      return new ReflectiveFeign.FeignInvocationHandler(target, dispatch);
    }
  }

总结

这篇文章主要对RefectiveFeign的newInstance()方法进行分析,newInstance()方法主要是创建RPC动态代理的实例,过程是先进行方法解析,针对每一个方法创建对应的方法处理器,然后创建调用处理器InvocationHandler,用到的类是默认是FeignInvocationHandler,然后通过java的JDK的Proxy.newProxyInstance方法来创建出一个动态的代理对象。协议解析类Contract调用的是springMVC的SpringMvcContract协议规则解析类,使用SpringMvcContract协议规则解析类对于开发人员来说不需要重新进行学习,降低了开发成本和维护程度,远程调用RPC的方法注解和服务端提供的方法注解保持一致。虽然feign有自己的默认协议规则,但是没有使用。