Retrofit 源码解析

Retrofit 源码解析

Retrofit 是 okHttp 的包装类。网络请求都是 Okhttp 处理的。

1.初始化 Retrofit

# Retrofit
public Retrofit build() {
    if (baseUrl == null) {
       throw new IllegalStateException("Base URL required.");
    }
//如果没有设置 OkHttpClient ,会默认创建一个
    okhttp3.Call.Factory callFactory = this.callFactory;
    if (callFactory == null) {
      callFactory = new OkHttpClient();
    }
    List<CallAdapter.Factory> adapterFactories = new ArrayList<>(this.adapterFactories);
      //添加默认的 ExecutorCallAdapterFactory
 adapterFactories.add(Platform.get().defaultCallAdapterFactory(callbackExecutor));
      List<Converter.Factory> converterFactories = new ArrayList<>(this.converterFactories);
      return new Retrofit(callFactory, baseUrl, converterFactories, adapterFactories,
          callbackExecutor, validateEagerly);
    }

2.创建 Service 对象

public <T> T create(final Class<T> service) {
	   ...    
//动态代理
return (T) Proxy.newProxyInstance(service.getClassLoader(), new Class<?>[] { service },
        new InvocationHandler() {
          private final Platform platform = Platform.get();
			//调用 service 方法
    @Override public Object invoke(Object proxy, Method method, Object... args)
              throws Throwable {
            // If the method is a method from Object then defer to normal invocation.
            if (method.getDeclaringClass() == Object.class) {
              return method.invoke(this, args);
            }
            if (platform.isDefaultMethod(method)) {
              return platform.invokeDefaultMethod(method, service, proxy, args);
            }
            return loadMethodHandler(method).invoke(args);
          }
        });}

3.调用 SerVice 的方法

进行 动态代理调用 new InvocationHandler().invoke(). 最后实际调用的是 MethodHandler 的 invoke .
MethodHandler 初始化需要:Converter,CallAdapter,RequestFactory

 # MethodHandler 
 ##是 Service 内方法的实际处理
  MethodHandler loadMethodHandler(Method method) {
    MethodHandler handler;
    synchronized (methodHandlerCache) {
    	//method 是 Service 内部的方法
    	//methodHandlerCache = Map 
    	//以 method 为 key,在 map中查找,有就初始化,没有就创建
    	//即每个方法对应一个 MethodHandler
      handler = methodHandlerCache.get(method);
      if (handler == null) {
        handler = MethodHandler.create(this, method);
        methodHandlerCache.put(method, handler);
      }
    }
    return handler;
  }
    # MethodHandler 
   #初始化
    static MethodHandler create(Retrofit retrofit, Method method) {
    //先简单知道他们的功能,后面再详细看看
    
    //将Call 转换为别的类型,比如 Rxjava 中的 Observable
    CallAdapter<?> callAdapter = createCallAdapter(method, retrofit);
   ...
   //改变入参和返回值的类型。比如:GsonConverterFactory 中将入参改为 ResponseBody
      Converter<ResponseBody, ?> responseConverter =
        createResponseConverter(method, retrofit, responseType);
        //处理方法中的 注解和参数
    RequestFactory requestFactory = RequestFactoryParser.parse(method, responseType, retrofit);
    return new MethodHandler(retrofit.callFactory(), requestFactory, callAdapter,
        responseConverter);
  }
   # MethodHandler   
   private static CallAdapter<?> createCallAdapter(Method method, Retrofit retrofit) {
   ...
         return retrofit.callAdapter(returnType, annotations);
  ...
    }
    #MethodHandler.createCallAdapter-> Retrofit.callAdapter-> nextCallAdapter
    #Retrofit 
      public CallAdapter<?> nextCallAdapter(...) {
   		...
   		//可以看出来,它只会取第一个符合方法返回值的adapter
       for (int i = start, count = adapterFactories.size(); i < count; i++) {
      CallAdapter<?> adapter = adapterFactories.get(i).get(returnType, annotations, this);
      if (adapter != null) {
        return adapter;
      }
    }
  ...
  }
  
  	#CallAdapter.Factory.get()
  	//service内 方法的返回值
   if (getRawType(returnType) != Call.class) {
      return null;
    }
  
  ## Converter 的创建和 callAdapter 原理差不多
调用 handle.invoke
  #MethodHandler
  Object invoke(Object... args) {
    return callAdapter.adapt(
        new OkHttpCall<>(callFactory, requestFactory, args, responseConverter));
  }

实际调用的是, callAdapter.adapt()。但我们都知道,集体的请求逻辑肯定是 OkHttpCall 处理的。具体的看看 Retrofit 默认的 callAdapter 的内部实现。

 #Retrofit.Build.build
 //adapterFactories.add(Platform.get().defaultCallAdapterFactory(callbackExecutor));
 #Platform
  private static final Platform PLATFORM = findPlatform();

  static Platform get() {
    return PLATFORM;
  }
	//创建 Platform
  private static Platform findPlatform() {
    try {
         Class.forName("android.os.Build");
      if (Build.VERSION.SDK_INT != 0) {
        return new Android();
      }
    } catch (ClassNotFoundException ignored) {
    ...
  }
//初始化  默认的 CallAdapter.Factory 
static class Android extends Platform {
    @Override CallAdapter.Factory defaultCallAdapterFactory(Executor callbackExecutor) {
      //callbackExecutor 在 Retrofit.Build.build.callbackExecutor()添加线程池。
      如果没有添加,则是 MainThreadExecutor
      if (callbackExecutor == null) {
        callbackExecutor = new MainThreadExecutor();
      }
      return new ExecutorCallAdapterFactory(callbackExecutor);
    }

    static class MainThreadExecutor implements Executor {
      private final Handler handler = new Handler(Looper.getMainLooper());

      @Override public void execute(Runnable r) {
      //回到主线程
        handler.post(r);
      }
    }
  }

得到 CallAdapter

 #ExecutorCallAdapterFactory
  @Override
  public CallAdapter<Call<?>> get(Type returnType, Annotation[] annotations, Retrofit retrofit) {
   ...
    return new CallAdapter<Call<?>>() {
    ...
    //这就是 handle.invoke 实际调用的方法。返回值就是 Service 方法的返回值 Call
      @Override public <R> Call<R> adapt(Call<R> call) {
        return new ExecutorCallbackCall<>(callbackExecutor, call);
      }
    };
  }

执行 Call.enqueue()(当然也可以执行execute,这里只是举例)。

 #ExecutorCallAdapterFactory$ExecutorCallbackCall
	//callback 回调接口
  @Override public void enqueue(final Callback<T> callback) {
      delegate.enqueue(new Callback<T>() {
        @Override public void onResponse(final Call<T> call, final Response<T> response) {
        //如果调用了Retrofit.Build.build.callbackExecutor(),那么就是运行在在线程池中,
        //如果没有,callbackExecutor ==MainThreadExecutor。则在主线程中
          callbackExecutor.execute(new Runnable() {
            @Override public void run() {
              if (delegate.isCanceled()) {
                // Emulate OkHttp's behavior of throwing/delivering an IOException on cancelation
                callback.onFailure(call, new IOException("Canceled"));
              } else {
                callback.onResponse(call, response);
              }
            }
          });
        }

    @Override public void onFailure(final Call<T> call, final Throwable t) {
          callbackExecutor.execute(new Runnable() {
            @Override public void run() {
              callback.onFailure(call, t);
            }
          });
        }
      });
    }

回顾

  1. CallAdapter 可以指定 Service 方法的返回值。
  1. Converter 修改请求参数和响应值的类型。
  2. Retrofit 流程:
    • 初始化Retrofit。(CallAdapter,Converter)
    • 创建 Service 对象。 调用 Retrofit 的 create 方法,动态代理生成 Service 对象
    • 调用Service 方法。 初始化 MethodHandler,并调用 它的invoke 方法。接着调用 CallAdapter 的 adapt(),并返回 Call 类型。(这里只是指默认的处理方式)
    • Call.equeue() 实际调用 OkhttpCall 内部的方法。

注:从处理流程的角度,对源码进行分析。其中关于方法和参数的注解,没有分析。如果有兴趣,可以看看 RequestFactoryParser。

参考:https://segmentfault.com/a/1190000005638577#articleHeader5

你可能感兴趣的:(开源库)