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

如何让OpenAPI Generator将Kotlin的Any类型生成为Any而非JsonObject?

解决Kotlin中Map<String, Any>在OpenAPI Generator中生成JsonObject的问题

问题核心

你当前的问题是:Kotlin DTO里的Map<String, Any>字段,生成OpenAPI规范时被限定为additionalProperties: {"type": "object"},导致OpenAPI Generator输出Map<String, JsonObject>,使用起来需要额外转换,且Jackson转换报错。

解决方案

1. 修正OpenAPI规范定义

首先要让OpenAPI规范正确反映Map<String, Any>的语义——值可以是任意JSON类型(字符串、数字、布尔、对象、数组、null),而不是仅允许对象类型。

将原来的spec片段:

"payload": {
  "type": "object",
  "additionalProperties": {
    "type": "object"
  }
}

修改为以下两种方式之一:

  • 简洁版(允许任意类型):
"payload": {
  "type": "object",
  "additionalProperties": true
}
  • 明确版(枚举所有支持的类型):
"payload": {
  "type": "object",
  "additionalProperties": {
    "anyOf": [
      {"type": "string"},
      {"type": "number"},
      {"type": "integer"},
      {"type": "boolean"},
      {"type": "object"},
      {"type": "array"},
      {"type": "null"}
    ]
  }
}

2. 调整OpenAPI Generator配置

针对Kotlin + kotlinx.serialization的场景,需要配置生成器将任意类型映射为更通用的类型,而非JsonObject:

  • 使用命令行时添加参数:
openapi-generator-cli generate \
  -i openapi-spec.json \
  -g kotlin \
  --additional-properties=serializationLibrary=kotlinx_serialization,mapAnyToJsonElement=false
  • 或者用配置文件(如config.yaml):
generatorName: kotlin
additionalProperties:
  serializationLibrary: kotlinx_serialization
  mapAnyToJsonElement: false

这样生成的类会变成:

@Serializable
public data class EventPayloadDto(
    @SerialName(value = "payload")
    val payload: kotlin.collections.Map<kotlin.String, Any>? = null,
)

3. 从Kotlin代码生成规范时的注解调整

如果你的OpenAPI规范是从Kotlin代码自动生成的(比如用SpringDoc、Ktor OpenAPI插件),给payload字段添加注解来控制生成的spec:

import io.swagger.v3.oas.annotations.media.Schema

data class EventDto(
  @Schema(additionalProperties = true)
  val payload: Map<String, Any>,
  // ...其他字段
)

这会让生成的spec自动使用additionalProperties: true,避免被限定为仅对象类型。

4. 序列化/反序列化的正确姿势

不要混合使用Jackson和kotlinx.serialization,针对生成的Map<String, Any>或Map<String, JsonElement>,直接用kotlinx.serialization的API处理:

  • 序列化:
import kotlinx.serialization.encodeToString
import kotlinx.serialization.json.Json

val payloadJson = Json.encodeToString(event.payload)
  • 反序列化:
val payloadMap: Map<String, Any> = Json.decodeFromString(payloadJson)

如果需要更灵活的类型处理,也可以改用Map<String, JsonElement>作为DTO字段,它能直接兼容所有JSON类型,且kotlinx.serialization原生支持,不需要额外转换。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.11 19:40:41