在 Spring Boot 3.x 中使用 SpringDoc 2 / Swagger V3

SpringDoc V1 只支持到 Spring Boot 2.x

springdoc-openapi v1.7.0 is the latest Open Source release supporting Spring Boot 2.x and 1.x.

Spring Boot 3.x 要用 SpringDoc 2 / Swagger V3, 并且包名也改成了 springdoc-openapi-starter-webmvc-ui

SpringDoc V2 https://springdoc.org/v2/

配置

增加 Swagger 只需要在 pom.xml 中添加依赖

xml 复制代码
<dependency>
  <groupId>org.springdoc</groupId>
  <artifactId>springdoc-openapi-starter-webmvc-ui</artifactId>
  <version>2.3.0</version>
</dependency>

Spring Boot 启动时就会自动启用 Swagger, 从以下地址可以访问 接口形式(JSON, YAML)和WEB形式的接口文档

如果要关闭, 启用, 自定义接口地址, 在 application.yml 中添加配置

复制代码
springdoc:
  api-docs:
    path: /v3/api-docs
    enabled: false

对应WEB地址的配置为

复制代码
springdoc:
  swagger-ui:
    path: /swagger-ui.html
    enabled: false

因为WEB界面的显示基于解析JSON接口返回的结果, 如果api-docs关闭, swagger-ui即使enable也无法使用

在开发和测试环境启动服务时, 可以用VM参数分别启用

复制代码
# in VM arguments
-Dspringdoc.api-docs.enabled=true -Dspringdoc.swagger-ui.enabled=true

使用注解

@Tag

Swagger3 中可以用 @Tag 作为标签, 将接口方法进行分组. 一般定义在 Controller 上, 如果 Controller 没用 @Tag 注解, Swagger3 会用Controller的类名作为默认的Tag, 下面例子用 @Tag 定义了一个"Tutorial"标签, 带有说明"Tutorial management APIs", 将该标签应用于TutorialController后, 在 Swagger3 界面上看到的这个 Controller 下面的方法集合就是 Tutorial.

java 复制代码
@Tag(name = "Tutorial", description = "Tutorial management APIs")
@RestController
@RequestMapping("/api")
public class TutorialController {
  //...
}

也可以将 @Tag 添加到单独的方法上, 这样在 Swagger3 界面上, 就会将这个方法跟同样是 Tutorial 标签的其它方法集合在一起.

java 复制代码
public class AnotherController {
  @Tag(name = "Tutorial", description = "Tutorial APIs")
  @PostMapping("/tutorials")
  public ResponseEntity<Tutorial> createTutorial(@RequestBody Tutorial tutorial) {
    //...
  }
}

@Operation

Swagger3中 @Operation注解用于单个API方法. 例如

java 复制代码
public class MoreController {

  @Operation(
      summary = "Retrieve a Tutorial by Id",
      description = "Some description",
      tags = { "tutorials", "get" })
  @GetMapping("/tutorials/{id}")
  public ResponseEntity<Tutorial> getTutorialById(@PathVariable("id") long id) {
    //...
  }
}

tags = { "tutorials", "get" }可以将一个方法放到多个Tag分组中

@ApiResponses 和 @ApiResponse

Swagger3 使用 @ApiResponses 注解标识结果类型列表, 用@ApiResponse注解描述各个类型. 例如

java 复制代码
    public class AnotherController {
    @ApiResponses({
        @ApiResponse(
                responseCode = "200",
                content = { @Content(schema = @Schema(implementation = UserBO.class), mediaType = "application/json") }),
        @ApiResponse(
                responseCode = "404",
                description = "User not found.", content = { @Content(schema = @Schema()) })
    })
    @GetMapping("/user/{id}")
    public ResponseEntity<UserBO> getUserById(@PathVariable("id") long id) {
        return null;
    }
}

@Parameter

@Parameter注解用于描述方法参数, 例如:

java 复制代码
@GetMapping("/tutorials")
public ResponseEntity<Map<String, Object>> getAllTutorials(
  @Parameter(description = "Search Tutorials by title") @RequestParam(required = false) String title,
  @Parameter(description = "Page number, starting from 0", required = true) @RequestParam(defaultValue = "0") int page,
  @Parameter(description = "Number of items per page", required = true) @RequestParam(defaultValue = "3") int size) {
    //...
}

@Schema annotation

Swagger3 用 @Schema 注解对象和字段, 以及接口中的参数类型, 例如

java 复制代码
@Schema(description = "Tutorial Model Information")
public class Tutorial {

  @Schema(accessMode = Schema.AccessMode.READ_ONLY, description = "Tutorial Id", example = "123")
  private long id;

  @Schema(description = "Tutorial's title", example = "Swagger Tutorial")
  private String title;

  // getters and setters
}

accessMode = Schema.AccessMode.READ_ONLY用于在接口定义中标识字段只读

实例

定义接口

java 复制代码
@Tag(
        name = "CRUD REST APIs for User Resource",
        description = "CRUD REST APIs - Create User, Update User, Get User, Get All Users, Delete User"
)
@Slf4j
@RestController
public class IndexController {

    @Operation(summary = "Get a user by its id")
    @GetMapping(value = "/user_get")
    public String doGetUser(
            @Parameter(name = "id", description = "id of user to be searched")
            @RequestParam(name = "id", required = true)
            String id) {
        return "doGetUser: " + id;
    }

    @Operation(summary = "Add a user")
    @PostMapping(value = "/user_add")
    public String doAddUser(
            @io.swagger.v3.oas.annotations.parameters.RequestBody(description = "User to add.", required = true)
            @RequestBody UserBO user) {
        return "doAddUser: " + user.getName();
    }
    
    @ApiResponses({
            @ApiResponse(
                    responseCode = "200",
                    content = { @Content(schema = @Schema(implementation = UserBO.class), mediaType = "application/json") }),
            @ApiResponse(
                    responseCode = "404",
                    description = "User not found.", content = { @Content(schema = @Schema()) })
    })
    @GetMapping("/user/{id}")
    public ResponseEntity<UserBO> getUserById(@PathVariable("id") long id) {
        return null;
    }
}

对于这行代码@io.swagger.v3.oas.annotations.parameters.RequestBody(description = "User to add.", required = true),

因为 Swagger3 的 RequestBody 类和 Spring MVC 的 RequestBody 重名了, 所以在注释中不得不用完整路径, 比较影响代码格式. 在GitHub上有对这个问题的讨论(链接 https://github.com/swagger-api/swagger-core/issues/3628), 暂时无解.

定义对象

java 复制代码
@Schema(description = "UserBO Model Information")
@Data
public class UserBO {

    @Schema(description = "User ID")
    private String id;
    @Schema(description = "User Name")
    private String name;
}

参考

相关推荐
带刺的坐椅2 天前
SpringBoot3 使用 SolonMCP 开发 MCP
java·ai·springboot·solon·mcp
LUCIAZZZ3 天前
JVM之虚拟机运行
java·jvm·spring·操作系统·springboot
堕落年代3 天前
SpringSecurity当中的CSRF防范详解
前端·springboot·csrf
一零贰肆3 天前
深入理解SpringBoot中的SpringCache缓存技术
java·springboot·springcache·缓存技术
LUCIAZZZ4 天前
JVM之内存管理(一)
java·jvm·spring·操作系统·springboot
LUCIAZZZ6 天前
JVM之内存管理(二)
java·jvm·后端·spring·操作系统·springboot
天上掉下来个程小白7 天前
缓存套餐-01.Spring Cache入门案例
java·redis·spring·缓存·springboot·springcache
程序员buddha9 天前
SpringBoot+Dubbo+Zookeeper实现分布式系统步骤
分布式·zookeeper·dubbo·springboot
天上掉下来个程小白9 天前
缓存套餐-03.功能测试
redis·缓存·springboot·苍穹外卖·springcache
Ten peaches10 天前
苍穹外卖(订单状态定时处理、来单提醒和客户催单)
java·数据库·sql·springboot