转自:
Retrofit 2.0 自定义Converter
本文原创作者:一叶飘舟 作者博客地址:http://blog.csdn.net/jdsjlzx
Annotation
我们在重写requestBodyConverter
和responseBodyConverter
方法时,有时候单凭Type是无法进行判断,信息不够,这时候,就需要使用方法参数里的额外参数进行判断了:
我们先看requestBodyConverter
的函数签名:
public Converter<?, RequestBody> requestBodyConverter(
Type type,
Annotation[] parameterAnnotations,
Annotation[] methodAnnotations,
Retrofit retrofit)
其中 parameterAnnotations
是定义才接口的方法参数里的注解,如下面的@Query
,@TypeString
:,以及@Body
等
@GET("applist/mini-appcenter/")
Call<MiniAppCenterPojo> getMiniApp(@Query("offsets") @TypeString String offsets);
methodAnnotations
是定义在方法上的注解:比如下面的@GET
,TypeString
注解
@TypeString
@GET("applist/mini-appcenter/")
Call<MiniAppCenterPojo> getMiniApp(@Query("offsets") String offsets);
再来看看responseBodyConverter
的函数签名:
public Converter<ResponseBody, ?> responseBodyConverter(
Type type,
Annotation[] annotations,
Retrofit retrofit)
responseBodyConverter
是: convert(转换)返回数据时,不再涉及到请求时,上行数据的处理,因此,上面的annotations
是方法上的注解,比如:
@MarkMethod()
@POST("gl")
Call<PubkeyResponse> getPubPriKey3(@Body @MarkParam PubPriKey pubPriKey);
上面代码中的: @markMethod
和 @POAT("gl")
P.S. 既然我们能取到参数上 和 方法上的注解,那么就可以同过自定义注解,来约束和区分使用哪个自定义ConverterFactory了,比如上面的@TypeString,就是作者自己定义的一个注解
下面是一个简单的StringConverFactory
public class StringConverterFactory extends Converter.Factory {
@Override
public Converter<ResponseBody, ?> responseBodyConverter(Type type, Annotation[] annotations, Retrofit retrofit) {
if (!(type instanceof Class<?>)) {
return null;
}
for (Annotation annotation : annotations) {
if (annotation instanceof TypeString) {
return new StringResponseConverter();
}
}
return null;
}
@Override
public Converter<?, RequestBody> requestBodyConverter(Type type, Annotation[] parameterAnnotations, Annotation[] methodAnnotations, Retrofit retrofit) {
if (!(type instanceof Class<?>)) {
return null;
}
for (Annotation annotation : parameterAnnotations) {
if (annotation instanceof TypeString) {
return new StringRequestConverter();
}
}
return null;
}
public static class StringResponseConverter implements Converter<ResponseBody, String> {
@Override
public String convert(ResponseBody value) throws IOException {
return value.string();
}
}
public static class StringRequestConverter implements Converter<String, RequestBody> {
@Override
public RequestBody convert(String value) throws IOException {
return RequestBody.create(MediaType.parse("application/octet-stream"), value);
}
}
}
其中(下面的说法,再第三篇: Retrofit - 自定义ConverterFactory (三),有具体说明)
-
public Converter<ResponseBody, ?> responseBodyConverter(Type type, Annotation[] annotations, Retrofit retrofit)
type是Call<T> Observable<T> 里面的泛型,annotations 是方法上的注解,由于返回数据不涉及上行数据的处理,因此不可能是方法参数的注解 -
public Converter<?, RequestBody> requestBodyConverter(Type type, Annotation[] parameterAnnotations, Annotation[] methodAnnotations, Retrofit retrofit)
里面的type 是方法参数里面的Class类型
小结:
本节重点是,responseBodyConverter (...)
和 requestBodyConverter (...)
方法参数中的理解,
我们可以通过对type
的判断,及annotation[ ]
,parameterAnnotations[ ]
注解,来决定我们是否要convert(转换) ResponsBody 或者 ResponseBody