SpringDoc 基本使用指南

发布于:2025-07-22 ⋅ 阅读:(13) ⋅ 点赞:(0)

SpringDoc 是基于 Spring Boot 的现代化 API 文档生成工具,通过自动化扫描代码和注解,生成符合 OpenAPI 3.0+ 规范 的交互式文档,并集成 Swagger UI 提供可视化测试界面。以下是其核心详解:


核心特性与优势

  • 开箱即用

    仅需添加依赖,无需复杂配置即可自动生成文档,支持 Spring WebMvc、WebFlux、Spring Security 及 Jakarta EE。

  • 注解驱动

    使用 JSR-303 规范注解(如 @Tag@Operation)替代 SpringFox 专属注解,降低学习成本。

  • 动态兼容性

    完美适配 Spring Boot 2.6+ 及 3.x(含 JDK 17+),解决 SpringFox 因停维护导致的不兼容问题。

  • 多格式输出

    支持 JSON/YAML/HTML 格式文档,并提供分组功能,可按模块划分接口(如公开 API 与内部 API)。


集成与配置

  • 依赖引入(Spring Boot 3.x)

    <dependency>
        <groupId>org.springdoc</groupId>
        <artifactId>springdoc-openapi-starter-webmvc-ui</artifactId>
        <version>2.5.0</version> <!-- 官方稳定版,兼容 Spring Boot 3.3.x:cite[2]:cite[8] -->
    </dependency>
    
  • 基础配置(application.yml)

    springdoc:
      swagger-ui:
        # 开启 swagger-ui 文档展示
        enabled: true
        # UI访问路径
        path: /swagger-ui.html
        # 标签排序方式
        tags-sorter: alpha
        # 操作排序方式
        operations-sorter: alpha
        # 保持认证状态
        persistAuthorization: true
        # 禁用示例接口
        disable-swagger-default-url: true
      api-docs:
        # 开启 OpenAPI 展示
        enabled: true
        # OpenAPI JSON路径
        path: /v3/api-docs
      default-consumes-media-type: application/json
      default-produces-media-type: application/json
      cache:
        # 关闭文档缓存
        disabled: false
      # 显示actuator端点
      show-actuator: false
      # 推荐保持默认,显示结构化参数
      # default-flat-param-object: true
      # 允许在文档中展示 Spring MVC 的 ModelAndView 返回类型
      model-and-view-allowed: true
      # 推荐关闭以确保文档精确性
      override-with-generic-response: false
    
  • 全局信息配置类(可选)

    @Configuration
    @OpenAPIDefinition(
      info = @Info(title = "项目API文档", version = "1.0", description = "SpringBoot接口文档")
    )
    public class SpringDocConfig { 
      // 无需额外代码
    }
    

注解使用

常用注解

场景 SpringDoc 注解 示例
控制器描述 @Tag(name="模块", description="") @Tag(name="用户管理", description="用户CRUD")
接口方法描述 @Operation(summary="", description="") @Operation(summary="创建用户", description="需管理员权限")
参数描述 @Parameter(description="") @Parameter(description="用户ID", required=true)
模型属性描述 @Schema(description="") public class User { @Schema(description="用户名") private String name; }l
解析对象属性为查询参数 @ParameterObject public BizResponse getUserPage(@ParameterObject UserPageForm form) {}

提示:

  • @Hidden 可隐藏接口或参数;
  • 支持 Spring Security 的 @PreAuthorize 注解,自动在文档中标记权限需求。

控制层注解使用示例

@RestController
@RequestMapping("/api/users")
@Tag(name = "用户管理", description = "用户相关操作API")
public class UserController{

    @Operation(summary = "获取用户信息", description = "通过用户id获取用户信息")
    @Parameters({
        @Parameter(in = ParameterIn.PATH, name = "id", description = "用户uid", required = true)
    })
    @ApiResponse(responseCode = "404", description = "User not found")
    @GetMapping("/{id}")
    public ResponseEntity<User> getUserById(@PathVariable Long id){
        // 实现代码
        return new ResponseEntity(new User(10001,"feng","ADMIN"), HttpStatusCode.valueOf(200));
    }
    
    @Operation(summary = "获取用户列表-分页")
    @GetMapping("/userPage.do")
    public BizResponse getUserPage(@ParameterObject UserPageForm form) {
        return BizResponse.ok(userServer.getUserPage(form));
    }
    
    @Operation(summary = "文件上传")
    @PostMapping(name = "/upload", consumes = MediaType.MULTIPART_FORM_DATA_VALUE)
    public BizResponse<FileInfoVo> fileUpload(
            @Parameter(description = "文件",
                    content = @Content(mediaType = MediaType.MULTIPART_FORM_DATA_VALUE,
                            schema = @Schema(type = "string", format = "binary")))
            @RequestParam MultipartFile file) {
        FileInfo fileInfo = fileStorageService.of(file).setPath(uploadFilePath).upload();
        return BizResponse.ok(fileInfo);
    }
}

模型注解使用示例

import io.swagger.v3.oas.annotations.media.Schema;
import io.swagger.v3.oas.annotations.media.Schema.RequiredMode;
import jakarta.validation.constraints.Email;
import jakarta.validation.constraints.Size;

@data
public clas sUser{

    @Schema(description = "用户ID", example = "1001")
    private Integer id;

    @Schema(description = "用户名", example = "john_doe", requiredMode = RequiredMode.REQUIRED)
    @Size(min = 3, max = 20, message = "用户名长度必须在3到20个字符之间")
    private String username;
    
    @Schema(description = "用户角色", allowableValues = {"ADMIN", "USER", "GUEST"})
    private String role;

    @Schema(description = "邮箱", example = "john_doe@mail.com")
    @Email
    private String email;
    
    @Schema(description = "最近登录时间", example = "2025-07-15 12:25:32", type = "string")
    private Date lastLoginTime;
    
    @Schema(description = "出生年月日", example = "2025-07-15", type = "string")
    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
    private Date birthDate;
}

文件上传注解使用示例

  • 文件上传必须声明以下配置,否则 SpringDoc 无法识别为文件类型,文件参数不会显示为文件上传控件

    • @PostMapping 必须配置 consumes = MediaType.MULTIPART_FORM_DATA_VALUE
    • MultipartFile 参数必须明确声明 format = "binary"
  • 单文件上传

    @PostMapping(value = "/upload", consumes = MediaType.MULTIPART_FORM_DATA_VALUE)
    @Operation(summary = "上传文件")
    public ResponseEntity<String> uploadFile(
        @Parameter(
            description = "文件参数",
            required = true,
            content = @Content( // 关键:嵌套Content注解
                mediaType = MediaType.APPLICATION_OCTET_STREAM_VALUE,
                schema = @Schema(type = "string", format = "binary") // 明确格式
            )
        )
        @RequestParam("file") MultipartFile file) {
        // 业务逻辑
    }
    
  • 多文件上传(数组形式)

    @Parameter(
        description = "多文件上传",
        content = @Content(
            mediaType = MediaType.MULTIPART_FORM_DATA_VALUE,
            array = @ArraySchema( // 声明数组类型
                schema = @Schema(type = "string", format = "binary")
            )
        )
    )
    @RequestParam("files") MultipartFile[] files
    
  • 混合参数(文件+表单数据)

    @RequestBody(
        description = "混合参数请求",
        content = @Content(
            mediaType = MediaType.MULTIPART_FORM_DATA_VALUE,
            encoding = {
                @Encoding(name = "file", contentType = "image/jpeg"), // 指定文件类型
                @Encoding(name = "remark", contentType = "text/plain") // 文本参数
            }
        )
    )
    @RequestPart("file") MultipartFile file,
    @RequestPart("remark") String remark
    

分组与扩展功能

分组配置

  • 按模块隔离接口

    @Bean
    public GroupedOpenApi publicApi() {
        return GroupedOpenApi.builder()
            .group("公开接口")
            .pathsToMatch("/api/public/**")
            .build();
    }
    
    @Bean
    public GroupedOpenApi adminApi() {
        return GroupedOpenApi.builder()
            .group("管理接口")
            .pathsToMatch("/api/admin/**")
            .addOpenApiMethodFilter(method -> method.isAnnotationPresent(PreAuthorize.class))
            .build();
    }
    

    访问 Swagger UI 右上角切换分组


生产环境安全建议

  • 通过配置动态关闭文档

    springdoc:
      swagger-ui:
        enabled: false   # 生产环境禁用 UI
      api-docs:
        enabled: false   # 禁用 OpenAPI 端点:cite[1]
    

从 SpringFox 迁移指南

SpringFox 注解 SpringDoc 替代方案
@Api @Tag
@ApiOperation @Operation(summary="", description="")
@ApiModelProperty @Schema(description="")
@ApiParam @Parameter
@ApiIgnore @Hidden

迁移优势:

  • 支持 Spring Boot 3.x 和 JDK 17+;
  • 注解更简洁,符合 OpenAPI 3 规范

最佳实践与常见问题

  1. 依赖冲突

    排除旧版 Swagger 依赖(如 springfox-swagger2),避免与 SpringDoc 冲突1。

  2. 拦截器导致文档无法访问

    若项目使用 Spring Security,需放行文档路径:

    http.authorizeRequests().antMatchers("/swagger-ui/**", "/v3/api-docs/**").permitAll();
    
  3. 文档生成失败排查

    检查控制器是否被扫描:确保 @RestController 位于 springdoc.packages-to-scan 指定路径下


总结

SpringDoc 凭借 零配置启动注解简洁深度兼容 Spring 生态 的优势,已成为 Spring Boot API 文档的首选工具。其核心价值在于:

  • 自动化 - 减少手动维护文档的成本;
  • 标准化 - 严格遵循 OpenAPI 3 规范;
  • 可扩展 - 分组、安全控制灵活适配复杂项目。
  • 访问 http://localhost:8080/swagger-ui.html 即可查看交互式文档(默认路径)

网站公告

今日签到

点亮在社区的每一天
去签到