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 的源码,然后再来看会了解的更加深刻。

相关推荐
boooooooom1 小时前
别再用错 ref/reactive!90%程序员踩过的响应式坑,一文根治
javascript·vue.js·面试
张元清1 小时前
Astro 6.0:被 Cloudflare 收购两个月后,这个"静态框架"要重新定义全栈了
前端·javascript·面试
青青家的小灰灰1 小时前
深入理解 async/await:现代异步编程的终极解决方案
前端·javascript·面试
Baihai_IDP3 小时前
为什么 AI 巨头们放弃私有壁垒,争相拥抱 Agent Skills
人工智能·面试·llm
Moment3 小时前
Agent 开发本质上就是高级点的 CRUD
前端·后端·面试
哈里谢顿14 小时前
0305乒乓xx agent运维开发岗面试记录
面试
哈里谢顿14 小时前
0309面试二总结
面试
哈里谢顿14 小时前
0309面试一记录
面试
哈里谢顿14 小时前
0310面试二记录
面试
哈里谢顿14 小时前
0310面试记录一
面试