由于 Knife4j 长期未适配 Spring Boot 4.x + Jakarta EE,参考其设计思路重新实现,提供适配 Spring Boot 4.0 + springdoc-openapi 3.x 的 OpenAPI 文档聚合 UI,支持 Gateway 多服务聚合与单服务两种模式。
![]() 概览 |
![]() 接口详情 |
![]() 设置 |
![]() 文档导出 |
| 功能 | 说明 |
|---|---|
| 网关聚合 | 支持 manual(手动配置路由)和 discover(基于服务发现自动聚合)两种模式 |
| 单服务模式 | 无需网关,单体应用直接使用,支持多分组配置 |
| 接口调试 | 内置调试面板,支持 path/query/header/cookie 参数,支持 JSON、form-data、multipart 请求体,支持文件上传 |
| Basic Auth | 可选为文档页面开启 HTTP Basic 保护,防止未授权访问,单服务和网关模式均支持 |
| UI 鉴权透传 | 全局配置 Bearer Token 或自定义 Header,调试请求自动携带,可持久化到本地存储 |
| DOCX 导出 | 一键导出当前服务接口文档为 Word 文档 |
| x-order 排序 | 支持通过 x-order 扩展字段自定义 Tag / Operation 排序 |
| YAML/JSON | 自动识别 spec 格式,同时支持 JSON 和 YAML |
| 可分享链接 | 接口详情页 URL 包含定位信息,可直接分享给他人 |
后端
- Java 21
- Spring Boot 4.0.4
- Spring Cloud 2025.1.0
- springdoc-openapi 3.0.1
前端(springdoc-plus-web)
- Vue 3.5 + TypeScript 5.9
- Tailwind CSS v4
- Vite 7
springdoc-plus
├── springdoc-plus-core # 共享枚举、模型类(GatewayRoute、UiConfig 等)
├── springdoc-plus-ui # 前端构建产物打包模块(供两个 starter 依赖)
├── springdoc-plus-web # 前端源码(Vue 3 + Tailwind CSS v4)
├── springdoc-plus-openapi3-spring-boot-starter # 单服务 starter
├── springdoc-plus-gateway-spring-boot-starter # Spring Cloud Gateway 聚合 starter
└── springdoc-plus-samples # 示例工程
├── user-service-sample (port 8081)
├── order-service-sample (port 8082)
└── gateway-sample (port 8080)
<dependency>
<groupId>io.github.weimin96</groupId>
<artifactId>springdoc-plus-openapi3-spring-boot-starter</artifactId>
<version>0.1.5</version>
</dependency>同时确保项目已引入
springdoc-openapi-starter-webmvc-ui,该 starter 会自动传递依赖。
@OpenAPIDefinition(info = @Info(title = "用户服务", version = "v1"))
@SpringBootApplication
public class UserServiceApplication {
public static void main(String[] args) {
SpringApplication.run(UserServiceApplication.class, args);
}
}默认无需任何配置即可使用,以下为完整可选配置项:
springdoc-plus:
openapi3:
enabled: true # 默认 true,设为 false 可整体关闭
tags-sorter: order # Tag 排序策略:alpha(字母序)| order(x-order 值)
operations-sorter: order
# 多分组配置(可选,不配置则使用默认的 /v3/api-docs 单分组)
groups:
- name: 用户接口
url: /v3/api-docs
context-path: /
order: 1
- name: 管理接口
url: /v3/api-docs/admin
context-path: /
order: 2
# UI 鉴权透传
auth:
enabled: true
header-name: Authorization
default-prefix: Bearer
persist: true # 是否将 Token 持久化到浏览器本地存储
# HTTP Basic 保护(保护 /doc.html 页面本身)
basic:
enabled: false
username: admin
password: secrethttp://localhost:8080/doc.html
<dependency>
<groupId>io.github.weimin96</groupId>
<artifactId>springdoc-plus-gateway-spring-boot-starter</artifactId>
<version>0.1.5</version>
</dependency>各下游服务同样需要引入 springdoc-plus-openapi3-spring-boot-starter 以暴露 /v3/api-docs 接口。
手动维护路由列表,配置清晰,不依赖服务注册中心:
spring:
cloud:
gateway:
server:
webflux:
routes:
- id: user-service
uri: http://localhost:8081
predicates:
- Path=/user-service/**
filters:
- StripPrefix=1
- id: order-service
uri: http://localhost:8082
predicates:
- Path=/order-service/**
filters:
- StripPrefix=1
springdoc-plus:
gateway:
enabled: true
strategy: manual
tags-sorter: order
operations-sorter: order
# Basic Auth 保护文档页面(可选)
basic:
enabled: false
username: admin
password: secret
# UI 鉴权透传 - 调试接口时自动携带 Token
auth:
enabled: true
header-name: Authorization
default-prefix: Bearer
persist: true
routes:
- name: 用户服务
service-name: user-service
url: /user-service/v3/api-docs
context-path: /user-service
order: 1
- name: 订单服务
service-name: order-service
url: /order-service/v3/api-docs
context-path: /order-service
order: 2基于服务发现自动找到所有服务的 API 文档,适合服务数量多且频繁变动的场景:
springdoc-plus:
gateway:
enabled: true
strategy: discover
discover:
enabled: true
version: openapi3 # OpenAPI 版本
excluded-services:
- gateway-sample # 排除网关服务自身
- config-server # 排除其他非业务服务
openapi3-url: /v3/api-docs # 各服务的文档路径(统一)
resolve-context-path-from-gateway-routes: true # 从 Gateway 路由推断 contextPath
# 对特定服务做个性化配置(可选)
service-config:
user-service:
order: 1
group-name: 用户服务
context-path: /user-service
order-service:
order: 2
context-path: /order-service
group-names:
- default
- admin # 该服务有多个分组Discover 模式前置条件:
- Gateway 已启用服务发现(
spring.cloud.gateway.discovery.locator.enabled=true,或配置了 Simple Discovery)- 下游服务已注册到注册中心(Nacos、Consul、Eureka、Simple Discovery 等均可)
http://localhost:8080/doc.html
mvn -q -DskipTests package# 终端 1:用户服务(port 8081)
cd springdoc-plus-samples/user-service-sample
mvn -q spring-boot:run
# 终端 2:订单服务(port 8082)
cd springdoc-plus-samples/order-service-sample
mvn -q spring-boot:run
# 终端 3:网关(port 8080)
cd springdoc-plus-samples/gateway-sample
mvn -q spring-boot:run| 地址 | 说明 |
|---|---|
http://localhost:8080/doc.html |
网关聚合 UI(汇聚用户服务 + 订单服务) |
http://localhost:8081/doc.html |
用户服务独立 UI |
http://localhost:8082/doc.html |
订单服务独立 UI |
示例工程默认使用 manual 模式,如需切换为 discover 模式,将 gateway-sample/src/main/resources/application.yml 中的 strategy: manual 改为 strategy: discover 即可。
| 参数 | 类型 | 默认值 | 说明 |
|---|---|---|---|
enabled |
Boolean | true |
是否启用单服务文档功能 |
tags-sorter |
alpha | order |
alpha |
Tag 排序策略。order 使用 x-order 扩展字段 |
operations-sorter |
alpha | order |
alpha |
Operation 排序策略 |
groups[].name |
String | default |
分组名称,不能为空 |
groups[].url |
String | /v3/api-docs |
分组对应的 OpenAPI 文档地址,不能为空 |
groups[].context-path |
String | / |
该分组用于调试请求的 basePath |
groups[].order |
Integer | 0 |
分组排序权重,数值越小越靠前 |
auth.enabled |
Boolean | true |
是否在 UI 中展示鉴权配置入口 |
auth.header-name |
String | Authorization |
鉴权 Header 名称 |
auth.default-prefix |
String | "" |
鉴权值前缀,如 Bearer |
auth.persist |
Boolean | true |
是否将填写的 Token 持久化到浏览器 |
basic.enabled |
Boolean | false |
是否开启 HTTP Basic 保护文档页面 |
basic.username |
String | — | Basic Auth 用户名(enabled=true 时必填) |
basic.password |
String | — | Basic Auth 密码(enabled=true 时必填) |
| 参数 | 类型 | 默认值 | 说明 |
|---|---|---|---|
enabled |
Boolean | false |
是否启用网关聚合 |
strategy |
manual | discover |
MANUAL |
聚合策略 |
tags-sorter |
alpha | order |
alpha |
Tag 排序策略 |
operations-sorter |
alpha | order |
alpha |
Operation 排序策略 |
routes |
List | [] |
manual 模式的路由列表(见下表) |
discover.enabled |
Boolean | false |
是否启用服务发现 |
discover.version |
openapi3 |
openapi3 |
下游服务的 API 规范版本 |
discover.excluded-services |
Set<String> | [] |
排除的服务名列表(支持精确匹配) |
discover.openapi3-url |
String | /v3/api-docs |
各服务统一的文档路径 |
discover.resolve-context-path-from-gateway-routes |
Boolean | true |
是否从 Gateway 路由 predicates 自动推断 contextPath |
discover.service-config |
Map | {} |
按 serviceId 对特定服务做个性化配置 |
auth.enabled |
Boolean | true |
是否启用 UI 鉴权透传 |
auth.header-name |
String | Authorization |
鉴权 Header 名称 |
auth.default-prefix |
String | "" |
鉴权值前缀,如 Bearer |
auth.persist |
Boolean | true |
是否将填写的 Token 持久化到浏览器 |
basic.enabled |
Boolean | false |
是否开启 HTTP Basic 保护文档页面 |
basic.username |
String | — | Basic Auth 用户名 |
basic.password |
String | — | Basic Auth 密码 |
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
name |
String | 是 | 分组在 UI 中的显示名称 |
service-name |
String | 是 | 下游服务名(与 Gateway 路由 id 或服务注册名对应) |
url |
String | 是 | 通过网关访问下游 OpenAPI 文档的路径,如 /user-service/v3/api-docs |
context-path |
String | 否 | 调试请求时的 basePath 前缀,通常与 Gateway 路由的 StripPrefix 对应,如 /user-service |
order |
Integer | 否 | 排序权重,数值越小越靠前,默认 0 |
两个 starter 均支持用 HTTP Basic 保护 /doc.html 及 /springdoc-plus-ui/** 路径,防止未授权人员访问文档。
springdoc-plus:
# 单服务用 openapi3,网关用 gateway
openapi3:
basic:
enabled: true
username: admin
password: your-secret-password启用后浏览器会弹出标准 Basic Auth 认证对话框。认证使用恒定时间比对,防止时序攻击。
⚠️ Basic Auth 以 Base64 明文传输,生产环境请务必配合 HTTPS 使用。
在 UI 右上角"设置"中填写 Token,调试接口时会自动将其添加到请求头中,无需每次手动设置。
springdoc-plus:
gateway:
auth:
enabled: true
header-name: Authorization # 请求头名称
default-prefix: Bearer # 自动拼接前缀,填写 Token 时不需要手动加 "Bearer "
persist: true # 刷新页面后 Token 仍然保留接口详情页采用左右分栏布局:左侧展示接口文档(参数说明、请求体 Schema、响应文档),右侧固定显示调试面板。
调试面板支持:
| 类型 | 说明 |
|---|---|
| 路径参数(path) | 自动识别 {id} 占位符并替换 |
| 查询参数(query) | 自动拼接到 URL |
| 请求头(header) | 可在调试面板"请求头"标签页手动添加 |
| JSON 请求体 | 根据 Schema 自动生成示例,支持手动编辑 |
Form 表单(application/x-www-form-urlencoded) |
逐字段填写 |
文件上传(multipart/form-data) |
支持单文件和多文件 |
| 响应查看 | 展示状态码、响应头、响应体,JSON 自动格式化 |
调试参数和请求体会自动保存到本地存储
在 UI 顶部工具栏点击「导出」,可将当前服务的接口文档导出为 Word(.docx) 文件,内容包含:
- 服务基本信息(版本、服务地址、联系方式)
- 按 Tag 分组的接口列表
- 每个接口的请求参数、请求体 Schema、响应定义
前端源码位于 springdoc-plus-web/,基于 Vue 3 + TypeScript + Tailwind CSS v4。
cd springdoc-plus-web
pnpm install
# 开发模式(需要后端服务已启动在 8080)
pnpm dev
# 构建并复制产物到 springdoc-plus-ui
pnpm deployQ: 为什么访问 /doc.html 提示 404?
单服务模式请检查:
springdoc-plus.openapi3.enabled是否为true(默认值即为 true)- classpath 中是否存在
springdoc-openapi-starter-webmvc-ui
Q: 网关聚合后某个服务的接口"Try it out"请求失败,提示 CORS 或路径错误?
检查 context-path 配置是否与网关路由的 StripPrefix 对应。例如:
# Gateway 路由
- Path=/user-service/**
- StripPrefix=1
# 则 context-path 应配置为 /user-service
routes:
- context-path: /user-serviceQ: Discover 模式下某些服务没有出现在文档列表中?
- 确认服务已成功注册到注册中心,可通过
/actuator/gateway/routes验证 - 检查
excluded-services是否误将该服务排除 - 确认该服务暴露了
springdoc.api-docs.enabled=true且路径与openapi3-url一致
Q: 如何使用 x-order 控制接口排序?
在 tags-sorter / operations-sorter 设置为 order 后,通过 springdoc 的扩展注解设置排序值:
@Tag(
name = "用户管理",
extensions = @Extension(properties = @ExtensionProperty(name = "x-order", value = "1"))
)
@Operation(
summary = "查询用户",
extensions = @Extension(properties = @ExtensionProperty(name = "x-order", value = "1"))
)Q: Basic Auth 开启后 Spring Security 会冲突吗?
不会。BasicAuthFilter(单服务)和 BasicAuthWebFilter(网关)只拦截文档相关路径(/doc.html、/springdoc-plus-ui/**),不影响业务接口路由,也不依赖 Spring Security。
欢迎提交 Issue 和 Pull Request。



