Retrofit系列文章翻译8—自定义一个响应转换器

原文链接:https://futurestud.io/blog/retrofit-send-objects-in-request-body
本篇介绍了在 Retrofit 里如何设置自定义 JSON 转换器。下面的列表显示了该系列的所有文章:

在 Retrofit 2里实现自定义响应转换器是一个复杂的过程. 我们一定会写一篇关于如何在 Retrofit 2中创建和集成自己的响应转换器的另一篇博客. 一旦发布,我们将在此处链接和更新本说明。(原文评论里提到 Retrofit 2的自定义转换器教程不会公开发布了, 有读者自己做了实现, 可以参考, 译者注)

Retrofit 系列目录

  1. 开始创建android客户端[已翻译]
  2. Android上的基本认证[已翻译]
  3. Android上的令牌认证[已翻译]
  4. Android上的OAuth
  5. 多个 Query 参数使用同一名字[已翻译]
  6. 同步与异步请求[已翻译]
  7. 在请求体里发送对象[已翻译]
  8. 自定义一个响应转换器
  9. 添加自定义请求头
  10. 可选的 Query 参数
  11. 如何集成 XML 转换器
  12. 使用 Log Level 调试请求
  13. 如何上传文件
  14. Series Round-Up
  15. Retrofit 2 — 1.9 升级指南
  16. Retrofit 2 — 如何上传文件
  17. Retrofit 2 — Log 请求与响应
  18. Retrofit 2 — Android 上的 Hawk 认证
  19. Retrofit 2 — 简单错误处理
  20. 如何在 Retrofit 1 里使用 OkHttp 3
  21. Retrofit 2 — 图书更新发布庆典
  22. 提交表单数据 — Urlencoded
  23. 提交表单数据 — Urlencoded 使用FieldMap
  24. Retrofit 2 — 在 OkHttp 拦截器里管理请求头部
  25. Retrofit 2 — 如何给每一个请求添加 Query 参数
  26. Retrofit 2 — 使用QueryMap 添加多个 Query 参数
  27. Retrofit 2 — 如何在请求时使用动态 Url
  28. Retrofit 2 — Url 处理,分辨和解析
  29. Retrofit 2 — POST 和PUT 请求里的常量, 默认值和逻辑值
  30. Retrofit 2 — 如何下载文件
  31. Retrofit 2 — 取消请求
  32. Retrofit 2 — 重用分析请求
  33. Retrofit 2 — 如何在运行时修改 API Base Url
  34. 可选Path参数
  35. 如何刷新 Access Token
  36. Retrofit 2 — 如何提交文本请求体
  37. Retrofit 2 — 使用 Query 参数来分页
  38. Retrofit 2 — 使用 链接头和动态 Url 来分页(比如GitHub)
  39. Retrofit 2 — 使用范围头字段来分页 (比如 Heroku)
  40. Retrofit 2 — 转换器介绍
  41. Retrofit 2 — 添加并自定义 Gson 转换器
  42. Retrofit 2 — 实现自定义转换器
  43. Retrofit 2 — 只在开发环境里启用日志
  44. Retrofit 2 — 如何上传多个文件
  45. Retrofit 2 — Passing Multiple Parts Along a File with @PartMap
  46. Retrofit 2 — 模仿服务端响应基本概念
  47. Retrofit 2 — 模仿服务端响应自定义网络行为
  48. Retrofit 2 — 使用 @HeaderMap 定义动态请求头

基础

Retrofit 默认附带了 Google's JSON. 每个JSON映射都在GSON的帮助下完成. 有时候,你的框架或属性需要改变集成的JSON转换器. 一个著名的转换器是 Jackson. 我们将使用 Jackson 做为代码示例.

现有的 Retrofit 转换器

除了 GSON, Retrofit 可被配置成各种内容格式. retrofit-converters 目录列出了现有的响应转换器:

  • JSON (使用Jackson)
  • XML (使用Simple)
  • Protocol Buffers (使用 protobuf 或者 Wire)

与gradle的整合可以用以下命令来完成:

compile 'com.squareup.retrofit:converter-:1.9.0'

# e.g. Jackson
compile 'com.squareup.retrofit:converter-jackson:1.9.0'

# e.g. XML
compile 'com.squareup.retrofit:converter-simplexml:1.9.0' 

你应该知道如何整合 protocol buffers :)

创建你自己的转换器

一旦你需要或想要创建自己的 Retrofit 响应转换器,你可以按照下面的步骤. 我们将使用 Jackson 库来说明具体的定义和处理.
记住: 目前已有的 Retrofit 转换器 你可以通过集成各自的gradle依赖直接使用它们.

Jackson Gradle 依赖

首先, 定义 Jackson 依赖. 本例使用的是 Jackson 2.x ,与以前的 Jackson 1.x 有很大的不同. 添加需要的 Maven 库和编译依赖.

repositories {  
    maven { url "http://repository.codehaus.org/org/codehaus" }
}

dependencies {  
    compile 'com.fasterxml.jackson.core:jackson-databind:2.4.3'
}

实现自定义的 JSON 转换器

替换 Retrofit 的 JSON 转换器最重要的部分是实现 Converter 接口并覆盖两个方法: fromBody and toBody.

public class JacksonConverter implements Converter {
    private ObjectMapper mapper = new ObjectMapper();

    @Override
    public Object fromBody(TypedInput body, Type type) throws ConversionException {
        JavaType javaType = mapper.getTypeFactory().constructType(type);

        try {
            return mapper.readValue(body.in(), javaType);
        } catch (IOException e) {
            throw new ConversionException(e);
        }
    }

    @Override
    public TypedOutput toBody(Object object) {
        try {
            String charset = "UTF-8";
            String json = mapper.writeValueAsString(object);
            return new JsonTypedOutput(json.getBytes(charset));
        } catch (IOException e) {
            throw new AssertionError(e);
        }
    }

    private static class JsonTypedOutput implements TypedOutput {
        private final byte[] jsonBytes;

        JsonTypedOutput(byte[] jsonBytes) { this.jsonBytes = jsonBytes; }

        @Override public String fileName() { return null; }
        @Override public String mimeType() { return "application/json; charset=UTF-8"; }
        @Override public long length() { return jsonBytes.length; }
        @Override public void writeTo(OutputStream out) throws IOException { out.write(jsonBytes); }
    }
}

JsonTypedOutput 类被用来设置正确的 mimeType. 由于输出类型是JSON, mime 类型也应该是 application/json.

设置自定义JSON转换器

Retrofit 的 JSON转换器被集成在RestAdapter里. 通过调用RestAdapter对象的setConverter()方法可以改变转换器. 此外, 当创建 rest 客户端时, 你可以在RestAdapter的构建过程里直接设置转换器来集成 jackson 转换器.

    // Create our Converter
    JacksonConverter jacksonConverter = new JacksonConverter();

    // Build the Retrofit REST adaptor pointing to the URL specified, with the Converter.
    // Note: The Converter must be set before the .build() command
    RestAdapter restAdapter = new RestAdapter.Builder()
        .setConverter(jacksonConverter)
        .setEndpoint("https://api.example.com/")
        .build();

干得漂亮! 以后你创建的所有RestAdapter都将使用 JacksonConverter 来处理 JSON.

如果你遇到任何问题或困难, 请 Twitter @futurestud_io.

你可能感兴趣的:(Retrofit系列文章翻译8—自定义一个响应转换器)