美文网首页
撸Retrofit2源码

撸Retrofit2源码

作者: zhujiaqqq | 来源:发表于2019-11-21 16:02 被阅读0次

    本文使用Retrofit-2.6.2源码

    切入点:

    • retrofit对象构造

    • new Retrofit.Builder()
                      .baseUrl(Constants.BASE_URL)
                      .client(getOkHttpClient())
                      .addConverterFactory(GsonConverterFactory.create())
                      .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
                      .build();
      
    • 调用请求接口retrofit.create(final Class<T> service)


    Retrofit对象构造

    Retrofit对象构造使用的是构造者模式,主要看retrofit2.Retrofit.Builder类:

    public static final class Builder {
        private final Platform platform;
        private @Nullable okhttp3.Call.Factory callFactory;
        private @Nullable HttpUrl baseUrl;
        private final List<Converter.Factory> converterFactories = new ArrayList<>();
        private final List<CallAdapter.Factory> callAdapterFactories = new ArrayList<>();
        private @Nullable Executor callbackExecutor;
        private boolean validateEagerly;
            ...
      }
    

    Builder主要构造的几个成员变量:

    • platform:Android平台还是非Android平台(Java8)
    • callFactory:实现newCall方法的类,一般是OkHttpClient
    • baseUrl:hostUrl
    • converterFactories:对网络请求对响应进行转化
    • callAdapterFactories;对请求的封装
    • callbackExecutor:Android平台下默认为主线程handler执行
    • validateEagerly:默认为false,为true的时候提前加载请求方法

    retrofit.create()

    整个Retrofit的使用就是从create方法开始的:

      public <T> T create(final Class<T> service) {
        // 1 监测service请求接口是不是有效的
        Utils.validateServiceInterface(service);
        if (validateEagerly) {
          // 2 如果validateEagerly=true,那么预加载请求的方法
          eagerlyValidateMethods(service);
        }
        //3 使用动态代理处理service请求接口
        return (T) Proxy.newProxyInstance(service.getClassLoader(), new Class<?>[] { service },
            new InvocationHandler() {
              private final Platform platform = Platform.get();
              private final Object[] emptyArgs = new Object[0];
    
              @Override public @Nullable Object invoke(Object proxy, Method method,
                  @Nullable 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 loadServiceMethod(method).invoke(args != null ? args : emptyArgs);
              }
            });
      }
    
    1. 注释1处,监测service请求接口是不是有效的:

      • 条件一:service类是一个接口

      • 条件二:service接口中不包含其他子接口

        则认为有效,否则直接抛异常

        static <T> void validateServiceInterface(Class<T> service) {
          if (!service.isInterface()) {
           //如果不是接口直接抛出异常
            throw new IllegalArgumentException("API declarations must be interfaces.");
          }
       
          if (service.getInterfaces().length > 0) {
          // 如果service中包含其他子接口,抛出异常
            throw new IllegalArgumentException("API interfaces must not extend other interfaces.");
          }
        }
      
    1. 注释2处,如果validateEagerly=true,那么预加载请求的方法(默认validateEagerly=false,不会执行这个方法):

        private void eagerlyValidateMethods(Class<?> service) {
          //获取当前的平台,Android端开发的时候是Android()
          Platform platform = Platform.get();
          //遍历接口中的所有方法,挑选不是默认、静态的方法
          for (Method method : service.getDeclaredMethods()) {
            if (!platform.isDefaultMethod(method) && !Modifier.isStatic(method.getModifiers())) {
              // 将挑选出的方法进行包装,加入缓存
              loadServiceMethod(method);
            }
          }
        }
      
    2. 注释3处,使用动态代理处理service请求接口,在动态代理的invoke()方法中实现了请求接口的封装:

      @Override public @Nullable Object invoke(Object proxy, Method method,
                    @Nullable Object[] args) throws Throwable {
      // If the method is a method from Object then defer to normal invocation.
      if (method.getDeclaringClass() == Object.class) {
        // 如果这个方法是继承自object,那么这个方法不做处理,直接返回被代理的方法
       return method.invoke(this, args);
      }
      if (platform.isDefaultMethod(method)) {
       // 默认方法只会在Java8中出现,Android平台上直接会抛异常
       return platform.invokeDefaultMethod(method, service, proxy, args);
      }
        // 4 这里将请求进行封装、加入缓存,最后invoke调用
      return loadServiceMethod(method).invoke(args != null ? args : emptyArgs);
      }
      
       
    4. 注释4处,将请求进行封装、加入缓存,最后invoke调用:
    
       ```java
         ServiceMethod<?> loadServiceMethod(Method method) {
           // 在缓存中获取请求方法,如果存在直接返回
           ServiceMethod<?> result = serviceMethodCache.get(method);
           if (result != null) return result;
       
           synchronized (serviceMethodCache) {
             result = serviceMethodCache.get(method);
             if (result == null) {
               // 5 将请求方法进行封装得到一个ServiceMethod对象
               result = ServiceMethod.parseAnnotations(this, method);
               serviceMethodCache.put(method, result);
             }
           }
           return result;
         }
    
    1. 注释5处,通过ServiceMethod的静态方法parseAnnotations()将请求方法进行封装得到一个ServiceMethod对象:

        static <T> ServiceMethod<T> parseAnnotations(Retrofit retrofit, Method method) {
          // 将请求方法的注解、参数、参数的注解等提取并生成requestFactory对象
          RequestFactory requestFactory = RequestFactory.parseAnnotations(retrofit, method);
           // 获取请求方法的返回类型
          Type returnType = method.getGenericReturnType();
          if (Utils.hasUnresolvableType(returnType)) {
            // 如果是不是一个Class的类型或者不是参数化的Class类型,你就抛出异常
            throw methodError(method,
                "Method return type must not include a type variable or wildcard: %s", returnType);
          }
          if (returnType == void.class) {
            // 如果返回类型为空,抛出异常
            throw methodError(method, "Service methods cannot return void.");
          }
      
          return HttpServiceMethod.parseAnnotations(retrofit, method, requestFactory);
        }
      

      parseAnnotations()的RequestFactory requestFactory = RequestFactory.parseAnnotations(retrofit, method);这句话将请求方法的注解、参数、参数的注解等提取并生成requestFactory对象:

        static RequestFactory parseAnnotations(Retrofit retrofit, Method method) {
          return new Builder(retrofit, method).build();
        }
        
            RequestFactory build() {
            for (Annotation annotation : methodAnnotations) {
            // 这里解析请求方法的注解:请求类型、是否有请求体、请求的url、请求头
              parseMethodAnnotation(annotation);
            }
               ...
            int parameterCount = parameterAnnotationsArray.length;
            parameterHandlers = new ParameterHandler<?>[parameterCount];
              // 逐一解析参数
            for (int p = 0, lastParameter = parameterCount - 1; p < parameterCount; p++) {
              parameterHandlers[p] =
                  parseParameter(p, parameterTypes[p], parameterAnnotationsArray[p], p == lastParameter);
            }
               ...
            return new RequestFactory(this);
          }
      

      到此,完成了请求方法的request部分的封装。但是ServiceMethod对象还缺少返回参数的封装,所有ServiceMethod.parseAnnotations()方法最终调用return HttpServiceMethod.parseAnnotations(retrofit, method, requestFactory);做后续处理,返回一个完整的ServiceMethod对象。

        static <ResponseT, ReturnT> HttpServiceMethod<ResponseT, ReturnT> parseAnnotations(
            Retrofit retrofit, Method method, RequestFactory requestFactory) {
           // 6 获取请求方法的返回类型
          adapterType = method.getGenericReturnType();
           // 7 通过方法的返回类型去创建callAdapter
          CallAdapter<ResponseT, ReturnT> callAdapter =
              createCallAdapter(retrofit, method, adapterType, annotations);
          // 8 响应的类型
          Type responseType = callAdapter.responseType();
           // 9 构建响应的转换器
          Converter<ResponseBody, ResponseT> responseConverter =
              createResponseConverter(retrofit, method, responseType);
      
          okhttp3.Call.Factory callFactory = retrofit.callFactory;
      
          return new CallAdapted<>(requestFactory, callFactory, responseConverter, callAdapter);
        }
      

      注释6处,获取请求方法的返回类型,一般情况下是:Call<xxxBean>Observable<xxxBean>这样的封装类型。通过这个返回类型,注释7处得到了callAdapter:

        private static <ResponseT, ReturnT> CallAdapter<ResponseT, ReturnT> createCallAdapter(
            Retrofit retrofit, Method method, Type returnType, Annotation[] annotations) {
           return (CallAdapter<ResponseT, ReturnT>) retrofit.callAdapter(returnType, annotations);
        }
      
      

      这里调用哦那个retrofit类的callAdapter()方法:

        public CallAdapter<?, ?> callAdapter(Type returnType, Annotation[] annotations) {
           // 调用nextCallAdapter()方法
          return nextCallAdapter(null, returnType, annotations);
        }
        public CallAdapter<?, ?> nextCallAdapter(@Nullable CallAdapter.Factory skipPast, Type returnType,
            Annotation[] annotations) {
          int start = callAdapterFactories.indexOf(skipPast) + 1;
          for (int i = start, count = callAdapterFactories.size(); i < count; i++) {
            // 遍历callAdapterFactories找到合适的callAdapter返回
            CallAdapter<?, ?> adapter = callAdapterFactories.get(i).get(returnType, annotations, this);
            if (adapter != null) {
              return adapter;
            }
          }
        }
      

      callAdapterFactories.get(i).get(returnType, annotations, this)因为callAdapterFactories中可能有多个Factory,且它们的实现都不一样,一下对比两个:

      • DefaultCallAdapterFactory.class

         @Override public @Nullable CallAdapter<?, ?> get(
             Type returnType, Annotation[] annotations, Retrofit retrofit) {
           if (getRawType(returnType) != Call.class) {
             return null;
           }
           final Type responseType = Utils.getParameterUpperBound(0, (ParameterizedType) returnType);
        
          return new CallAdapter<Object, Call<?>>() {
             @Override public Type responseType() {
               return responseType;
             }
            @Override public Call<Object> adapt(Call<Object> call) {
               return executor == null
                   ? call
                   : new ExecutorCallbackCall<>(executor, call);
             }
          };
         }
        

        如果返回类型不是Call的包装类型,那么直接返回null。

      • CompletableFutureCallAdapterFactory.class (Java8)

          @Override public @Nullable CallAdapter<?, ?> get(
              Type returnType, Annotation[] annotations, Retrofit retrofit) {
            if (getRawType(returnType) != CompletableFuture.class) {
              return null;
            }
          
            Type innerType = getParameterUpperBound(0, (ParameterizedType) returnType);
            if (getRawType(innerType) != Response.class) {
              // Generic type is not Response<T>. Use it for body-only adapter.
              return new BodyCallAdapter<>(innerType);
            }
            Type responseType = getParameterUpperBound(0, (ParameterizedType) innerType);
            return new ResponseCallAdapter<>(responseType);
          }
        

        如果返回类型的被包装类不是CompletableFuture,那么直接返回null

      最终从callAdapterFactories筛选出合适的Fractory。

      注释8处,获取响应的类型:

      return Utils.getParameterUpperBound(index, type);
      

      注释9处,构建响应的转换器:

        private static <ResponseT> Converter<ResponseBody, ResponseT> createResponseConverter(
            Retrofit retrofit, Method method, Type responseType) {
          Annotation[] annotations = method.getAnnotations();
          return retrofit.responseBodyConverter(responseType, annotations);
        }
      

      使用的retrofit的responseBodyConverter()方法:

        public <T> Converter<ResponseBody, T> responseBodyConverter(Type type, Annotation[] annotations) {
          return nextResponseBodyConverter(null, type, annotations);
        }
      
        public <T> Converter<ResponseBody, T> nextResponseBodyConverter(
            @Nullable Converter.Factory skipPast, Type type, Annotation[] annotations) {
          checkNotNull(type, "type == null");
          checkNotNull(annotations, "annotations == null");
      
          int start = converterFactories.indexOf(skipPast) + 1;
          for (int i = start, count = converterFactories.size(); i < count; i++) {
            Converter<ResponseBody, ?> converter =
                converterFactories.get(i).responseBodyConverter(type, annotations, this);
            if (converter != null) {
              //noinspection unchecked
              return (Converter<ResponseBody, T>) converter;
            }
          }
        }
      

      responseBodyConverter()方法调用了nextResponseBodyConverter()方法,与之前callAdapter的创建类似,也是从factories中获取合适的Factory然后创建出converter对象。

      最终通过responseConverter 、callAdapter、入参传入的requestFactory以及retrofit.callFactory构造出请求方法独有的HttpServiceMethod对象。

      至此,请求方法的封装过程已经完毕。


      请求调用:ServiceMethod.invoke()

      ServiceMethod是一个抽象类,invoke()方法的实现在它的子类HttpServiceMethod中:

        @Override final @Nullable ReturnT invoke(Object[] args) {
          Call<ResponseT> call = new OkHttpCall<>(requestFactory, args, callFactory, responseConverter);
          return adapt(call, args);
        }
      
        protected abstract @Nullable ReturnT adapt(Call<ResponseT> call, Object[] args);
      

      从上面创建HttpServiceMethod的代码可以看出,HttpServiceMethod的实现类为CallAdapted,所以adapt()也是在CallAdapted中实现的:

          @Override protected ReturnT adapt(Call<ResponseT> call, Object[] args) {
            return callAdapter.adapt(call);
          }
      

      adapt的最终实现有回到了HttpServiceMethod对象的成员变量callAdapter的adapt()方法中了,callAdapter

      接口有多个实现类,这里看两个实现类的adapt:

      • D efaultCallAdapterFactory.call

        new CallAdapter<Object, Call<?>>() {
                        public Type responseType() {
                            return responseType;
                        }
        
                        public Call<Object> adapt(Call<Object> call) {
                            return (Call)(executor == null ? call : new DefaultCallAdapterFactory.ExecutorCallbackCall(executor, call));
                        }
                    }
                    
            static final class ExecutorCallbackCall<T> implements Call<T> {
                final Executor callbackExecutor;
                final Call<T> delegate;
        
                ExecutorCallbackCall(Executor callbackExecutor, Call<T> delegate) {
                    this.callbackExecutor = callbackExecutor;
                    this.delegate = delegate;
                }
        
                public void enqueue(final Callback<T> callback) {
                    Utils.checkNotNull(callback, "callback == null");
                    this.delegate.enqueue(new Callback<T>() {
                        public void onResponse(Call<T> call, final Response<T> response) {
                            ExecutorCallbackCall.this.callbackExecutor.execute(new Runnable() {
                                public void run() {
                                    if (ExecutorCallbackCall.this.delegate.isCanceled()) {
                                        callback.onFailure(ExecutorCallbackCall.this, new IOException("Canceled"));
                                    } else {
                                        callback.onResponse(ExecutorCallbackCall.this, response);
                                    }
        
                                }
                            });
                        }
        
                        public void onFailure(Call<T> call, final Throwable t) {
                            ExecutorCallbackCall.this.callbackExecutor.execute(new Runnable() {
                                public void run() {
                                    callback.onFailure(ExecutorCallbackCall.this, t);
                                }
                            });
                        }
                    });
                }
            }
        

        这是默认情况的callAdapter,直接在ExecutorCallbackCall中执行call.callback(主线程)。

      • RxJava2CallAdapter

          @Override public Object adapt(Call<R> call) {
            Observable<Response<R>> responseObservable = isAsync
                ? new CallEnqueueObservable<>(call)
                : new CallExecuteObservable<>(call);
        
            Observable<?> observable;
            if (isResult) {
              observable = new ResultObservable<>(responseObservable);
            } else if (isBody) {
              observable = new BodyObservable<>(responseObservable);
            } else {
              observable = responseObservable;
            }
               //添加调度器
            if (scheduler != null) {
              observable = observable.subscribeOn(scheduler);
            }
        
            if (isFlowable) {
              return observable.toFlowable(BackpressureStrategy.LATEST);
            }
            if (isSingle) {
              return observable.singleOrError();
            }
            if (isMaybe) {
              return observable.singleElement();
            }
            if (isCompletable) {
              return observable.ignoreElements();
            }
            return RxJavaPlugins.onAssembly(observable);
          }
        

        通过判断是同步还是异步,创建对应的Observable对象,然后根据类型不同返回不同的Observable对象。

      至此,整个retrofit调用请求的过程全部完成。

      总结

      • Retrofit 库主要使用了运行时注解+动态代理实现对网络请求接口的封装
      • 使用适配器模式对请求的结果进行转换,以实现与不同框架的搭配使用

    相关文章

      网友评论

          本文标题:撸Retrofit2源码

          本文链接:https://www.haomeiwen.com/subject/pnetwctx.html