1.Retrofit的原理是什么
Retrofit是一个基于AOP思想,对RestfulApi注解进行动态代理的网络框架。
2.AOP是什么
Aspect Oriented Programming 面向切面编程。
面向切片编程是编程实践中的解耦利器,能够极大的减少对象的创建,
AOP的思想是在不影响主体逻辑的前提下,动态的插入逻辑,利用反射进行调用。在执行频度不是很高的前提下,很多辅助代码都可以采用这种方式实现。
3.动态代理
以往我们实现代理的方式是定义一个接口,写一个真实实现类和一个代理类,这种方法我们称之为静态代理。这种方式的弊端是,当有很多类需要代理时,需要实现多个代理类。
而利用AOP,我们可以将代理实现的很优雅,只需要一个代理类就可以。这种方式我们称之为动态代理。
public interface IWork {
void doWork();
}
定义接口public class Coder implements IWork {
@Override
public void doWork() {
Log.i("AOP", "码农写代码");
}
}
public class Student implements IWork {
@Override
public void doWork() {
Log.i("AOP","学生学习");
}
}
实现接口public class DynamicProxy implements InvocationHandler {
//代理类
private Object target;
/**
* 绑定委托对象并返回一个代理类
* @param target
* @return
*/
public Object bind(Object target) {
this.target = target;
return Proxy.newProxyInstance(target.getClass().getClassLoader(), target.getClass().getInterfaces(), this);
}
/**
* @param proxy 被代理的对象。
* @param method:要调用的方法
* @param args:方法调用时所需要的参数
*/
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
Object result = null;
// 切面插入前
Log.i("AOP","代理逻辑插入前");
// 执行真实类逻辑
result = method.invoke(target, args);
// 切面插入后
Log.i("AOP","代理逻辑插入后");
return result;
}
}
代理类 IWork iWork = (IWork) new DynamicProxy().bind(new Coder());
iWork.doWork();
iWork = (IWork) new DynamicProxy().bind(new Student());
iWork.doWork();
代码应用一个代理类同时代理了Coder和Student两个实体类。
说了这么多,回归正题。
Retrofit就是利用这种动态代理的方式实现的,下面我们看源码。
public interface RetrofitAPI {
@Headers({"Accept:application/x.vr.v1.0.1+json"})
@POST("rest/find")
@FormUrlEncoded
Call<AppListEntity> getAppList(@Header("Authorization") String token, @FieldMap Map<String, Object> map);
}
定义接口RetrofitAPI api = retrofit.create(RetrofitAPI.class);
接口代理实现 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);
}
});
}
Retrofit create方法利用泛型实现了动态代理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;
}
这个方法用来解析Retrofit的注解,生成相应的method方法
OkHttpCall okHttpCall = new OkHttpCall<>(serviceMethod, args);
return serviceMethod.callAdapter.adapt(okHttpCall);
最终被OkHttp调用。有兴趣的可以研究一下Retrofit的注解是如何解析的。
参考文章
感谢yanbin对AOP的讲解
http://www.cnblogs.com/yanbincn/archive/2012/06/01/2530377.html
版权声明:本文为jasonwang18原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。