Retrofit 源码分析4-从 invoke 方法看看网络请求是如何实现的

时间:2021-7-4 作者:qvyue

这次主要分析动态代理实现的 invoke 方法,

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 (method.getDeclaringClass() == Object.class) {
            return method.invoke(this, args);
        }
        args = args != null ? args : emptyArgs;
        return platform.isDefaultMethod(method)
            ? platform.invokeDefaultMethod(method, service, proxy, args)
            : loadServiceMethod(method).invoke(args);
    }
}

invoke 方法里,主要做了三件事。第一件是判断该方法是不是 Object 的方法,例如 toString, clone 啊等等吧,如果是就以 Object 方法的调用方式执行。第二件是判断该方法是不是 Android 系统方法,这里有个 platform 变量,根据赋值来源就会发现它是用来区分 Java 还是 Android 平台。这点在官网上也有提到,Retrofit 支持 Android 和 Java 平台,显然如果运行在安卓系统上,那就应该是 Android 平台。第三件是调用 loadServiceMethod 方法,这个才是我们需要关心的。

ServiceMethod> loadServiceMethod(Method method) {
    ServiceMethod> result = serviceMethodCache.get(method);
    if (result != null) return result;
    synchronized (serviceMethodCache) {
        result = serviceMethodCache.get(method);
        if (result == null) {
            result = ServiceMethod.parseAnnotations(this, method);
            serviceMethodCache.put(method, result);
        }
    }
    return result;
}

方法的大致逻辑是从 serviceMethodCache 缓存里找到 method 对应的 ServiceMethod 类型对象,如果找不到需要做一次加载,并将对象存入缓存中。这里的加载过程值得我们去关注一下,代码比较多,先分析下大致步骤,

  1. 调用 ServiceMethod 的静态方法 parseAnnotations,大意是利用 Retrofit 对象以及 Method 对象进行解析。
  2. 首先做的就是通过解析创建出一个 RequestFactory 对象,这个对象里包含着很多信息,例如请求方式(即 POST 还是 GET 等请求),请求头,contentType 等等。
  3. 接着通过 HttpServiceMethod 的静态方法 parseAnnotations 进一步解析,入参有 Retrofit 对象,Method 对象和刚才创建的 RequestFactory 对象。
  4. HttpServiceMethod 继承自 ServiceMethod,但也是个抽象类,这个类提供的 parseAnnotations 方法的主要内容是进一步解析,并创建前面说过的适配器和转换器,最后利用 RequestFactory 对象,OkHttp 对象,转换器对象,适配器对象创建了一个 CallAdapted 类型的对象并返回。
  5. CallAdapted 类是 HttpServiceMethod 的子类,实现了父类的抽象方法 adapt。而 HttpServiceMethod 又实现了 ServiceMethod 的抽象方法 invoke,在 invoke 方法里调用了 adapt 方法。
  6. 所以前面说到的加载过程,最终就是返回了一个 CallAdapted 类型的对象,并存到缓存中。接下去就是调用了 CallAdapted 对象的 invoke 方法,显然最终调用了 CallAdapted 自身的 adapt 方法。
  7. CallAdapted 提供的 adapt 方法里就一句,那就是调用适配器的 adapt 方法,并返回一个值。
  8. 前面说过,以 RxJava2CallAdapter 适配器为了,最终就是调用了它的 adapt 方法,入参是 Call 类型对象,这个 Call 就是请求的关键。

综上,调用网络请求的方法之后就会触发以上的一系列操作,后面将会从两个角度继续分析,一个是看看这个 Call 的生成及后续,一个是看看涉及到的 RxJava2 相关的东西。

声明:本文内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:qvyue@qq.com 进行举报,并提供相关证据,工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。