Retrofit源码流程分析
简单使用流程
以下是一个简单的Retrofit使用流程,在源码分析中只关注一些流程上的东西,忽略细节陷入细节的话很容易晕,好吧细节我也没咋看懂。。。


Step1 创建Retrofit实例
先看看Retrofit中的一些变量
public final class Retrofit {private final Map<Method, ServiceMethod<?>> serviceMethodCache = new ConcurrentHashMap<>();//很明显就是一个用于生成Okhttp的Call实例的工厂//后续会看到其实就是把OkhttpClient赋值给它final okhttp3.Call.Factory callFactory;//这就是上图中对应的.baseUrl("")这里传入了一个空字符串,当然实际项目中肯定不能这样//这只是为了方便,Retrofit会把传入的字符传转为HttpUrl对象final HttpUrl baseUrl;//保存自定义和默认的转换器,把响应数据转为特定格式final List<Converter.Factory> converterFactories;//保存自定义和默认的Call的适配器final List<CallAdapter.Factory> callAdapterFactories;//一个线程调度器final @Nullable Executor callbackExecutor;//一个标志位判断是否需求提前验证上图Api接口中的这些方法,并保存到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;}
Retrofit.Builder()
首先来到Retrofit.Builder()中:截取部分代码片段


在Builder()中的代码很简单Platform.get()方法会来到Platform类的findPlatform()方法,方法名其实已经很明确了此方法和平台有关
if (Build.VERSION.SDK_INT != 0) {return new Android();}
在Android开发中一定会调用到new Android()生成一个Android类型的实例,当然此实例对象是继承自Platform,来看一下它又做了什么
static class Android extends Platform {@IgnoreJRERequirement // Guarded by API check.@Override boolean isDefaultMethod(Method method) {if (Build.VERSION.SDK_INT < 24) {return false;}return method.isDefault();}@Override public Executor defaultCallbackExecutor() {return new MainThreadExecutor();}//1:这里会返回一个默认的CallAdapter实例,具体后面分析@Override List<? extends CallAdapter.Factory> defaultCallAdapterFactories(@Nullable Executor callbackExecutor) {if (callbackExecutor == null) throw new AssertionError();DefaultCallAdapterFactory executorFactory = new DefaultCallAdapterFactory(callbackExecutor);return Build.VERSION.SDK_INT >= 24? asList(CompletableFutureCallAdapterFactory.INSTANCE, executorFactory): singletonList(executorFactory);}@Override int defaultCallAdapterFactoriesSize() {return Build.VERSION.SDK_INT >= 24 ? 2 : 1;}//2:这里返回一个默认的数据转换器@Override List<? extends Converter.Factory> defaultConverterFactories() {return Build.VERSION.SDK_INT >= 24? singletonList(OptionalConverterFactory.INSTANCE): Collections.<Converter.Factory>emptyList();}@Override int defaultConverterFactoriesSize() {return Build.VERSION.SDK_INT >= 24 ? 1 : 0;}//3:用于线程调度static class MainThreadExecutor implements Executor {private final Handler handler = new Handler(Looper.getMainLooper());@Override public void execute(Runnable r) {handler.post(r);}}}
总结:在Builder()中Platform.get()–>findPlatform()–>new Android()这一个流程走下来主要就是关联具体的平台,至于初始化实例对象就是在Android()中标记的那三点在build中会去调用,具体的作用后续会用到
Retrofit.Builder().build()
直接上代码
public Retrofit build() {//baseUrl为null直接抛出异常if (baseUrl == null) {throw new IllegalStateException("Base URL required.");}/***注意:这里就把this.callFactory赋值给Call.Factory了简单看一下它的初始化流程:* public Builder client(OkHttpClient client) {* return callFactory(checkNotNull(client, "client == null"));}* * public Builder callFactory(okhttp3.Call.Factory factory) {* this.callFactory = checkNotNull(factory, "factory == null");* return this;}* 从这两个方法就可以看出了callFactory就是一个OkhttpClient,即Call.Factory* 就是OkhttpClient,还记得Okhttp中的call怎么创建出来的吗?就是通过* OkHttpClient的newCall方法创建的,从这里大概能猜出为什么经常听到Retrofit底* 层是使用的Okhttp了*/okhttp3.Call.Factory callFactory = this.callFactory;if (callFactory == null) {callFactory = new OkHttpClient();}/*** 这里就是初始化Retrofit的线程调度器了,如果我们没有手动设置的话就会使用* platform中初始化的那个线程调度器即:MainThreadExecutor*/Executor callbackExecutor = this.callbackExecutor;if (callbackExecutor == null) {callbackExecutor = platform.defaultCallbackExecutor();}/*** 后续的代码就是把默认的数据转换器以及call的适配器全部保存到list中,包括自己设置 * 以及Retrofit默认的*/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);}
Step1就到此结束,总的来说就是初始化一些实例并保存下来
Step2 Retrofit.Create()
public <T> T create(final Class<T> service) {Utils.validateServiceInterface(service);//这里在Retrofit的变量就已经分析了if (validateEagerly) {eagerlyValidateMethods(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);}//如果是默认方法(比如 Java8 ),就执行 platform 的默认方法。否则执行// loadServiceMethod方法的invoke方法if (platform.isDefaultMethod(method)) {return platform.invokeDefaultMethod(method, service, proxy, args);}return loadServiceMethod(method).invoke(args != null ? args : emptyArgs);}});}
这里一目了然核心就是一个动态代理,回到最开始的使用流程来看当调用api.fetchData方法之后会来到InvocationHandler的invoke中并最终调用loadServiceMethod方法,主要看最后一行loadServiceMethod(method).invoke(args != null ? args : emptyArgs),这里分两部分来看loadServiceMethod和invoke
loadServiceMethod
ServiceMethod<?> loadServiceMethod(Method method) {ServiceMethod<?> result = serviceMethodCache.get(method);if (result != null) return result;synchronized (serviceMethodCache) {result = serviceMethodCache.get(method);if (result == null) {/*** 该方法核心就是为了获取ServiceMethod实例,以method为key首先在map中取* 如果没有就通过parseAnnotations去创建,并把已经构造出来的Retrofit实例* 和method传进去*/result = ServiceMethod.parseAnnotations(this, method);serviceMethodCache.put(method, result);}}return result;}
/*** RequestFactory.parseAnnotations(retrofit, method)主要是解析方法的注解* 和参数的注解并保存下来* * HttpServiceMethod.parseAnnotations主要是创建CallAdapter即请求的适配器* 以及Convert即数据转换器* * 最终会返回一个HttpServiceMethod的具体实现类的实例对象* 具体代码后面再分析*/
abstract class ServiceMethod<T> {static <T> ServiceMethod<T> parseAnnotations(Retrofit retrofit, Method method) {RequestFactory requestFactory = RequestFactory.parseAnnotations(retrofit, method);// ......省略return HttpServiceMethod.parseAnnotations(retrofit, method, requestFactory);}abstract @Nullable T invoke(Object[] args);
}
先梳理下流程:
1、首先Retrofit.Builder().build()这中间会去初始化一些实例比如默认的CallAdapter.Factory以及默认的数据转换器并保存,当然也会保存我们自己设置的,还会把OkhttpClient赋值给retrofit的Call.Factory变量最后创建Retrofit实例
2、通过动态代理在create中返回一个Api的proxy对象
3、当使用api.fetchData的时候来到invocationHandler的invoke中并最终调用loadServiceMethod(…).invoke(…)
4、创建一个HttpServiceMethod的具体实现类的实例对象,在创建的过程中首先通过RequestFactory.parseAnnotations去解析方法以及方法参数的注解,其次在HttpServiceMethod.parseAnnotations中还会创建CallAdapter、Convert
5、调用HttpServiceMethod的具体实例的invoke方法
RequestFactory.parseAnnotations
RequestFactory build() {for (Annotation annotation : methodAnnotations) {//这里主要是解析method的注解如GET、POST等,获取其中的值并保存这里就是//{pageNo}/fetch 这部分很简单感兴趣可以看下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);}
private @Nullable ParameterHandler<?> parseParameter(int p, Type parameterType, @Nullable Annotation[] annotations, boolean allowContinuation) {ParameterHandler<?> result = null;//这里主要是解析method参数的注解if (annotations != null) {for (Annotation annotation : annotations) {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;}}if (result == null) {if (allowContinuation) {try {/*** 注意这里如果我们Api接口里面使用的是协程那么会把isKotlinSuspendFunction* 置为true,协程中的suspend方法转为java代码的时候就是这个Continuation类型*/if (Utils.getRawType(parameterType) == Continuation.class) {isKotlinSuspendFunction = true;return null;}} catch (NoClassDefFoundError ignored) {}}throw parameterError(method, p, "No Retrofit annotation found.");}return result;}
HttpServiceMethod.parseAnnotations
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;//1、这里就是在解析method参数注解的时候设置的,如果使用了协程那么会置为trueif (isKotlinSuspendFunction) {Type[] parameterTypes = method.getGenericParameterTypes();Type responseType = Utils.getParameterLowerBound(0,(ParameterizedType) parameterTypes[parameterTypes.length - 1]);if (getRawType(responseType) == Response.class && responseType instanceof ParameterizedType) {responseType = Utils.getParameterUpperBound(0, (ParameterizedType) responseType);//2、continuationWantsResponse赋值为truecontinuationWantsResponse = true;} adapterType = new Utils.ParameterizedTypeImpl(null, Call.class, responseType);annotations = SkipCallbackExecutorImpl.ensurePresent(annotations);} else {adapterType = method.getGenericReturnType();}//3、这里就是创建CallAdapterCallAdapter<ResponseT, ReturnT> callAdapter =createCallAdapter(retrofit, method, adapterType, annotations);Type responseType = callAdapter.responseType();//4、创建数据转换器Converter<ResponseBody, ResponseT> responseConverter =createResponseConverter(retrofit, method, responseType);//5、retrofit.callFactory就是okhttpClient,在Retrofit...build()已经分析过okhttp3.Call.Factory callFactory = retrofit.callFactory;/*** 6、从这里就开始创建HttpServiceMethod的具体实现类了* 不是协程suspend的话就返回CallAdapted* 是协程就返回SuspendForResponse*/if (!isKotlinSuspendFunction) {return new CallAdapted<>(requestFactory, callFactory, responseConverter, callAdapter);} else if (continuationWantsResponse) {return (HttpServiceMethod<ResponseT, ReturnT>) new SuspendForResponse<>(requestFactory,callFactory, responseConverter, (CallAdapter<ResponseT, Call<ResponseT>>) callAdapter);} else {return (HttpServiceMethod<ResponseT, ReturnT>) new SuspendForBody<>(requestFactory,callFactory, responseConverter, (CallAdapter<ResponseT, Call<ResponseT>>) callAdapter,continuationBodyNullable);}}
注意
1、创建的CallAdapter可能是系统默认的可能是我们自己设置的如RxJava3CallAdapterRxJava3CallAdapter是从RxJava3CallAdapterFactory中get()出来的,而RxJava3CallAdapterFactory就是通过addCallAdapterFactory(RxJava3CallAdapterFactory.create())设置的
2、通过判断协程suspend去创建不同的HttpServiceMethod的具体实现类
下面来看一下CallAdapter的创建流程通过一系列调用最终会来到nextCallAdapter方法中:
public CallAdapter<?, ?> nextCallAdapter(@Nullable CallAdapter.Factory skipPast, Type returnType,Annotation[] annotations) {checkNotNull(returnType, "returnType == null");checkNotNull(annotations, "annotations == null");int start = callAdapterFactories.indexOf(skipPast) + 1;for (int i = start, count = callAdapterFactories.size(); i < count; i++) {/*** callAdapterFactories在之前就介绍过,这里根据returnType去寻找CallAdapter* 比如:我们在Api中的fetchData returnType 类型为 Single,那么返回的就是 RxJava2CallAdapterFactory 所获取的 CallAdapter* * 若returnType是Call返回的就是默认的CallAdapter,即DefaultCallAdapterFactory.get获取到的* 而它也在Retrofit..build()中就已经设置到callAdapterFactories中了*/ CallAdapter<?, ?> adapter = callAdapterFactories.get(i).get(returnType, annotations, this);if (adapter != null) {return adapter;}}//省略...}
再次回顾loadServiceMethod这一套流程
1、解析方法、方法参数的注解
2、创建CallAdapter(Convert的创建和它差不多)
3、创建HttpServiceMethod的具体实现类的实例对象并返回
实际上callAdapter使用的就是一个适配器模式,把我们的请求转换一次实际上底层还是使用的是Okhttp call.enqueue那套,而具体的HttpServiceMethod则是在invoke中去做一些其它处理,毕竟协程的请求和Rx这些肯定还是有不同的地方
invoke
别忘了在loadServiceMethod后紧跟着就调用了invoke方法,现在来看一下,
if (!isKotlinSuspendFunction) {return new CallAdapted<>(requestFactory, callFactory, responseConverter, callAdapter);} else if (continuationWantsResponse) {//noinspection unchecked Kotlin compiler guarantees ReturnT to be Object.return (HttpServiceMethod<ResponseT, ReturnT>) new SuspendForResponse<>(requestFactory,callFactory, responseConverter, (CallAdapter<ResponseT, Call<ResponseT>>) callAdapter);} else {//noinspection unchecked Kotlin compiler guarantees ReturnT to be Object.return (HttpServiceMethod<ResponseT, ReturnT>) new SuspendForBody<>(requestFactory,callFactory, responseConverter, (CallAdapter<ResponseT, Call<ResponseT>>) callAdapter,continuationBodyNullable);}
在HttpServiceMethod.parseAnnotations中最终通过isKotlinSuspendFunction创建了不同的HttpServiceMethod实例,默认情况下是CallAdapted,来看下它的处理,实际上不管是哪种实例,invoke都调用的是HttpServiceMethod的invoke,子类都只是重写了adapt方法。

在这里我们看到创建了一个Call对象,这个call对象是Retrofit中的,注意这里的参数有requestFactory, args, callFactory, responseConverter,requestFactory中封装了方法和方法参数的各种注解,args是反复的参数,callFactory实际上就是个OkhttpClient,responseConverter则是数据转换器。
下面先来看下adapt做了什么:
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;}/*** invoke会来到这里,而这里又调用的是callAdapter.adapt并把httpCall传进去了* 我们现在讨论的是默认的情况,即addCallAdapterFactory这些都没设置* 并且返回参数也是Call,所以这里的callAdapter是从DefaultCallAdapterFactory的get()中获取的*/ @Override protected ReturnT adapt(Call<ResponseT> call, Object[] args) {return callAdapter.adapt(call);}}
来看一下DefaultCallAdapterFactory的get()方法做了什么
@Override public @Nullable CallAdapter<?, ?> get(/*** 这里直接new了一个CallAdapter的实例*/return new CallAdapter<Object, Call<?>>() {@Override public Type responseType() {return responseType;}/*** adapt最终又会来到这里并创建了ExecutorCallbackCall,注意参数处了传进来的HttpCall外还有线程调度器executor*/@Override public Call<Object> adapt(Call<Object> call) {return executor == null? call: new ExecutorCallbackCall<>(executor, call);}};}
看下ExecutorCallbackCall,它实现了Retrofit的Call接口,到这里实际上就是loadServiceMethod(method).invoke(args != null ? args : emptyArgs)这段代码的终点了,它最终返回的是一个实现了Retrofit.Call的对象,这也说明了在上面的使用流程中fetchData后为什么还要调用enqueue()方法
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;}@Override public void enqueue(final Callback<T> callback) {checkNotNull(callback, "callback == null");delegate.enqueue(new Callback<T>() {@Override public void onResponse(Call<T> call, final Response<T> response) {callbackExecutor.execute(new Runnable() {@Override public void run() {if (delegate.isCanceled()) {// Emulate OkHttp's behavior of throwing/delivering an IOException on cancellation.callback.onFailure(ExecutorCallbackCall.this, new IOException("Canceled"));} else {callback.onResponse(ExecutorCallbackCall.this, response);}}});}@Override public void onFailure(Call<T> call, final Throwable t) {callbackExecutor.execute(new Runnable() {@Override public void run() {callback.onFailure(ExecutorCallbackCall.this, t);}});}});}//省略...}
Step3 call.enqueue
我们得到的call对象实际上就是一个ExecutorCallbackCall对象,当调用enqueue的时候会来到delegate.enqueue(…)中,delegate实际上是一个HttpCall对象,具体的网络请求是在HttpCall中执行的,这里需要结合HttpCall中的代码来看
//HttpCall@Override public void enqueue(final Callback<T> callback) {checkNotNull(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 {/*** 1、创建Okhttp.call,在createRawCall中还会根据requestFactory去创建okhttp3.Request* requestFactory中包含了请求的各种注解信息,毕竟只有call没有request肯定是不行的晒*/call = rawCall = createRawCall();} catch (Throwable t) {throwIfFatal(t);failure = creationFailure = t;}}}if (failure != null) {callback.onFailure(this, failure);return;}if (canceled) {call.cancel();}// step2call.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}}});}
注意step2,在DefaultCallAdapterFactory.ExecutorCallbackCall的enqueue方法暂且命名为enqueue1这里为enqueue2,执行的enqueue1实际上会来到enqueue2中,因为enqueue1中的call实际上是HttpCall类型,这里接收一个CallBack对象用于请求回调,我们知道网络请求肯定不能在主线程,这个时候一直说的excutor线程调度器就起作用了,当执行callback.onResponse或者callback.onFailure又会回到enqueue1中去,再利用excutor把线程给切会主线程中
到此一套完整的流程就结束了
CallAdapter的替换过程
之前讨论的是默认情况现在假如我们这样使用


我们通过addCallAdapterFactory添加了RxJava3CallAdapterFactory并且方法searchAndroidRepos返回的是Observable类型,现在重新回到HttpServiceMethod.parseAnnotations中直接看核心代码


最终还是来到retrofit的nextCallAdapter方法中,根据returnType Observable这个时候得到就是RxJava3CallAdapterFactory.get()返回的CallAdapter即:RxJava3CallAdapter,当然此时loadServiceMethod返回的HttpServiceMethod的具体实例还是CallAdapted,所以这个时候invoke最终会来到RxJava3CallAdapter的adapt方法中:
@Overridepublic Object adapt(Call<R> call) {//在这里把httpCall封装到Observable中了,剩下的也就是RxJava的事情了//不管怎样它最终还是会回到httpCall的enqueue中并且使用okhttp.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);}
到目前为止,CallAdapter 怎么变成一个 RxJava2CallAdapter 以及它的具体调用,我们也就清楚了
Retrofit怎样支持kotlin协程的
还是回到HttpServiceMethod.parseAnnotations中来
static <ResponseT, ReturnT> HttpServiceMethod<ResponseT, ReturnT> parseAnnotations(Retrofit retrofit, Method method, RequestFactory requestFactory) {boolean isKotlinSuspendFunction = requestFactory.isKotlinSuspendFunction;boolean continuationWantsResponse = false;// step1if (isKotlinSuspendFunction) {Type[] parameterTypes = method.getGenericParameterTypes();Type responseType = Utils.getParameterLowerBound(0,(ParameterizedType) parameterTypes[parameterTypes.length - 1]);if (getRawType(responseType) == Response.class && responseType instanceof ParameterizedType) {// Unwrap the actual body type from Response. responseType = Utils.getParameterUpperBound(0, (ParameterizedType) responseType);//step2continuationWantsResponse = true;} if (!isKotlinSuspendFunction) {return new CallAdapted<>(requestFactory, callFactory, responseConverter, callAdapter);} else if (continuationWantsResponse) {//step3return (HttpServiceMethod<ResponseT, ReturnT>) new SuspendForResponse<>(requestFactory,callFactory, responseConverter, (CallAdapter<ResponseT, Call<ResponseT>>) callAdapter);} }
这里精简了代码直接看最主要的
1、step1在RequestFactory.parseAnnotations中已经解释过了,如果方法是协程suspend那么会被置位true
2、continuationWantsResponse置为true
3、HttpServiceMethod的具体实例为SuspendForResponse
invoke方法都还是调用的HttpServiceMethod中的invoke,这个之前就说过,这里直接来看SuspendForResponse的adapt方法
static final class SuspendForResponse<ResponseT> extends HttpServiceMethod<ResponseT, Object> {private final CallAdapter<ResponseT, Call<ResponseT>> callAdapter;SuspendForResponse(RequestFactory requestFactory, okhttp3.Call.Factory callFactory,Converter<ResponseBody, ResponseT> responseConverter,CallAdapter<ResponseT, Call<ResponseT>> callAdapter) {super(requestFactory, callFactory, responseConverter);this.callAdapter = callAdapter;}@Override protected Object adapt(Call<ResponseT> call, Object[] args) {/*** step1* 注意这里的callAdapter还是默认的callAdapter即从DefaultCallAdapterFactory.get获取的* 所以这里的call实际上就是ExecutorCallbackCall*/call = callAdapter.adapt(call);/*** step2* args[args.length - 1]取最后一个参数* 强转为Continuation类型*/Continuation<Response<ResponseT>> continuation =(Continuation<Response<ResponseT>>) args[args.length - 1];try {// step3return KotlinExtensions.awaitResponse(call, continuation);} catch (Exception e) {return KotlinExtensions.yieldAndThrow(e, continuation);}}}
准备好了后会调用KotlinExtensions.awaitResponse(call, continuation)
suspend fun <T : Any> Call<T>.awaitResponse(): Response<T> {return suspendCancellableCoroutine { continuation ->continuation.invokeOnCancellation {cancel()}/*** 这里用到了kotlin的扩展函数的特性,然后调用了call的enqueue方法*/enqueue(object : Callback<T> {override fun onResponse(call: Call<T>, response: Response<T>) {continuation.resume(response)}override fun onFailure(call: Call<T>, t: Throwable) {continuation.resumeWithException(t)}})}
}
Continuation
这里解释一下KotlinExtensions.awaitResponse(call, continuation)这段代码
@GET("search/repositories?sort=stars&q=Android")suspend fun searchAndroidRepos2(@Query("per_page") per_page: Int,@Query("page") page: Int): RepoResponse

这两段代码和KotlinExtensions.awaitResponse的情况很相似都是java调用kotlin suspend方法的代码,awaitResponse方法没有参数为什么java调用需要传递两个参数
1、awaitResponse是Call的一个扩展方法java调用时候需要把Call对象传进去
2、java调用kotlin suspend方法的代码,需要在最后传递一个Continuation类型的参数
以上就是Retrofit对kotlin的支持
本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!
