Retrofit源码分析
来源:互联网 发布:淘宝隐形眼镜可以买吗 编辑:程序博客网 时间:2024/05/17 21:13
关于Retrofit,网上有很多源码分析,感觉好多都是泛泛而谈,当然好文章也有几篇,怀揣着瑟瑟发抖的心,我也走进了Retrofit源码的大门。。。。。
Retrofit retrofit = new Retrofit.Builder() .addConverterFactory(GsonConverterFactory.create()) .baseUrl(API_URL) .build();
首先,创建一个Retrofit对象,咱们一个方法一个方法的去看。首先看new Retrofit.Builder():
Builder(Platform platform) { this.platform = platform; // 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());}public Builder() { this(Platform.get());}
Platfrom.get() ????? 这是啥玩意?那我们来看Platform类:
private static final Platform PLATFORM = findPlatform();static Platform get() { return PLATFORM;}
private static Platform findPlatform() { try { Class.forName("android.os.Build"); if (Build.VERSION.SDK_INT != 0) { return new Android(); } } catch (ClassNotFoundException ignored) { } //省略n行代码。。。。。 return new Platform();}
static class Android extends Platform { @Override public Executor defaultCallbackExecutor() { return new MainThreadExecutor(); } @Override CallAdapter.Factory defaultCallAdapterFactory(Executor callbackExecutor) { return new ExecutorCallAdapterFactory(callbackExecutor); } static class MainThreadExecutor implements Executor { private final Handler handler = new Handler(Looper.getMainLooper()); @Override public void execute(Runnable r) { handler.post(r); } }}Android这个类继承了Platform, 类中重写了两个方法,第一个方法defaultCallbackExecutor(),return 了一个MainThreadExecutor对象,我们一眼就看出来了这个对象是干嘛的了,将消息发送给主线程,那肯定是刷新UI了。第二个方法先不管,等用到的时候再说。
再回到Retrofit类中,我们的得到:this.platform = new Android();
converterFactories.add(new BuiltInConverters());这个方法,看字面的意思,加入一个转换器,我们进入到BuiltInConverters中,确实也是这么回事,转换request,response,url的格式,先跳过这块,如果有时间我们再做分析。
Builder()分析完了,来看:
addConverterFactory(GsonConverterFactory.create())这个不多说了,将GsonConverterFactory也加入到咱们转换工厂的List中
.baseUrl(API_URL)设置咱们的访问域名
最后一个方法Build():
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> adapterFactories = new ArrayList<>(this.adapterFactories); adapterFactories.add(platform.defaultCallAdapterFactory(callbackExecutor)); // Make a defensive copy of the converters. List<Converter.Factory> converterFactories = new ArrayList<>(this.converterFactories); return new Retrofit(callFactory, baseUrl, converterFactories, adapterFactories, callbackExecutor, validateEagerly);}callFactory = new OkHttpClient(), 哦,原来Retrofit网络请求部分用的也是OkHttpClient,但是我们也能看出来我们可以自定义callFactory
platfrom.defaultCallbackEXecutor(); 刚才咱们分析过了,返回的是一个Executor, 这是retrofit默认给我提供的处理方式;如果我们在RxJava就不一样了
adapterFactories处理线程关系的list, 可以看到这个将callbackExecutor放到了defaultCallAdapterFactory中。
最后返回Retrofit对象。
ZhuanLanApi api = retrofit.create(ZhuanLanApi.class);我们进入create方法中:
public <T> T create(final Class<T> service) { Utils.validateServiceInterface(service); if (validateEagerly) { eagerlyValidateMethods(service); } return (T) Proxy.newProxyInstance(service.getClassLoader(), new Class<?>[] { service }, new InvocationHandler() { private final Platform platform = Platform.get(); @Override public Object invoke(Object proxy, Method method, 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); } ServiceMethod serviceMethod = loadServiceMethod(method); OkHttpCall okHttpCall = new OkHttpCall<>(serviceMethod, args); return serviceMethod.callAdapter.adapt(okHttpCall); } });}使用了动态代理
if (method.getDeclaringClass() == Object.class) { return method.invoke(this, args);}这个方法当时我觉得很奇怪,后来仔细琢磨一下,这个方法主要提供兼容用户调用hashCode等Object方法,看到这里,很感叹,作为一个成熟的网络框架,那么多人去
使用,细节很关键。
if (platform.isDefaultMethod(method)) { return platform.invokeDefaultMethod(method, service, proxy, args);}这个判断不用管,Android类中没有重写isDefaultMethod方法,始终返回false
ServiceMethod serviceMethod = loadServiceMethod(method);去创建ServiceMethod对象
ServiceMethod loadServiceMethod(Method method) { ServiceMethod result; synchronized (serviceMethodCache) { result = serviceMethodCache.get(method); if (result == null) { result = new ServiceMethod.Builder(this, method).build(); serviceMethodCache.put(method, result); } } return result;}这里巧妙的用了一个缓存,重点是build()方法:
public ServiceMethod build() { callAdapter = createCallAdapter(); responseType = callAdapter.responseType(); //省略n行代码。。。 responseConverter = createResponseConverter(); for (Annotation annotation : methodAnnotations) { parseMethodAnnotation(annotation); } //省略n行代码。。。 int parameterCount = parameterAnnotationsArray.length; parameterHandlers = new ParameterHandler<?>[parameterCount]; for (int p = 0; p < parameterCount; p++) { Type parameterType = parameterTypes[p]; if (Utils.hasUnresolvableType(parameterType)) { throw parameterError(p, "Parameter type must not include a type variable or wildcard: %s", parameterType); } Annotation[] parameterAnnotations = parameterAnnotationsArray[p]; if (parameterAnnotations == null) { throw parameterError(p, "No Retrofit annotation found."); } parameterHandlers[p] = parseParameter(p, parameterType, parameterAnnotations); } //省略n行代码。。。 return new ServiceMethod<>(this);}
callAdapter = createCallAdapter();进入createCallAdapter方法:
private CallAdapter<?> createCallAdapter() { Type returnType = method.getGenericReturnType(); //省略n行 Annotation[] annotations = method.getAnnotations(); try { return retrofit.callAdapter(returnType, annotations); } catch (RuntimeException e) { // Wide exception range because factories are user code. throw methodError(e, "Unable to create call adapter for %s", returnType); }}
method.getGenericReturnType()得到返回值类型(带泛型)
Annotation[] annotations = method.getAnnotations();得到方法的所有注解
retrofit.callAdapter方法中跳转到nextCallAdapter,所以我们直接来看nextCallAdapter方法
public CallAdapter<?> nextCallAdapter(CallAdapter.Factory skipPast, Type returnType, Annotation[] annotations) { checkNotNull(returnType, "returnType == null"); checkNotNull(annotations, "annotations == null"); int start = adapterFactories.indexOf(skipPast) + 1; for (int i = start, count = adapterFactories.size(); i < count; i++) { CallAdapter<?> adapter = adapterFactories.get(i).get(returnType, annotations, this); if (adapter != null) { return adapter; } } //省略n行。。。}
CallAdapter<?> adapter = adapterFactories.get(i).get(returnType, annotations, this);还记得我们向adapterFactories集合中存过ExecutorCallAdapterFactory对象,这段代码就是把它取出来,get()方法:
@Overridepublic CallAdapter<Call<?>> get(Type returnType, Annotation[] annotations, Retrofit retrofit) { if (getRawType(returnType) != Call.class) { return null; } final Type responseType = Utils.getCallResponseType(returnType); return new CallAdapter<Call<?>>() { @Override public Type responseType() { return responseType; } @Override public <R> Call<R> adapt(Call<R> call) { return new ExecutorCallbackCall<>(callbackExecutor, call); } };}返回了一个Call对象,responseType方法返回的是方法的泛型类型,
adapt返回的是ExecutorCallbackCall对象:
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) { if (callback == null) throw new NullPointerException("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); } }); } }); }
//省略n行代码。。。。
}
这个对象中包含enqueue方法,看到这里,相信你已经明白了。。。现在我们继续回到ServiceMethod中build()方法中:
responseType = callAdapter.responseType();这个刚才说过了。。
responseConverter = createResponseConverter();这里和adapterFactory一样的逻辑,就不提了。。。
for (Annotation annotation : methodAnnotations) { parseMethodAnnotation(annotation);}根据注解,来判断是什么请求。。。代码我就不贴了
return new ServiceMethod<>(this);最后将ServiceMethod对象返回。。。
OkHttpCall okHttpCall = new OkHttpCall<>(serviceMethod, args);return serviceMethod.callAdapter.adapt(okHttpCall);最后调用ExecutorCallbackCall对象的adapt方法
Call<text> call = api.getAuthor("1", "1");这时候就可以传参数请求网络了。。。。
大概的流程就是这样的,当然有很多细节,包括反射啊,注解啊等等。。。要说起来太多了,我觉得Retrofit是一个非常好的网络请求框架,它把工厂模式用淋漓极致,扩展性非常好。。
0 0
- Retrofit源码分析
- Retrofit源码分析
- Retrofit源码分析
- Retrofit源码简要分析
- Retrofit源码分析1
- Retrofit源码分析
- Retrofit 源码分析
- Retrofit源码分析
- Retrofit源码分析
- Retrofit 2.0源码分析
- Retrofit 源码分析
- Retrofit源码分析
- Retrofit的源码分析
- Retrofit 源码分析
- Retrofit 源码分析流程
- Retrofit源码分析
- Retrofit 源码简单分析
- Retrofit源码分析-前
- setlocal enabledelayedexpansion的作用
- Java工程通过JDBC连接数据库方法(SQL Server)
- 设计模式系列之十二状态模式
- CodeForces745B B - Hongcow Solves A Puzzle 暴力+判断
- Combination Sum
- Retrofit源码分析
- 3. Tomcat
- dos下 和 批处理中的 for 语句的基本用法
- iOS - Swift 自定义UITabBarController
- 文章标题
- 斐波那契数列-递归
- Windows下用breakpad抓取C++程序崩溃报告
- spring 注解
- 9Patch实例&详解缩放区域与内容显示区域