Moshi配合Retrofit序列化动态内部类如何避免转义和额外字段?
问题根因
- 之前的自定义适配器
toJson方法返回String类型,Moshi会将该字符串作为JSON字符串值处理,自动添加外层引号、转义内部双引号,属于预期行为,不是bug。 PolymorphicJsonAdapterFactory强制要求添加类型标识字段用于反序列化区分,无法满足无额外字段的纯序列化需求。
解决方案
直接改写自定义适配器,通过JsonWriter直接控制序列化输出,不需要返回字符串,Moshi不会额外包裹内容,也不会添加多余字段:
import com.squareup.moshi.JsonWriter import com.squareup.moshi.Moshi import com.squareup.moshi.ToJson class AnimalAttributesAdapter { @ToJson fun toJson(writer: JsonWriter, value: AnimalAttributes?, moshi: Moshi) { // 空值处理 if (value == null) { writer.nullValue() return } // 按实际类型获取对应子类的自动生成适配器 val adapter = when (value) { is DogAttributes -> moshi.adapter(DogAttributes::class.java) is CatAttributes -> moshi.adapter(CatAttributes::class.java) else -> throw UnsupportedOperationException("不支持的属性类型: $value") } // 直接将子类序列化结果写入当前节点 adapter.toJson(writer, value) } }
配置方式
保持原有Moshi配置逻辑即可,无需其他改动:
val moshi = Moshi.Builder() .add(AnimalAttributesAdapter()) // 其他适配器配置 .build()
序列化效果
传入DogAttributes实例的最终请求体符合预期:
{"name":"my pet name","attributes":{"bark":true,"bite":false}}
注意事项
保留各子类的@JsonClass(generateAdapter = true)注解,Moshi会使用自动生成的高性能适配器完成子类序列化,无需手动处理字段映射。
内容的提问来源于stack exchange,提问作者mtrakal
相关产品推荐
相关产品推荐

