Retrofit中@Body的使用
来源:互联网 发布:于正 知乎 编辑:程序博客网 时间:2024/05/17 03:45
关于Retrofit的参数标签@Field、@Path、@Query等等的使用网上已经有很多文章了,可是关于@Body的使用不仅少而且还都是略微的带过,这里就说下Body的用法。
首先@Body的作用是把对象转换成需要的字符串发送到服务器,明白这一点就能对应实际的需要了,比如服务端需要的是关于某一个自定义对象的JSON数据格式,当然服务端若也是Java开发的,那这段JSON能通过工具能自动生成想要的对象,额,其他语言的也能;说了些题外话,主要想说明对象转字符串,当然转化就需要有个转换器——Converter,这个Converter是一个接口,由Retrofit提供,我们定义一个类WrapperConverter implements Converter,如下:
public class WrapperConverter implements Converter { private static final String CHARSET_DEFAULT = "utf-8"; private Gson gson; @Override public Object fromBody(TypedInput body, Type type) throws ConversionException {...return obj; }public Gson getGson(){ if (gson==null)gson = new Gson(); return gson; } @Override public TypedOutput toBody(Object o) { if (o instanceof List) { try { String postNames = o.toString(); postNames = postNames.substring(1, postNames.length() - 1); return new ArrayTypedOutPut(postNames.getBytes(CHARSET_DEFAULT), CHARSET_DEFAULT); } catch (UnsupportedEncodingException e) { throw new AssertionError(e); } } else { try { return new JsonTypedOutPut(getGson().toJson(o).getBytes(CHARSET_DEFAULT), CHARSET_DEFAULT); } catch (UnsupportedEncodingException e) { throw new AssertionError(e); } } } private static class JsonTypedOutPut implements TypedOutput { private final byte[] jsonBytes; private final String mimeType; public JsonTypedOutPut(byte[] jsonBytes, String encode) { this.jsonBytes = jsonBytes; this.mimeType = "application/json; charset=" + encode; } @Override public String fileName() { return null; } @Override public String mimeType() { return mimeType; } @Override public long length() { return jsonBytes.length; } @Override public void writeTo(OutputStream out) throws IOException { out.write(jsonBytes); } } private static class ArrayTypedOutPut implements TypedOutput { private final byte[] arrayBytes; private final String mimeType; public ArrayTypedOutPut(byte[] arrayBytes, String encode) { this.arrayBytes = arrayBytes; this.mimeType = "application/text; charset=" + encode; } @Override public String fileName() { return null; } @Override public String mimeType() { return mimeType; } @Override public long length() { return arrayBytes.length; } @Override public void writeTo(OutputStream out) throws IOException { out.write(arrayBytes); } }}
fromBody是处理接收数据的,就比如像上面说的从JSON转换成Object,这个不是这里要说的重点;看toBody函数,这个函数里面就是处理对象转换字符串(当然不仅限于字符串),代码中的toBody可以把元素为String的List转成逗号分隔的字符串或者将Object转成JSON;好了,基础工作做完了,看下怎么在interface里面使用:
@POST("add")void GG(@Body List ggs, Callback<String> callback)@PUT("add")void GG(@Body List mms, Callback<String> callback)注意:@Body不能与@FormUrlEncoded共用,否则报错;而@Field偏偏是提交表单使用的,需要@FormUrlEncoded,这很明白了,根据数学的某个公理得出@Body和@Field也是不能同时使用的。
在Retrofit的定义中,POST、PUT、、PATCH请求允许使用Body,如果我们的DELETE请求想使用Body是不被通过的,怎么办呢,用我们自定义的DELETE注释。下面是一源码,可以参考:
@Documented@Target(METHOD)@Retention(RUNTIME)@RestMethod(value = "DELETE", hasBody = true)public @interface DELETE { String value();}这是自定义的,Retrofit提供的DELETE没有hasBody = true,也就说它内部对DELETE的处理默认是不接收Body的,按上面做就行了
以上的处理都是基于Retrofit1.9的,2.0也有对应的转化器部分,自行解决就好
若有不恰当的地方,欢迎拍砖
1 4
- Retrofit中@Body的使用
- android Retrofit框架使用@body上传数据,服务端接收数据为空的解决办法
- android开发中Retrofit的使用
- Retrofit中如何正确的使用https?
- Retrofit学习使用中犯的错
- Retrofit中https的正确使用
- Retrofit中如何正确的使用https?
- 在retrofit+Rxjava中如何取得状态码非200(出现错误)时的response里的body
- 在retrofit+Rxjava中如何取得状态码非200(出现错误)时的response里的body
- Android retrofit 注解@QueryMap和@Body的区别
- 【Box2D】Box2d中关于body的一些使用
- Retrofit 的使用
- retrofit 的使用。
- Retrofit 的使用简介
- Retrofit的使用封装
- retrofit的使用
- Retrofit的简单使用
- retrofit的使用
- C#中线程的使用(一):通过委托开启一个线程
- iOS 在地图上绘制运动轨迹
- NodeJS HTTP模块编写POST提交表单Demo
- 方格填数 (搜索)
- HDU_1058 && HDU_3199(指针 + dp)
- Retrofit中@Body的使用
- Simhash学习笔记
- Notification踩过的坑
- HTML5知识
- hdu 2874
- 大型网站Session管理
- JS简单实现图片上一张下一张操作
- 汇编指令和机器码的对应表
- iOS 源代码分析 --- MBProgressHUD