You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Ktor中反序列化含不同类型列表的JSON响应?

解决方案

1. 重构数据类:使用泛型Result类

将重复的ResultOne和ResultTwo替换为单一泛型Result类,通过类型占位符兼容不同的列表元素类型:

@Serializable
data class Result<T>(
    val count: Int,
    val result: List<T>
)

@Serializable
data class TypeOne(
   val str1: String,
   val str2: String,
   val int1: Int
)

@Serializable
data class TypeTwo(
    val str1: String,
    val dbl1: Double,
    val int1: Int
)

2. 复用HTTP请求方法:泛型+Reified类型

借助Kotlin的reified泛型特性,让Ktor在运行时获取具体序列化类型,实现请求方法的完全复用:

// 保留原HttpClient配置
private val httpClient = HttpClient {    
    install(ContentNegotiation) {
        json(Json{
            isLenient = true
            ignoreUnknownKeys = true
        })
    }
}

// 泛型请求方法,reified关键字让编译器保留类型信息
private suspend inline fun <reified T> fetchResults(ints: List<Int>): Result<T> {
    return httpClient.get("https://my.api.com/search") {
        // 可在这里统一处理查询参数,比如传入的ints列表
        url {
            parameters.appendAll("ids", ints.map { it.toString() })
        }
    }.body()
}

// 调用示例
fun getResultTypeOne() {
    val response = runBlocking { fetchResults<TypeOne>(listOf(1,2)).result }
}

fun getResultTypeTwo() {
    val response = runBlocking { fetchResults<TypeTwo>(listOf(1,2)).result }
}

核心说明

  • 泛型Result类:通过<T>抽象列表元素类型,彻底消除结构重复的Result类定义。
  • Reified泛型:inline fun <reified T>让Kotlin编译器在编译期保留T的具体类型,确保Ktor能正确调用Kotlinx Serialization的序列化器,完成JSON到目标类型的解析。
  • 扩展灵活性:如果不同类型请求需要差异化参数,可在fetchResults中添加参数判断逻辑,或直接传入参数配置块,进一步提升复用性。

内容的提问来源于stack exchange,提问作者user4414119

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.08 23:56:10