Retrofit 源码解析

了解完OKHttp,接下来让我们认识一下 Retrofit--> OkHttp的封装库

基本使用

网络接口数据

在这里使用的接口是 WanAndroid 的接口 www.wanandroid.com/hotkey/json

json 复制代码
{
  "data": [{
    "id": 6,
    "link": "",
    "name": "面试",
    "order": 1,
    "visible": 1
  },
    {
      "id": 9,
      "link": "",
      "name": "Studio3",
      "order": 1,
      "visible": 1
    },
    {
      "id": 5,
      "link": "",
      "name": "动画",
      "order": 2,
      "visible": 1
    },
    {
      "id": 1,
      "link": "",
      "name": "自定义View",
      "order": 3,
      "visible": 1
    },
    {
      "id": 2,
      "link": "",
      "name": "性能优化 速度",
      "order": 4,
      "visible": 1
    },
    {
      "id": 3,
      "link": "",
      "name": "gradle",
      "order": 5,
      "visible": 1
    },
    {
      "id": 4,
      "link": "",
      "name": "Camera 相机",
      "order": 6,
      "visible": 1
    },
    {
      "id": 7,
      "link": "",
      "name": "代码混淆 安全",
      "order": 7,
      "visible": 1
    },
    {
      "id": 8,
      "link": "",
      "name": "逆向 加固",
      "order": 8,
      "visible": 1
    }],
  "errorCode": 0,
  "errorMsg": ""
}

数据bean

kotlin 复制代码
class BaseResponse<T> {
    var errorCode: String? = null
    var errorMsg: Int? = 0
    var data: T? = null
}

data class DataBean(
    val id: Int? = 0,
    val link: String? = "",
    val name: String? = "",
    val order: Int? = 0,
    val visible: Int? = 0
)

描述网络请求的接口

kotlin 复制代码
interface MainService {
    @GET("/hotkey/json")
    fun getData(): Call<BaseResponse<List<HotKeyInfo>>>
}

发起请求

kotlin 复制代码
fun getData() {
    // 1.Retrofit创建
    val retrofit = Retrofit.Builder().baseUrl("https://www.wanandroid.com/")
        .addConverterFactory(GsonConverterFactory.create()).build()

    // 2.创建网络请求接口示例
    val service = retrofit.create(MainService::class.java)

    // 3.创建Call
    val call = service.getData()

    // 4.进行网络请求
    // 同步请求
    val response = call.execute()
    val apiResult = response.body()

    // 异步请求
    call.enqueue(object : Callback<BaseResponse<List<HotKeyInfo>>> {
        override fun onResponse(
            call: Call<BaseResponse<List<HotKeyInfo>>>,
            response: Response<BaseResponse<List<HotKeyInfo>>>
                ) {
            val apiResult = response.body()
        }

        override fun onFailure(call: Call<BaseResponse<List<HotKeyInfo>>>, t: Throwable) {
        }

    })
}

简单来说就是:

  • 构建 Retrofit 实例
  • 构建 API 接口实例
  • 执行请求,解析响应

流程分析

构建Retrofit 实例

kotlin 复制代码
val retrofit = Retrofit.Builder()
    .baseUrl("https://www.wanandroid.com/")
    .client(new OkHttpClient().newBuilder().connectTimeout(10, TimeUnit.SECONDS).build())
    .addConverterFactory(GsonConverterFactory.create())
    .addCallAdapterFactory(RxJavaCallAdapterFactory.create())
    .build()

从代码可以看出,这是使用建造者模式来构建的实例

kotlin 复制代码
public final class Retrofit {
    // 接口缓存。
    // 一个接口请求的方法为一个 Method,对应一个ServiceMethod,ServiceMethod内部有着网络请求相关配置
    private final Map<Method, ServiceMethod<?>> serviceMethodCache = new ConcurrentHashMap<>();

    // OkHttp的接口,创建 OkHttp请求的工厂接口,只有一个实现类:OKHttpClient
    final okhttp3.Call.Factory callFactory;
    // host地址
    final HttpUrl baseUrl;
    // 将请求或者返回结果进行转换的工厂类列表
    // 例如 Retrofit 自带的 GsonConverterFactory
    final List<Converter.Factory> converterFactories;
    // callAdapter 工厂集合, CallAdapter 就是 Call 的转换器
    // callAdapterFactory会根据自己的能力返回合适的CallAdapter
    final List<CallAdapter.Factory> callAdapterFactories;
    // Call请求的回调方法运行的executor
    // 默认Retrofit定义的MainThreadExecutor,即运行在主线程的Executor
    final @Nullable Executor callbackExecutor;
    // 字面意思就是提前验证,如果是true的话,当retrofit.create创建接口实现类时,就进行接口的解析和初始化,生成相应的ServiceMethod,放入缓存map中
    final boolean validateEagerly;

    Retrofit(
        okhttp3.Call.Factory callFactory,
        HttpUrl baseUrl,
        List<Converter.Factory> converterFactories,
        List<CallAdapter.Factory> callAdapterFactories,
        @Nullable Executor callbackExecutor,
        boolean validateEagerly) {
        this.callFactory = callFactory;
        this.baseUrl = baseUrl;
        this.converterFactories = converterFactories; // Copy+unmodifiable at call site.
        this.callAdapterFactories = callAdapterFactories; // Copy+unmodifiable at call site.
        this.callbackExecutor = callbackExecutor;
        this.validateEagerly = validateEagerly;
    }
        ...省略代码...


    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 platform) {
            this.platform = platform;
        }

        public Builder() {
            this(Platform.get());
        }
            ...省略代码...

        public Retrofit build() {
            if (baseUrl == null) {
                throw new IllegalStateException("Base URL required.");
            }

            okhttp3.Call.Factory callFactory = this.callFactory;
            if (callFactory == null) {
                callFactory = new OkHttpClient();
            }

            Executor callbackExecutor = this.callbackExecutor;
            if (callbackExecutor == null) {
                callbackExecutor = platform.defaultCallbackExecutor();
            }

            // Make a defensive copy of the adapters and add the default Call adapter.
            List<CallAdapter.Factory> callAdapterFactories = new ArrayList<>(this.callAdapterFactories);
            callAdapterFactories.addAll(platform.defaultCallAdapterFactories(callbackExecutor));

            // Make a defensive copy of the converters.
            List<Converter.Factory> converterFactories =
            new ArrayList<>(
                1 + this.converterFactories.size() + platform.defaultConverterFactoriesSize());

            // Add the built-in converter factory first. This prevents overriding its behavior but also
            // ensures correct behavior when using converters that consume all types.
            converterFactories.add(new BuiltInConverters());
            converterFactories.addAll(this.converterFactories);
            converterFactories.addAll(platform.defaultConverterFactories());

            return new Retrofit(
                callFactory,
                baseUrl,
                unmodifiableList(converterFactories),
                unmodifiableList(callAdapterFactories),
                callbackExecutor,
                validateEagerly);
        }
    }
}

我们可以看到 Builder中有个 Platform变量,这个参数是通过 Platform.get()获取的

kotlin 复制代码
class Platform {
    private static final Platform PLATFORM = findPlatform();

    static Platform get() {
        return PLATFORM;
    }

    private static Platform findPlatform() {
        return "Dalvik".equals(System.getProperty("java.vm.name"))
        ? new Android() //
        : new Platform(true);
    }
}

从这段代码我们可以看到,Platform提供了Android 和Java平台的支持,也就是说 Retrofit 不仅可以用在 Android 开发,也可以用在后端Java开发。 在Android平台下,Platform的主要作用有以下几个:

  • 通过 defaultCallbackExecutor 方法提供一个默认的 CallbackExecutor。Android平台会提供一个 MainThreadExecutor。
  • 通过 defaultCallAdapterFactories 方法,提供默认的 CallAdapterFactory。DefaultCallAdapterFactory(将异步请求结果的回调使用 callbackExecutor 运行)。
  • 通过 defaultConverterFactories 方法,提供默认的 ConverterFactory。是一个空的 List。

我们看一下 build方法

kotlin 复制代码
okhttp3.Call.Factory callFactory = this.callFactory;
if (callFactory == null) {
    callFactory = new OkHttpClient();
}

如果没有设置 callFactory,创建一个OkHttpClient 对象

将Platform提供的用户的配置和Platform提供的默认支持加入,完成Retrofit的创建。

kotlin 复制代码
Executor callbackExecutor = this.callbackExecutor;
if (callbackExecutor == null) {
    callbackExecutor = platform.defaultCallbackExecutor();
}

List<CallAdapter.Factory> callAdapterFactories = new ArrayList<>(this.callAdapterFactories);
callAdapterFactories.addAll(platform.defaultCallAdapterFactories(callbackExecutor));

List<Converter.Factory> converterFactories =
    new ArrayList<>(
        1 + this.converterFactories.size() + platform.defaultConverterFactoriesSize());

converterFactories.add(new BuiltInConverters());
converterFactories.addAll(this.converterFactories);
converterFactories.addAll(platform.defaultConverterFactories());

构建 API 接口实例

kotlin 复制代码
// 2.创建网络请求接口示例
val service = retrofit.create(MainService::class.java)

让我们看一下 create方法的源码

create

kotlin 复制代码
public <T> T create(final Class<T> service) {
    // 验证 API service
    // 如果 validateEagerly 为true, 这里直接对 service进行解析和初始化,否则将在第一次运行时进行初始化
    validateServiceInterface(service);
    return (T)
    // 这里采用了动态代理模式, service 就是被代理类

    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 {
                // 如果是 Object的方法,则直接调用这个方法。
                // 这里限制只能是接口
                // If the method is a method from Object then defer to normal invocation.
                if (method.getDeclaringClass() == Object.class) {
                    return method.invoke(this, args);
                }
                 //如果不是系统默认方法,通过loadServiceMethod()方法返回一个ServiceMethod,并调用invoke方法
                args = args != null ? args : emptyArgs;
                return platform.isDefaultMethod(method)
                ? platform.invokeDefaultMethod(method, service, proxy, args)
                : loadServiceMethod(method).invoke(args);
            }
        });
}

这个方法主要做了两件事:

  • 验证API接口类
  • 利用动态代理在运行期间实例化API接口。
kotlin 复制代码
private void validateServiceInterface(Class<?> service) {
    // service 必须是 interface, 否则抛出异常
    if (!service.isInterface()) {
        throw new IllegalArgumentException("API declarations must be interfaces.");
    }

    Deque<Class<?>> check = new ArrayDeque<>(1);
    check.add(service);
    while (!check.isEmpty()) {
        Class<?> candidate = check.removeFirst();
        if (candidate.getTypeParameters().length != 0) {
            StringBuilder message =
            new StringBuilder("Type parameters are unsupported on ").append(candidate.getName());
            if (candidate != service) {
                message.append(" which is an interface of ").append(service.getName());
            }
            throw new IllegalArgumentException(message.toString());
        }
        Collections.addAll(check, candidate.getInterfaces());
    }
    
    // 是否立即验证API接口中的所有方法,由用户设置,默认为false
    if (validateEagerly) {
        Platform platform = Platform.get();
        // 遍历 service 中定义的所有方法
        for (Method method : service.getDeclaredMethods()) {
            // 如果该方法不是系统默认方法且方法修饰符不是静态方法就执行loadServiceMethod方法
            if (!platform.isDefaultMethod(method) && !Modifier.isStatic(method.getModifiers())) {
                // 加载请求方法。
                loadServiceMethod(method);
            }
        }
    }
}

继续往下看,loadServiceMethod()

kotlin 复制代码
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;
}

先从缓存中查找,如果没有的话,则通过 ServiceMethod.parseAnnotations() 方法获取到 ServiceMethod,放入缓存,并返回。

ServiceMethod

继续往下看 ServiceMethod.parseAnnotations()

kotlin 复制代码
abstract class ServiceMethod<T> {
    static <T> ServiceMethod<T> parseAnnotations(Retrofit retrofit, Method method) {
        RequestFactory requestFactory = RequestFactory.parseAnnotations(retrofit, method);

        Type returnType = method.getGenericReturnType();
        if (Utils.hasUnresolvableType(returnType)) {
            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);
    }

    abstract @Nullable T invoke(Object[] args);
}

在这个方法中,先创建了一个 requestFactory, 然后通过 HttpServiceMethod.parseAnnotations 将 requestFactory 传给 HttpServiceMethod,并返回 ServiceMethod。

RequestFactory

先看一下 RequestFactory

kotlin 复制代码
final class RequestFactory {
    static RequestFactory parseAnnotations(Retrofit retrofit, Method method) {
        return new Builder(retrofit, method).build();
    }

    private final Method method;
    private final HttpUrl baseUrl;
    final String httpMethod;
    // 相对url,例如注解@GET 后边的值
    private final @Nullable String relativeUrl;
    // 注解 Headers解析
    private final @Nullable Headers headers;
    // 注解 Header中 Content-Type的值
    private final @Nullable MediaType contentType;
    // 是否有body
    private final boolean hasBody;
    // 是否是FromEncoded
    private final boolean isFormEncoded;
    // 是否是 Multipart
    private final boolean isMultipart;
    // 方法的每个入参都有一个对应的 parameterHandlers
    private final ParameterHandler<?>[] parameterHandlers;
    // 是否是kotlin的suspend方法
    final boolean isKotlinSuspendFunction;
    ...省略代码...
}

Builder.build 对RequestFactory进行创建

kotlin 复制代码
Builder(Retrofit retrofit, Method method) {
    this.retrofit = retrofit;
    this.method = method;
    // 获取方法注解,返回值是 Annotaition[]
    this.methodAnnotations = method.getAnnotations();
    // 获取方法参数类型,返回值为 Type[]
    this.parameterTypes = method.getGenericParameterTypes();
    // 获取参数中的注解,返回值为 Annotation[][]
    this.parameterAnnotationsArray = method.getParameterAnnotations();
}

RequestFactory build() {
    // 解析方法注解,例如GET、POST等
    for (Annotation annotation : methodAnnotations) {
        parseMethodAnnotation(annotation);
    }

    ...省略代码...
    
    // 解析每个入参和其注解,生成对应的ParameterHandler
    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);
}

build方法中有两个核心方法 parseMethodAnnotation 和 parseParameter 其中 parseMethodAnnotation 是对方法的注解进行解析,即 POST、GET、PUT等

kotlin 复制代码
private void parseMethodAnnotation(Annotation annotation) {
    if (annotation instanceof DELETE) {
        parseHttpMethodAndPath("DELETE", ((DELETE) annotation).value(), false);
    } else if (annotation instanceof GET) {
        parseHttpMethodAndPath("GET", ((GET) annotation).value(), false);
    } else if (annotation instanceof HEAD) {
        parseHttpMethodAndPath("HEAD", ((HEAD) annotation).value(), false);
    } else if (annotation instanceof PATCH) {
        parseHttpMethodAndPath("PATCH", ((PATCH) annotation).value(), true);
    } else if (annotation instanceof POST) {
        parseHttpMethodAndPath("POST", ((POST) annotation).value(), true);
    } else if (annotation instanceof PUT) {
        parseHttpMethodAndPath("PUT", ((PUT) annotation).value(), true);
    } else if (annotation instanceof OPTIONS) {
        parseHttpMethodAndPath("OPTIONS", ((OPTIONS) annotation).value(), false);
    } else if (annotation instanceof HTTP) {
        HTTP http = (HTTP) annotation;
        parseHttpMethodAndPath(http.method(), http.path(), http.hasBody());
    } else if (annotation instanceof retrofit2.http.Headers) {
        String[] headersToParse = ((retrofit2.http.Headers) annotation).value();
        if (headersToParse.length == 0) {
            throw methodError(method, "@Headers annotation is empty.");
        }
        headers = parseHeaders(headersToParse);
    } else if (annotation instanceof Multipart) {
        if (isFormEncoded) {
            throw methodError(method, "Only one encoding annotation is allowed.");
        }
        isMultipart = true;
    } else if (annotation instanceof FormUrlEncoded) {
        if (isMultipart) {
            throw methodError(method, "Only one encoding annotation is allowed.");
        }
        isFormEncoded = true;
    }
}

parseParameter是对方法参数和其上的注解进行处理

kotlin 复制代码
private @Nullable ParameterHandler<?> parseParameter(
    int p, Type parameterType, @Nullable Annotation[] annotations, boolean allowContinuation) {
    ParameterHandler<?> result = null;
    if (annotations != null) {
        for (Annotation annotation : annotations) {
            // 生成 annotationAction
            ParameterHandler<?> annotationAction =
            parseParameterAnnotation(p, parameterType, annotations, annotation);

            if (annotationAction == null) {
                continue;
            }

            if (result != null) {
                throw parameterError(
                    method, p, "Multiple Retrofit annotations found, only one allowed.");
            }

            result = annotationAction;
        }
    }

        ...省略代码...

    return result;
}

parseParameterAnnotation这个方法就是根据annotation的不同,生成不同的ParameterHandler 对象实例,方法太长就不粘贴了,感兴趣的可以自己跟着源码看一下,逻辑也很简单。

HttpServiceMethod

我们在继续看 HttpServiceMethod.parseAnnotations。从方法名来看,还是对注解的解析

kotlin 复制代码
static <ResponseT, ReturnT> HttpServiceMethod<ResponseT, ReturnT> parseAnnotations(
    Retrofit retrofit, Method method, RequestFactory requestFactory) {
    boolean isKotlinSuspendFunction = requestFactory.isKotlinSuspendFunction;
    boolean continuationWantsResponse = false;
    boolean continuationBodyNullable = false;

    Annotation[] annotations = method.getAnnotations();
    Type adapterType;
    if (isKotlinSuspendFunction) {
        // 忽略kotlin 挂起函数方式的代码
    } else {
        adapterType = method.getGenericReturnType();
    }

    // 从callAdapterFactories 中获取到合适的CallAdapter,对call进行转换
    CallAdapter<ResponseT, ReturnT> callAdapter =
    createCallAdapter(retrofit, method, adapterType, annotations);
    Type responseType = callAdapter.responseType();

    ...省略代码...

    // 从converterFactories中获取到合适的 responseConverter
    Converter<ResponseBody, ResponseT> responseConverter =
    createResponseConverter(retrofit, method, responseType);

    okhttp3.Call.Factory callFactory = retrofit.callFactory;
    if (!isKotlinSuspendFunction) {
        // 拿到requestFactory、合适的callAdapter、合适的responseConverter,组成了新的CallAdapted,CallAdapted是HttpServiceMethod的一个子类。
        return new CallAdapted<>(requestFactory, callFactory, responseConverter, callAdapter);
    }
    ...省略代码...
}
kotlin 复制代码
static final class CallAdapted<ResponseT, ReturnT> extends HttpServiceMethod<ResponseT, ReturnT> {
    private final CallAdapter<ResponseT, ReturnT> callAdapter;

    CallAdapted(
        RequestFactory requestFactory,
        okhttp3.Call.Factory callFactory,
        Converter<ResponseBody, ResponseT> responseConverter,
        CallAdapter<ResponseT, ReturnT> callAdapter) {
        super(requestFactory, callFactory, responseConverter);
        this.callAdapter = callAdapter;
    }

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

invoke

loadServiceMethod 分析完,就是invoke方法了

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

adapt方法最终走到的是 DefaultCallAdapterFactory 中 这里返回了ExecutorCallbackCall,对传入的OkHttpCall对象做了一层简单的封装,enqueue方法将回调函数运行在主线程中。

kotlin 复制代码
final class DefaultCallAdapterFactory extends CallAdapter.Factory {
    @Nullable
    private final Executor callbackExecutor;

    DefaultCallAdapterFactory(@Nullable Executor callbackExecutor) {
        this.callbackExecutor = callbackExecutor;
    }

    @Nullable
    public CallAdapter<?, ?> get(Type returnType, Annotation[] annotations, Retrofit retrofit) {
        if (getRawType(returnType) != Call.class) {
            return null;
        } else if (!(returnType instanceof ParameterizedType)) {
            throw new IllegalArgumentException("Call return type must be parameterized as Call<Foo> or Call<? extends Foo>");
        } else {
            final Type responseType = Utils.getParameterUpperBound(0, (ParameterizedType)returnType);
            final Executor executor = Utils.isAnnotationPresent(annotations, SkipCallbackExecutor.class) ? null : this.callbackExecutor;
            return new CallAdapter<Object, Call<?>>() {
                public Type responseType() {
                    return responseType;
                }

                public Call<Object> adapt(Call<Object> call) {
                    return (Call)(executor == null ? call : new 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) {
            Objects.requireNonNull(callback, "callback == null");
            this.delegate.enqueue(new Callback<T>() {
                public void onResponse(Call<T> call, Response<T> response) {
                    ExecutorCallbackCall.this.callbackExecutor.execute(() -> {
                        if (ExecutorCallbackCall.this.delegate.isCanceled()) {
                            callback.onFailure(ExecutorCallbackCall.this, new IOException("Canceled"));
                        } else {
                            callback.onResponse(ExecutorCallbackCall.this, response);
                        }

                    });
                }

                public void onFailure(Call<T> call, Throwable t) {
                    ExecutorCallbackCall.this.callbackExecutor.execute(() -> {
                        callback.onFailure(ExecutorCallbackCall.this, t);
                    });
                }
            });
        }

        public boolean isExecuted() {
            return this.delegate.isExecuted();
        }

        public Response<T> execute() throws IOException {
            return this.delegate.execute();
        }

        public void cancel() {
            this.delegate.cancel();
        }

        public boolean isCanceled() {
            return this.delegate.isCanceled();
        }

        public Call<T> clone() {
            return new ExecutorCallbackCall(this.callbackExecutor, this.delegate.clone());
        }

        public Request request() {
            return this.delegate.request();
        }

        public Timeout timeout() {
            return this.delegate.timeout();
        }
    }
}

执行请求

kotlin 复制代码
// 4.进行网络请求
// 同步请求
val response = call.execute()
val apiResult = response.body()

// 异步请求
call.enqueue(object : Callback<BaseResponse<List<HotKeyInfo>>> {
    override fun onResponse(
        call: Call<BaseResponse<List<HotKeyInfo>>>,
        response: Response<BaseResponse<List<HotKeyInfo>>>
            ) {
        val apiResult = response.body()
    }

    override fun onFailure(call: Call<BaseResponse<List<HotKeyInfo>>>, t: Throwable) {
    }

})

来看一下 enqueue

kotlin 复制代码
@Override
public void enqueue(final Callback<T> callback) {
    Objects.requireNonNull(callback, "callback == null");

    okhttp3.Call call;
    Throwable failure;

    synchronized (this) {
        if (executed) throw new IllegalStateException("Already executed.");
        executed = true;

        call = rawCall;
        failure = creationFailure;
        if (call == null && failure == null) {
            try {
                // 这里就是创建 okhttp 的call
                call = rawCall = createRawCall();
            } catch (Throwable t) {
                throwIfFatal(t);
                failure = creationFailure = t;
            }
        }
    }

    if (failure != null) {
        callback.onFailure(this, failure);
        return;
    }

    if (canceled) {
        call.cancel();
    }
    // okhttp 的enqueue
    call.enqueue(
        new okhttp3.Callback() {
            @Override
            public void onResponse(okhttp3.Call call, okhttp3.Response rawResponse) {
                Response<T> response;
                try {
                    response = parseResponse(rawResponse);
                } catch (Throwable e) {
                    throwIfFatal(e);
                    callFailure(e);
                    return;
                }

                try {
                    callback.onResponse(OkHttpCall.this, response);
                } catch (Throwable t) {
                    throwIfFatal(t);
                    t.printStackTrace(); // TODO this is not great
                }
            }

            @Override
            public void onFailure(okhttp3.Call call, IOException e) {
                callFailure(e);
            }

            private void callFailure(Throwable e) {
                try {
                    callback.onFailure(OkHttpCall.this, e);
                } catch (Throwable t) {
                    throwIfFatal(t);
                    t.printStackTrace(); // TODO this is not great
                }
            }
        });
}
kotlin 复制代码
private okhttp3.Call createRawCall() throws IOException {
    // 创建 okhttp 的call
    // 这里的callFactory就是 OkHttpClient
    // requestFactory.create(args) 这个方法创建了一个 okhttp 的 request
    okhttp3.Call call = callFactory.newCall(requestFactory.create(args));
    if (call == null) {
        throw new NullPointerException("Call.Factory returned null.");
    }
    return call;
}

requestFactory.create 方法,将参数 转换为 Request中的数据

kotlin 复制代码
okhttp3.Request create(Object[] args) throws IOException {
    @SuppressWarnings("unchecked") // It is an error to invoke a method with the wrong arg types.
    // 之前根据参数的注解 生成的 对应的 handler
    ParameterHandler<Object>[] handlers = (ParameterHandler<Object>[]) parameterHandlers;

    int argumentCount = args.length;
    if (argumentCount != handlers.length) {
        throw new IllegalArgumentException(
            "Argument count ("
            + argumentCount
            + ") doesn't match expected count ("
            + handlers.length
            + ")");
    }

    RequestBuilder requestBuilder =
    new RequestBuilder(
        httpMethod,
        baseUrl,
        relativeUrl,
        headers,
        contentType,
        hasBody,
        isFormEncoded,
        isMultipart);

    if (isKotlinSuspendFunction) {
        // The Continuation is the last parameter and the handlers array contains null at that index.
        argumentCount--;
    }

    List<Object> argumentList = new ArrayList<>(argumentCount);
    for (int p = 0; p < argumentCount; p++) {
        argumentList.add(args[p]);
        // 对参数注解进行处理
        // 这个地方就是给 requestBuilder设置值
        handlers[p].apply(requestBuilder, args[p]);
    }

    return requestBuilder.get().tag(Invocation.class, new Invocation(method, argumentList)).build();
}

自此,retrofit的整个流程就解析结束了。 Retrofit 作为 OkHttp 的封装库,可以先了解OkHttp 的源码,然后再来看会了解的更加深刻。

相关推荐
鱼跃鹰飞7 小时前
大厂面试真题-简单说说线程池接到新任务之后的操作流程
java·jvm·面试
程序员清风9 小时前
浅析Web实时通信技术!
java·后端·面试
测试199810 小时前
外包干了2年,快要废了。。。
自动化测试·软件测试·python·面试·职场和发展·单元测试·压力测试
mingzhi6111 小时前
渗透测试-快速获取目标中存在的漏洞(小白版)
安全·web安全·面试·职场和发展
嚣张农民11 小时前
一文简单看懂Promise实现原理
前端·javascript·面试
Liknana13 小时前
Android 网易游戏面经
android·面试
威哥爱编程17 小时前
MongoDB面试专题33道解析
数据库·mongodb·面试
程序猿进阶17 小时前
Redis 基础数据改造
java·开发语言·数据库·redis·后端·面试·架构
刘艳兵的学习博客19 小时前
刘艳兵-DBA027-在Oracle数据库,通常可以使用如下方法来得到目标SQL的执行计划,那么通过下列哪些方法得到的执行计划有可能是不准确的?
数据库·oracle·面试·database·刘艳兵