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

如何将含多参数的枚举添加到OpenAPI.json并保留参数关联?

问题描述

我有一个带多参数的枚举类:

public enum MyEnum {
   VALUE_1("value1_string_1", "value1_string_2");

   private final String argument1;
   private final String argument2;

   MyEnum (String argument1, String argument2) {
        this.argument1 = argument1;
        this.argument2 = argument2;
   }

   public String getArgument1() {
       return argument1;
   }

   public String getArgument2() {
       return argument2;
   }
}

作为REST API的DTO类会使用该枚举的两个参数值为自身字段赋值:field1对应argument1,field2对应argument2:

public class MyDTO {
  private String field1;
  private String field2;
  ...
}
...
MyDTO myDto = new MyDTO();
myDto.setField1(VALUE_1.getArgument1())
myDto.setField2(VALUE_1.getArgument2())

我需要把包含参数信息的枚举添加到openapi.json中,但尝试用@Schema(..., implementation = MyEnum.class) private String field1;时,生成的文档只包含枚举名称,没有参数信息:

"field1" : {
   "type" : "string",
   "enum" : [ "VALUE_1" ]
}

核心需求:

  • 必须保留argument1和argument2的关联关系,API使用者需要明确知道value1_string_1和value1_string_2是配对的
  • 枚举的参数信息要自动同步到openapi.json,不能靠手动加描述来维护
  • 曾考虑用@Schema(... ref = "#/components/schemas/MyEnum/properties/argument1" ) private String field1;,但如果枚举本身没出现在文档里,这个引用就无效

当前项目依赖的Swagger版本:

<dependency>
  <groupId>io.swagger.core.v3</groupId>
  <artifactId>swagger-annotations</artifactId>
  <version>2.2.7</version>
</dependency>
解决方案

1. 让Swagger识别枚举的完整结构

给MyEnum加上@Schema注解标记类本身,同时给两个私有字段也加上@Schema说明,这样Swagger会把枚举当成一个带属性的组件来处理:

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

@Schema(name = "MyEnum", description = "包含配对参数的自定义枚举")
public enum MyEnum {
   VALUE_1("value1_string_1", "value1_string_2");

   @Schema(description = "枚举的第一个参数值")
   private final String argument1;
   @Schema(description = "与argument1配对的第二个参数值")
   private final String argument2;

   MyEnum (String argument1, String argument2) {
        this.argument1 = argument1;
        this.argument2 = argument2;
   }

   public String getArgument1() {
       return argument1;
   }

   public String getArgument2() {
       return argument2;
   }
}

这一步会让MyEnum作为完整的schema出现在openapi.json的components/schemas里,包含两个参数的定义和具体枚举实例的配对值。

2. 在DTO中关联枚举的对应参数

修改MyDTO的字段注解,用ref直接引用枚举的属性,同时加上示例值强化关联关系:

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

public class MyDTO {
  @Schema(ref = "#/components/schemas/MyEnum/properties/argument1", 
          example = "value1_string_1",
          description = "对应MyEnum的argument1参数值")
  private String field1;

  @Schema(ref = "#/components/schemas/MyEnum/properties/argument2", 
          example = "value1_string_2",
          description = "对应MyEnum的argument2参数值,与field1配对")
  private String field2;
  ...
}

3. 确保枚举被Swagger扫描到

如果枚举类不在Swagger默认扫描的包路径下,得在Swagger配置里手动把枚举所在的包加进去(以Spring项目为例):

import org.springdoc.core.GroupedOpenApi;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class SwaggerConfig {
    @Bean
    public GroupedOpenApi publicApi() {
        return GroupedOpenApi.builder()
                .group("public-api")
                .packagesToScan("com.yourproject.enums", "com.yourproject.dto") // 替换成你的枚举和DTO所在包
                .build();
    }
}

4. 验证最终效果

生成的openapi.json里,components/schemas会有MyEnum的完整定义:

"MyEnum": {
  "type": "object",
  "properties": {
    "argument1": {
      "type": "string",
      "description": "枚举的第一个参数值"
    },
    "argument2": {
      "type": "string",
      "description": "与argument1配对的第二个参数值"
    }
  },
  "enum": [
    {
      "argument1": "value1_string_1",
      "argument2": "value1_string_2"
    }
  ]
}

同时MyDTO的字段会正确关联到枚举的参数,API使用者能清晰看到value1_string_1和value1_string_2的配对关系,而且枚举更新时文档会自动同步。

备选方案:自定义处理枚举的转换器

如果上面的方法没生效,还可以写个自定义的ModelConverter来强制生成枚举的属性结构:

import io.swagger.v3.core.converter.AnnotatedType;
import io.swagger.v3.core.converter.ModelConverter;
import io.swagger.v3.core.converter.ModelConverterContext;
import io.swagger.v3.oas.models.media.Schema;

import java.util.Iterator;

public class EnumSchemaConverter implements ModelConverter {
    @Override
    public Schema resolve(AnnotatedType type, ModelConverterContext context, Iterator<ModelConverter> chain) {
        Schema schema = chain.next().resolve(type, context, chain);
        // 只处理MyEnum类型的枚举
        if (type.getType() == MyEnum.class) {
            schema.setType("object");
            schema.addProperty("argument1", new Schema().type("string").description("枚举第一个参数"));
            schema.addProperty("argument2", new Schema().type("string").description("枚举第二个参数"));
            
            // 遍历枚举实例,添加配对值
            for (MyEnum enumVal : MyEnum.values()) {
                schema.addEnumItem(new Object() {
                    public final String argument1 = enumVal.getArgument1();
                    public final String argument2 = enumVal.getArgument2();
                });
            }
        }
        return schema;
    }
}

然后在配置类里注册这个转换器:

import io.swagger.v3.core.converter.ModelConverters;
import jakarta.annotation.PostConstruct;
import org.springframework.context.annotation.Configuration;

@Configuration
public class SwaggerConfig {
    @PostConstruct
    public void setupEnumConverter() {
        ModelConverters.getInstance().addConverter(new EnumSchemaConverter());
    }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.17 16:25:00