docs: 新增 api-portal API 文档门户设计文档
This commit is contained in:
@@ -0,0 +1,758 @@
|
||||
# API Portal — 睿核科技 API 文档门户 设计文档
|
||||
|
||||
> 日期:2026-06-08
|
||||
> 状态:待审核
|
||||
> 作者:AI + 张晟
|
||||
|
||||
---
|
||||
|
||||
## 一、项目概述
|
||||
|
||||
### 1.1 项目名称
|
||||
|
||||
- **前端项目**:`api-portal`(睿核科技 API 文档门户)
|
||||
- **后端服务**:`rui-service-apidoc`(API 文档管理微服务)
|
||||
|
||||
### 1.2 核心目标
|
||||
|
||||
构建一个**精美的 API 文档门户系统**,具备以下能力:
|
||||
|
||||
1. **多源 API 文档聚合** — 自动同步微服务 OpenAPI JSON + 手动导入
|
||||
2. **自定义多级菜单** — 3 级菜单树,自由组织,不受 Controller 结构限制
|
||||
3. **文档补全增强** — 管理后台补充中文说明、示例、注意事项
|
||||
4. **精美文档展示** — VitePress 风格三栏布局,代码高亮
|
||||
5. **AI 结构化接口** — 提供完整 API 信息供 AI 读取、代码生成、变更感知
|
||||
6. **多项目管理** — 可自由创建项目,每个项目独立菜单和文档
|
||||
|
||||
### 1.3 用户角色
|
||||
|
||||
| 角色 | 说明 |
|
||||
|------|------|
|
||||
| 匿名访客 | 浏览公开项目的 API 文档 |
|
||||
| 开发者 | 浏览 + 搜索 + 测试 API |
|
||||
| 管理员 | 管理项目、菜单、同步 API、补全文档 |
|
||||
| AI Agent | 通过专用接口读取结构化 API 数据 |
|
||||
|
||||
---
|
||||
|
||||
## 二、系统架构
|
||||
|
||||
```
|
||||
┌──────────────────────────────────────────────────────────────────┐
|
||||
│ 整体架构 │
|
||||
├──────────────────────────────────────────────────────────────────┤
|
||||
│ │
|
||||
│ 微服务集群 │
|
||||
│ ┌───────────┐ ┌───────────┐ ┌───────────┐ ┌───────────┐ │
|
||||
│ │ rui-user │ │rui-system │ │rui-cashier│ │rui-payment│ │
|
||||
│ │/v3/api- │ │/v3/api- │ │/v3/api- │ │/v3/api- │ │
|
||||
│ │ docs │ │ docs │ │ docs │ │ docs │ │
|
||||
│ └─────┬─────┘ └─────┬─────┘ └─────┬─────┘ └─────┬─────┘ │
|
||||
│ │ │ │ │ │
|
||||
│ ▼ ▼ ▼ ▼ │
|
||||
│ ┌──────────────────────────────────────────────────────┐ │
|
||||
│ │ rui-service-apidoc(独立微服务) │ │
|
||||
│ │ │ │
|
||||
│ │ 同步引擎 文档管理 AI 接口 │ │
|
||||
│ │ - 定时拉取 - 菜单 CRUD - 结构化查询 │ │
|
||||
│ │ - 手动触发 - 文档补全 - 变更检测 │ │
|
||||
│ │ - JSON 导入 - 版本管理 - 代码生成数据 │ │
|
||||
│ └──────────┬───────────────────┬───────────────────────┘ │
|
||||
│ │ │ │
|
||||
│ ┌────────▼────────┐ ┌──────▼──────────┐ │
|
||||
│ │ admin-ui │ │ api-portal │ │
|
||||
│ │ (管理后台) │ │ (文档门户) │ │
|
||||
│ │ 补全信息/管理菜单 │ │ 精美展示/公开 │ │
|
||||
│ └─────────────────┘ └─────────────────┘ │
|
||||
│ │
|
||||
│ ┌────────────────────────────────────────┐ │
|
||||
│ │ AI Agent (Codex 等) │ │
|
||||
│ │ 通过 /ai/* 接口读取结构化 API 数据 │ │
|
||||
│ └────────────────────────────────────────┘ │
|
||||
└──────────────────────────────────────────────────────────────────┘
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 三、后端设计 — rui-apidoc
|
||||
|
||||
### 3.1 技术栈
|
||||
|
||||
| 项目 | 选型 | 说明 |
|
||||
|------|------|------|
|
||||
| 语言 | Java 21 | 和框架一致 |
|
||||
| 框架 | Spring Boot 3 + Spring Cloud | 和框架一致 |
|
||||
| 数据库 | MySQL 8 | 和框架一致 |
|
||||
| ORM | MyBatis-Plus | 继承 BaseEntity |
|
||||
| API 文档 | SpringDoc (OpenAPI 3) | 和框架一致 |
|
||||
| 注册中心 | Nacos | 复用现有 |
|
||||
| 包管理 | Maven | parent: rui-parent |
|
||||
|
||||
### 3.2 模块结构
|
||||
|
||||
遵循 `业务应用模块创建规则`,作为 `app/` 下的独立业务模块:
|
||||
|
||||
```
|
||||
app/
|
||||
└── rui-apidoc/
|
||||
├── pom.xml # parent: rui-app
|
||||
├── rui-apidoc-api/ # [可部署] REST API + 启动类
|
||||
│ └── src/main/java/com/rui/apidoc/api/
|
||||
│ ├── ApidocApplication.java
|
||||
│ └── controller/
|
||||
│ ├── PortalController.java # 文档门户 API(公开)
|
||||
│ ├── ApidocController.java # 管理后台 API(需认证)
|
||||
│ └── AiController.java # AI 专用 API
|
||||
├── rui-apidoc-common/ # [库] DTO、VO、枚举
|
||||
│ └── src/main/java/com/rui/apidoc/
|
||||
│ ├── dto/
|
||||
│ ├── vo/
|
||||
│ └── enums/
|
||||
├── rui-apidoc-core/ # [库] Entity、Mapper、Service
|
||||
│ └── src/main/java/com/rui/apidoc/core/
|
||||
│ ├── entity/
|
||||
│ ├── mapper/
|
||||
│ ├── service/
|
||||
│ └── config/
|
||||
└── rui-apidoc-task/ # [库] 定时同步任务
|
||||
└── src/main/java/com/rui/apidoc/task/
|
||||
└── SyncTask.java
|
||||
```
|
||||
|
||||
**POM 层级**:
|
||||
```
|
||||
app/pom.xml (rui-app)
|
||||
└── rui-apidoc/pom.xml (parent: rui-app)
|
||||
├── rui-apidoc-api → parent: rui-apidoc
|
||||
├── rui-apidoc-common
|
||||
├── rui-apidoc-core
|
||||
└── rui-apidoc-task
|
||||
```
|
||||
|
||||
**依赖关系**:
|
||||
```
|
||||
common → rui-common-core
|
||||
core → rui-common-mybatis, rui-common-security, common
|
||||
task → core, common
|
||||
api → core, task, rui-common-security, rui-common-web
|
||||
```
|
||||
|
||||
### 3.3 核心数据模型
|
||||
|
||||
> 所有实体继承 `BaseEntity`,自动包含 id, tenant_id, deleted, created_by, created_at, updated_by, updated_at 字段。
|
||||
> 建表 SQL 只写业务字段,公共字段由 BaseEntity 规范统一。
|
||||
|
||||
#### 3.3.1 项目表 `apidoc_project`
|
||||
|
||||
```sql
|
||||
CREATE TABLE apidoc_project (
|
||||
-- 业务字段
|
||||
project_key VARCHAR(64) NOT NULL COMMENT '项目唯一标识,如 rui-framework',
|
||||
name VARCHAR(128) NOT NULL COMMENT '项目名称',
|
||||
description TEXT DEFAULT NULL COMMENT '项目描述',
|
||||
visibility TINYINT NOT NULL DEFAULT 0 COMMENT '可见性 0=公开 1=需登录 2=仅管理员',
|
||||
logo_url VARCHAR(512) DEFAULT NULL COMMENT '项目 Logo',
|
||||
sort_order INT NOT NULL DEFAULT 0 COMMENT '排序',
|
||||
-- BaseEntity 公共字段
|
||||
id BIGINT NOT NULL COMMENT '主键ID(雪花算法)',
|
||||
tenant_id BIGINT NOT NULL DEFAULT 0 COMMENT '租户ID',
|
||||
deleted TINYINT NOT NULL DEFAULT 0 COMMENT '逻辑删除 0=正常 1=已删',
|
||||
created_by BIGINT DEFAULT NULL COMMENT '创建者ID',
|
||||
created_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
|
||||
updated_by BIGINT DEFAULT NULL COMMENT '更新者ID',
|
||||
updated_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
|
||||
PRIMARY KEY (id),
|
||||
UNIQUE KEY uk_project_key (project_key)
|
||||
) COMMENT='API文档项目';
|
||||
```
|
||||
|
||||
#### 3.3.2 微服务注册表 `apidoc_service`
|
||||
|
||||
```sql
|
||||
CREATE TABLE apidoc_service (
|
||||
-- 业务字段
|
||||
project_id BIGINT NOT NULL COMMENT '所属项目ID',
|
||||
service_name VARCHAR(128) NOT NULL COMMENT '服务名,如 rui-service-user',
|
||||
service_url VARCHAR(512) DEFAULT NULL COMMENT '服务地址,如 http://rui-service-user:8080',
|
||||
sync_mode TINYINT NOT NULL DEFAULT 0 COMMENT '同步模式 0=自动同步(URL) 1=手动导入',
|
||||
sync_status TINYINT NOT NULL DEFAULT 0 COMMENT '同步状态 0=未同步 1=同步中 2=成功 3=失败',
|
||||
last_sync_at DATETIME DEFAULT NULL COMMENT '最后同步时间',
|
||||
openapi_json MEDIUMTEXT DEFAULT NULL COMMENT '缓存的 OpenAPI JSON',
|
||||
-- BaseEntity 公共字段
|
||||
id BIGINT NOT NULL COMMENT '主键ID(雪花算法)',
|
||||
tenant_id BIGINT NOT NULL DEFAULT 0 COMMENT '租户ID',
|
||||
deleted TINYINT NOT NULL DEFAULT 0 COMMENT '逻辑删除',
|
||||
created_by BIGINT DEFAULT NULL,
|
||||
created_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
updated_by BIGINT DEFAULT NULL,
|
||||
updated_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
|
||||
PRIMARY KEY (id),
|
||||
INDEX idx_project (project_id)
|
||||
) COMMENT='API文档微服务注册';
|
||||
```
|
||||
|
||||
#### 3.3.3 多级菜单表 `apidoc_menu`
|
||||
|
||||
```sql
|
||||
CREATE TABLE apidoc_menu (
|
||||
-- 业务字段
|
||||
project_id BIGINT NOT NULL COMMENT '所属项目ID',
|
||||
parent_id BIGINT NOT NULL DEFAULT 0 COMMENT '父级菜单ID,0=顶级',
|
||||
name VARCHAR(128) NOT NULL COMMENT '菜单名称',
|
||||
icon VARCHAR(64) DEFAULT NULL COMMENT '图标',
|
||||
menu_type TINYINT NOT NULL DEFAULT 0 COMMENT '类型 0=目录 1=自定义内容页 2=接口组',
|
||||
sort_order INT NOT NULL DEFAULT 0 COMMENT '同级排序',
|
||||
service_id BIGINT DEFAULT NULL COMMENT '关联的微服务(menu_type=2时)',
|
||||
endpoint_paths JSON DEFAULT NULL COMMENT '关联的API路径列表',
|
||||
content MEDIUMTEXT DEFAULT NULL COMMENT 'Markdown自定义内容(menu_type=1时)',
|
||||
-- BaseEntity 公共字段
|
||||
id BIGINT NOT NULL COMMENT '主键ID(雪花算法)',
|
||||
tenant_id BIGINT NOT NULL DEFAULT 0 COMMENT '租户ID',
|
||||
deleted TINYINT NOT NULL DEFAULT 0 COMMENT '逻辑删除',
|
||||
created_by BIGINT DEFAULT NULL,
|
||||
created_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
updated_by BIGINT DEFAULT NULL,
|
||||
updated_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
|
||||
PRIMARY KEY (id),
|
||||
INDEX idx_project_parent (project_id, parent_id)
|
||||
) COMMENT='API文档菜单';
|
||||
```
|
||||
|
||||
#### 3.3.4 API 端点表 `apidoc_endpoint`
|
||||
|
||||
```sql
|
||||
CREATE TABLE apidoc_endpoint (
|
||||
-- 业务字段
|
||||
service_id BIGINT NOT NULL COMMENT '所属微服务ID',
|
||||
menu_id BIGINT DEFAULT NULL COMMENT '关联菜单ID',
|
||||
method VARCHAR(10) NOT NULL COMMENT 'HTTP方法 GET/POST/PUT/DELETE/PATCH',
|
||||
path VARCHAR(512) NOT NULL COMMENT '接口路径',
|
||||
summary VARCHAR(256) DEFAULT NULL COMMENT '接口摘要(来自OpenAPI)',
|
||||
description TEXT DEFAULT NULL COMMENT '接口描述(来自OpenAPI)',
|
||||
deprecated TINYINT NOT NULL DEFAULT 0 COMMENT '是否废弃',
|
||||
tags JSON DEFAULT NULL COMMENT 'OpenAPI tags',
|
||||
request_params JSON DEFAULT NULL COMMENT '查询参数 [{name,type,required,description}]',
|
||||
request_body JSON DEFAULT NULL COMMENT '请求体 JSON Schema',
|
||||
request_headers JSON DEFAULT NULL COMMENT '请求头',
|
||||
path_params JSON DEFAULT NULL COMMENT '路径参数',
|
||||
response_200 JSON DEFAULT NULL COMMENT '200 响应 JSON Schema',
|
||||
response_error JSON DEFAULT NULL COMMENT '错误响应 Schema',
|
||||
raw_openapi JSON DEFAULT NULL COMMENT '原始 OpenAPI operation 对象',
|
||||
content_hash VARCHAR(64) DEFAULT NULL COMMENT '内容哈希,用于变更检测',
|
||||
-- BaseEntity 公共字段
|
||||
id BIGINT NOT NULL COMMENT '主键ID(雪花算法)',
|
||||
tenant_id BIGINT NOT NULL DEFAULT 0 COMMENT '租户ID',
|
||||
deleted TINYINT NOT NULL DEFAULT 0 COMMENT '逻辑删除',
|
||||
created_by BIGINT DEFAULT NULL,
|
||||
created_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
updated_by BIGINT DEFAULT NULL,
|
||||
updated_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
|
||||
PRIMARY KEY (id),
|
||||
UNIQUE KEY uk_service_method_path (service_id, method, path),
|
||||
INDEX idx_service (service_id),
|
||||
INDEX idx_menu (menu_id)
|
||||
) COMMENT='API端点';
|
||||
```
|
||||
|
||||
#### 3.3.5 文档补充表 `apidoc_extra`
|
||||
|
||||
```sql
|
||||
CREATE TABLE apidoc_extra (
|
||||
-- 业务字段
|
||||
endpoint_id BIGINT NOT NULL COMMENT '关联端点ID',
|
||||
custom_title VARCHAR(256) DEFAULT NULL COMMENT '自定义标题(覆盖summary)',
|
||||
custom_desc TEXT DEFAULT NULL COMMENT '自定义说明(中文描述)',
|
||||
use_cases TEXT DEFAULT NULL COMMENT '使用场景说明',
|
||||
notes TEXT DEFAULT NULL COMMENT '注意事项',
|
||||
request_example JSON DEFAULT NULL COMMENT '请求示例',
|
||||
response_example JSON DEFAULT NULL COMMENT '响应示例',
|
||||
error_example JSON DEFAULT NULL COMMENT '错误响应示例',
|
||||
test_cases JSON DEFAULT NULL COMMENT '测试用例 [{name,params,expected}]',
|
||||
-- BaseEntity 公共字段
|
||||
id BIGINT NOT NULL COMMENT '主键ID(雪花算法)',
|
||||
tenant_id BIGINT NOT NULL DEFAULT 0 COMMENT '租户ID',
|
||||
deleted TINYINT NOT NULL DEFAULT 0 COMMENT '逻辑删除',
|
||||
created_by BIGINT DEFAULT NULL,
|
||||
created_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
updated_by BIGINT DEFAULT NULL,
|
||||
updated_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
|
||||
PRIMARY KEY (id),
|
||||
UNIQUE KEY uk_endpoint (endpoint_id)
|
||||
) COMMENT='API文档补充信息';
|
||||
```
|
||||
|
||||
#### 3.3.6 版本快照表 `apidoc_version`
|
||||
|
||||
```sql
|
||||
CREATE TABLE apidoc_version (
|
||||
-- 业务字段
|
||||
service_id BIGINT NOT NULL COMMENT '所属微服务ID',
|
||||
version VARCHAR(32) NOT NULL COMMENT '版本号,如 v1.2.0',
|
||||
openapi_json MEDIUMTEXT DEFAULT NULL COMMENT 'OpenAPI JSON 快照',
|
||||
change_log TEXT DEFAULT NULL COMMENT '变更日志(Markdown)',
|
||||
-- BaseEntity 公共字段
|
||||
id BIGINT NOT NULL COMMENT '主键ID(雪花算法)',
|
||||
tenant_id BIGINT NOT NULL DEFAULT 0 COMMENT '租户ID',
|
||||
deleted TINYINT NOT NULL DEFAULT 0 COMMENT '逻辑删除',
|
||||
created_by BIGINT DEFAULT NULL,
|
||||
created_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
updated_by BIGINT DEFAULT NULL,
|
||||
updated_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
|
||||
PRIMARY KEY (id),
|
||||
INDEX idx_service (service_id)
|
||||
) COMMENT='API文档版本快照';
|
||||
```
|
||||
|
||||
### 3.4 核心 API 设计
|
||||
|
||||
> 所有接口统一使用 `Result<T>` 返回封装(error=0 成功,code 为业务编码,message 提示,data 业务数据)。
|
||||
> Controller 路径遵循 `/{模块}/{功能}/{方法}` 规范。
|
||||
|
||||
#### 3.4.1 文档门户 API(公开,免认证)
|
||||
|
||||
| 方法 | 路径 | 返回类型 | 说明 |
|
||||
|------|------|---------|------|
|
||||
| GET | `/apidoc/portal/project/list` | `Result<List<ProjectVO>>` | 公开项目列表 |
|
||||
| GET | `/apidoc/portal/project/{key}` | `Result<ProjectVO>` | 项目详情 |
|
||||
| GET | `/apidoc/portal/project/{key}/menu` | `Result<List<MenuTreeVO>>` | 项目菜单树 |
|
||||
| GET | `/apidoc/portal/project/{key}/menu/{menuId}` | `Result<MenuDetailVO>` | 菜单详情 |
|
||||
| GET | `/apidoc/portal/endpoint/{id}` | `Result<EndpointDetailVO>` | 端点详情(含补充信息) |
|
||||
| GET | `/apidoc/portal/search` | `Result<List<EndpointVO>>` | 全文搜索 |
|
||||
|
||||
#### 3.4.2 管理后台 API(需认证 + 管理员权限)
|
||||
|
||||
遵循 Controller 分类规范,管理接口使用 `ApidocController`:
|
||||
|
||||
| 方法 | 路径 | 返回类型 | 说明 |
|
||||
|------|------|---------|------|
|
||||
| POST | `/apidoc/admin/project` | `Result<Long>` | 创建项目 |
|
||||
| PUT | `/apidoc/admin/project/{id}` | `Result<Void>` | 更新项目 |
|
||||
| DELETE | `/apidoc/admin/project/{id}` | `Result<Void>` | 删除项目 |
|
||||
| POST | `/apidoc/admin/service` | `Result<Long>` | 注册微服务 |
|
||||
| POST | `/apidoc/admin/service/{id}/sync` | `Result<Void>` | 手动触发同步 |
|
||||
| POST | `/apidoc/admin/service/{id}/import` | `Result<Void>` | 手动导入 OpenAPI JSON |
|
||||
| POST | `/apidoc/admin/menu` | `Result<Long>` | 创建菜单 |
|
||||
| PUT | `/apidoc/admin/menu/{id}` | `Result<Void>` | 更新菜单 |
|
||||
| DELETE | `/apidoc/admin/menu/{id}` | `Result<Void>` | 删除菜单 |
|
||||
| PUT | `/apidoc/admin/menu/sort` | `Result<Void>` | 批量排序 |
|
||||
| POST | `/apidoc/admin/menu/{id}/bind` | `Result<Void>` | 菜单绑定 API 端点 |
|
||||
| PUT | `/apidoc/admin/extra/{endpointId}` | `Result<Void>` | 更新补充信息 |
|
||||
| POST | `/apidoc/admin/service/{id}/snapshot` | `Result<Void>` | 创建版本快照 |
|
||||
|
||||
#### 3.4.3 AI 专用 API
|
||||
|
||||
| 方法 | 路径 | 返回类型 | 说明 |
|
||||
|------|------|---------|------|
|
||||
| GET | `/apidoc/ai/projects` | `Result<List<AiProjectVO>>` | 所有项目(含服务概况) |
|
||||
| GET | `/apidoc/ai/project/{key}/endpoints` | `Result<List<AiEndpointVO>>` | 项目全部端点(完整结构化) |
|
||||
| GET | `/apidoc/ai/endpoint/{id}` | `Result<AiEndpointDetailVO>` | 单个端点完整信息 |
|
||||
| GET | `/apidoc/ai/endpoint/search` | `Result<List<AiEndpointVO>>` | 搜索端点(keyword/method/path) |
|
||||
| GET | `/apidoc/ai/project/{key}/changes` | `Result<List<ApiChangeVO>>` | API 变更(增量,since参数) |
|
||||
| POST | `/apidoc/ai/query` | `Result<List<AiEndpointVO>>` | AI 自然语言查询 |
|
||||
|
||||
**AI 接口返回示例(`GET /apidoc/ai/endpoint/{id}`)**:
|
||||
|
||||
```json
|
||||
{
|
||||
"error": 0,
|
||||
"code": null,
|
||||
"message": "操作成功",
|
||||
"data": {
|
||||
"id": 1001,
|
||||
"method": "POST",
|
||||
"path": "/v1/user/users",
|
||||
"summary": "创建用户",
|
||||
"description": "管理员创建新用户,需要管理员权限",
|
||||
"deprecated": false,
|
||||
"tags": ["用户管理"],
|
||||
"auth": "需要 Bearer Token,角色:ADMIN",
|
||||
"requestParams": [],
|
||||
"pathParams": [],
|
||||
"requestHeaders": [
|
||||
{ "name": "Authorization", "required": true, "description": "Bearer Token" },
|
||||
{ "name": "Content-Type", "required": true, "value": "application/json" }
|
||||
],
|
||||
"requestBody": {
|
||||
"type": "object",
|
||||
"required": ["username", "password", "phone"],
|
||||
"properties": {
|
||||
"username": { "type": "string", "description": "用户名,4-20位字母数字", "example": "zhangsan" },
|
||||
"password": { "type": "string", "description": "密码,8-32位", "example": "Pass@123" },
|
||||
"phone": { "type": "string", "description": "手机号", "example": "13800138000" },
|
||||
"email": { "type": "string", "description": "邮箱(可选)", "example": "zhangsan@example.com" }
|
||||
}
|
||||
},
|
||||
"response200": {
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"error": { "type": "integer", "description": "0=成功", "example": 0 },
|
||||
"code": { "type": "string", "example": "SUCCESS" },
|
||||
"message": { "type": "string", "example": "操作成功" },
|
||||
"data": {
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"id": { "type": "integer", "description": "用户ID", "example": 1001 },
|
||||
"username": { "type": "string", "example": "zhangsan" },
|
||||
"created_at": { "type": "string", "format": "date-time" }
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"responseError": {
|
||||
"400": { "error": 400, "code": "PARAM_INVALID", "message": "参数校验失败" },
|
||||
"401": { "error": 401, "code": "UNAUTHORIZED", "message": "未登录" },
|
||||
"403": { "error": 403, "code": "FORBIDDEN", "message": "无权限" }
|
||||
},
|
||||
"extra": {
|
||||
"customTitle": "创建新用户",
|
||||
"customDesc": "管理员通过此接口创建新用户,创建后用户处于启用状态",
|
||||
"useCases": "后台管理 > 用户管理 > 新增用户",
|
||||
"notes": "用户名唯一,不可重复。密码需满足复杂度要求。",
|
||||
"requestExample": { "username": "zhangsan", "password": "Pass@123", "phone": "13800138000" },
|
||||
"responseExample": { "error": 0, "code": null, "message": "操作成功", "data": { "id": 1001, "username": "zhangsan" } },
|
||||
"testCases": [
|
||||
{
|
||||
"name": "正常创建",
|
||||
"params": { "username": "testuser01", "password": "Pass@123", "phone": "13900139001" },
|
||||
"expected": { "error": 0 }
|
||||
},
|
||||
{
|
||||
"name": "用户名重复",
|
||||
"params": { "username": "admin", "password": "Pass@123", "phone": "13900139002" },
|
||||
"expected": { "error": 400, "code": "USER_EXISTS" }
|
||||
}
|
||||
]
|
||||
},
|
||||
"service": { "name": "rui-service-user", "project": "rui-framework" },
|
||||
"updatedAt": "2026-06-08T10:00:00"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 3.5 同步引擎设计
|
||||
|
||||
```
|
||||
自动同步流程:
|
||||
1. rui-apidoc-task 中的定时任务(可配置周期) 或 手动触发
|
||||
2. 遍历 apidoc_service 中 sync_mode=0 且 sync_status!=1 的服务
|
||||
3. HTTP 请求 {service_url}/v3/api-docs 获取 OpenAPI JSON
|
||||
4. 使用 JsonUtil 解析 JSON,提取所有 Path + Operation
|
||||
5. 计算每个 Operation 的 content_hash,与 apidoc_endpoint 现有数据对比
|
||||
6. 新增/更新/标记废弃 端点,记录变更
|
||||
7. 更新 sync_status=2, last_sync_at, openapi_json
|
||||
|
||||
手动导入流程:
|
||||
1. 管理员在管理后台粘贴 OpenAPI JSON 或上传文件
|
||||
2. 同上解析入库逻辑,sync_mode=1
|
||||
```
|
||||
|
||||
### 3.6 启动类
|
||||
|
||||
```java
|
||||
package com.rui.apidoc.api;
|
||||
|
||||
import com.rui.common.security.annotation.EnableResourceServer;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
|
||||
@SpringBootApplication
|
||||
@EnableResourceServer
|
||||
public class ApidocApplication {
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(ApidocApplication.class, args);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 3.7 Nacos 白名单配置
|
||||
|
||||
```yaml
|
||||
security:
|
||||
oauth2:
|
||||
ignore-urls:
|
||||
- /apidoc/portal/**
|
||||
- /apidoc/ai/**
|
||||
```
|
||||
|
||||
> `/apidoc/portal/**` 和 `/apidoc/ai/**` 免认证公开访问。
|
||||
> `/apidoc/admin/**` 需管理员权限。
|
||||
## 四、前端设计 — api-portal
|
||||
|
||||
### 4.1 技术栈
|
||||
|
||||
| 项目 | 选型 | 说明 |
|
||||
|------|------|------|
|
||||
| 框架 | Vue 3 + TypeScript | 组合式 API (setup),和 admin-ui 一致 |
|
||||
| 构建 | Vite 6 | 和 admin-ui 一致 |
|
||||
| 样式 | UnoCSS | 原子化 CSS,和 admin-ui 一致 |
|
||||
| 路由 | Vue Router 4 | 侧边栏联动 |
|
||||
| HTTP | Axios | 统一封装 request,复用 admin-ui 模式 |
|
||||
| 代码高亮 | Shiki | 和 VitePress 同款高亮引擎 |
|
||||
| Markdown 渲染 | markdown-it + 自定义插件 | 自定义内容页 |
|
||||
| 图标 | @iconify-json/carbon | 专业文档风格 |
|
||||
|
||||
> api-portal 是独立项目(不依赖 Element Plus),UI 全部基于 UnoCSS 原子化样式构建。
|
||||
|
||||
### 4.2 页面结构
|
||||
|
||||
#### 三栏布局(接口文档页)
|
||||
|
||||
```
|
||||
┌─────────────────────────────────────────────────────────────────┐
|
||||
│ 🏠 Rui API Portal 🔍 搜索接口... 🌙 主题 🌐 中文 │
|
||||
├────────────┬──────────────────────────────────┬─────────────────┤
|
||||
│ │ │ │
|
||||
│ 📖 快速开始 │ POST /v1/user/users │ 请求示例 │
|
||||
│ │ ━━━━━━━━━━━━━━━━━━━━ │ │
|
||||
│ ▸ 用户管理 │ 创建新用户 │ curl -X POST \ │
|
||||
│ 登录 │ │ /v1/user/users \│
|
||||
│ 注册 │ 管理员通过此接口创建新用户,创建 │ -H 'Auth...' \ │
|
||||
│ 用户列表 │ 后用户处于启用状态。 │ -d '{...}' │
|
||||
│ 用户详情 │ │ │
|
||||
│ 创建用户 │ ⚡ 需要管理员权限 │─────────────────│
|
||||
│ 更新用户 │ 🔒 Bearer Token │ 响应示例 │
|
||||
│ ▸ 订单管理 │ │ │
|
||||
│ 创建订单 │ 请求参数 │ 200 OK │
|
||||
│ 查询订单 │ ┌──────┬──────┬────┬────┐ │ { │
|
||||
│ 取消订单 │ │ 参数 │ 类型 │必填│说明 │ │ "error":0, │
|
||||
│ ▸ 支付 │ ├──────┼──────┼────┼────┤ │ "data":{...}│
|
||||
│ 发起支付 │ │username│string│ ✓ │用户名│ │ } │
|
||||
│ 支付回调 │ │password│string│ ✓ │密码 │ │ │
|
||||
│ 退款 │ └──────┴──────┴────┴────┘ │─────────────────│
|
||||
│ │ │ 测试用例 │
|
||||
│ │ 响应参数 │ ✅ 正常创建 │
|
||||
│ │ ┌──────┬──────┬────┐ │ ❌ 用户名重复 │
|
||||
│ │ │ 字段 │ 类型 │说明 │ │ │
|
||||
│ │ ├──────┼──────┼────┤ │ │
|
||||
│ │ │ id │ long │用户ID│ │ │
|
||||
│ │ └──────┴──────┴────┘ │ │
|
||||
│ │ │ │
|
||||
└────────────┴──────────────────────────────────┴─────────────────┘
|
||||
```
|
||||
|
||||
#### 项目首页
|
||||
|
||||
```
|
||||
┌─────────────────────────────────────────────────────────────────┐
|
||||
│ 🏠 Rui API Portal 🔍 搜索接口... 🌙 主题 🌐 中文 │
|
||||
├─────────────────────────────────────────────────────────────────┤
|
||||
│ │
|
||||
│ 睿核科技 API 文档中心 │
|
||||
│ 探索、测试、集成我们的 API 服务 │
|
||||
│ │
|
||||
│ ┌──────────────────────────────────┐ │
|
||||
│ │ 🔍 搜索所有 API 接口... │ │
|
||||
│ └──────────────────────────────────┘ │
|
||||
│ │
|
||||
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │
|
||||
│ │ 📦 rui-frame │ │ 📦 rui-cashier│ │ 📦 rui-payment│ │
|
||||
│ │ work │ │ │ │ │ │
|
||||
│ │ 基础平台框架 │ │ 收银系统 │ │ 支付系统 │ │
|
||||
│ │ 128 接口 │ │ 56 接口 │ │ 32 接口 │ │
|
||||
│ │ 5 模块 │ │ 3 模块 │ │ 2 模块 │ │
|
||||
│ └─────────────┘ └─────────────┘ └─────────────┘ │
|
||||
│ │
|
||||
└─────────────────────────────────────────────────────────────────┘
|
||||
```
|
||||
|
||||
### 4.3 路由设计
|
||||
|
||||
```
|
||||
/ → 项目首页(项目卡片列表)
|
||||
/:projectKey → 项目页(菜单 + 欢迎页)
|
||||
/:projectKey/menu/:menuId → 菜单页(自定义内容 / 接口组)
|
||||
/:projectKey/endpoint/:id → 单个接口详情页
|
||||
/search?keyword=&projectId= → 搜索结果页
|
||||
```
|
||||
|
||||
### 4.4 核心功能
|
||||
|
||||
| 功能 | 说明 |
|
||||
|------|------|
|
||||
| 多级菜单导航 | 3 级可折叠侧边栏,图标 + 名称 |
|
||||
| 接口文档渲染 | 方法/路径/参数/响应/示例,结构化表格展示 |
|
||||
| 代码高亮 | 请求示例(curl/JS/Java)、响应示例 JSON |
|
||||
| Markdown 自定义页 | 菜单项关联自定义 Markdown 内容(快速开始、认证说明等) |
|
||||
| 全文搜索 | 搜索接口名、路径、描述、参数名 |
|
||||
| 深色模式 | 主题切换 |
|
||||
| 响应式 | 移动端适配(侧边栏折叠) |
|
||||
| "试一试" | 简易 API 测试面板(填参数发请求) |
|
||||
|
||||
### 4.5 项目结构
|
||||
|
||||
> 遵循 admin-ui 的目录约定:service 层使用 BaseService 模式,composables 存放组合式函数,views 存放页面。
|
||||
|
||||
```
|
||||
api-portal/
|
||||
├── package.json
|
||||
├── vite.config.ts
|
||||
├── uno.config.ts
|
||||
├── tsconfig.json
|
||||
├── index.html
|
||||
├── public/
|
||||
│ └── favicon.svg
|
||||
├── src/
|
||||
│ ├── main.ts
|
||||
│ ├── App.vue
|
||||
│ ├── service/ # API 请求封装(和 admin-ui 一致)
|
||||
│ │ ├── BaseService.ts # 通用 CRUD 基类(复用 admin-ui 模式)
|
||||
│ │ ├── portalService.ts # 文档门户接口
|
||||
│ │ └── types.ts # TypeScript 类型定义
|
||||
│ ├── composables/ # 组合式函数
|
||||
│ │ ├── useTheme.ts # 主题切换
|
||||
│ │ ├── useMenu.ts # 菜单状态
|
||||
│ │ └── useSearch.ts # 搜索
|
||||
│ ├── components/
|
||||
│ │ ├── layout/
|
||||
│ │ │ ├── AppHeader.vue # 顶部导航
|
||||
│ │ │ ├── AppSidebar.vue # 侧边栏
|
||||
│ │ │ ├── AppFooter.vue # 底部
|
||||
│ │ │ └── ThreeColumn.vue # 三栏布局容器
|
||||
│ │ ├── endpoint/
|
||||
│ │ │ ├── EndpointHeader.vue # 方法 + 路径 + 标签
|
||||
│ │ │ ├── ParamsTable.vue # 参数表格
|
||||
│ │ │ ├── ResponseSchema.vue # 响应结构
|
||||
│ │ │ ├── CodeBlock.vue # 代码块(Shiki 高亮)
|
||||
│ │ │ └── TryIt.vue # "试一试"面板
|
||||
│ │ ├── markdown/
|
||||
│ │ │ └── MarkdownRenderer.vue # Markdown 渲染
|
||||
│ │ └── search/
|
||||
│ │ └── SearchDialog.vue # 搜索弹窗
|
||||
│ ├── views/ # 页面(和 admin-ui 命名一致)
|
||||
│ │ ├── HomePage.vue # 首页
|
||||
│ │ ├── ProjectPage.vue # 项目页
|
||||
│ │ ├── MenuPage.vue # 菜单内容页
|
||||
│ │ ├── EndpointPage.vue # 接口详情页
|
||||
│ │ └── SearchPage.vue # 搜索结果页
|
||||
│ ├── router/
|
||||
│ │ └── index.ts
|
||||
│ ├── stores/ # Pinia 状态管理
|
||||
│ │ └── project.ts # 项目状态
|
||||
│ ├── styles/
|
||||
│ │ ├── variables.css # CSS 变量(主题色)
|
||||
│ │ └── prose.css # 文档内容样式
|
||||
│ └── utils/
|
||||
│ ├── request.ts # Axios 封装(复用 admin-ui 模式,baseURL 指向 apidoc 服务)
|
||||
│ └── format.ts # 格式化工具
|
||||
└── env.d.ts
|
||||
```
|
||||
|
||||
### 4.6 request.ts 设计
|
||||
|
||||
> 复用 admin-ui 的 request 封装模式,但 api-portal 是公开文档站,不需要 Token/租户拦截。
|
||||
|
||||
```typescript
|
||||
// src/utils/request.ts
|
||||
import axios from 'axios'
|
||||
|
||||
const request = axios.create({
|
||||
baseURL: '/api', // 通过网关转发到 rui-apidoc
|
||||
timeout: 10000,
|
||||
})
|
||||
|
||||
// 响应拦截 — 复用 Result<T> 的 error 判断逻辑
|
||||
request.interceptors.response.use(
|
||||
(response) => {
|
||||
const { data } = response
|
||||
if (data.error !== 0) {
|
||||
console.error(data.message || '请求失败')
|
||||
return Promise.reject(data)
|
||||
}
|
||||
return data
|
||||
},
|
||||
(error) => {
|
||||
console.error('网络错误', error.message)
|
||||
return Promise.reject(error)
|
||||
},
|
||||
)
|
||||
|
||||
export { request }
|
||||
```
|
||||
|
||||
### 4.7 service 层设计
|
||||
|
||||
> 遵循 admin-ui 的 BaseService 模式,但 api-portal 以只读查询为主。
|
||||
|
||||
```typescript
|
||||
// src/service/portalService.ts
|
||||
import { request } from '@/utils/request'
|
||||
|
||||
/** 获取公开项目列表 */
|
||||
export function getProjectList() {
|
||||
return request({ url: '/apidoc/portal/project/list', method: 'get' })
|
||||
}
|
||||
|
||||
/** 获取项目详情 */
|
||||
export function getProject(key: string) {
|
||||
return request({ url: `/apidoc/portal/project/${key}`, method: 'get' })
|
||||
}
|
||||
|
||||
/** 获取项目菜单树 */
|
||||
export function getMenuTree(key: string) {
|
||||
return request({ url: `/apidoc/portal/project/${key}/menu`, method: 'get' })
|
||||
}
|
||||
|
||||
/** 获取菜单详情 */
|
||||
export function getMenuDetail(key: string, menuId: string) {
|
||||
return request({ url: `/apidoc/portal/project/${key}/menu/${menuId}`, method: 'get' })
|
||||
}
|
||||
|
||||
/** 获取端点详情 */
|
||||
export function getEndpoint(id: string) {
|
||||
return request({ url: `/apidoc/portal/endpoint/${id}`, method: 'get' })
|
||||
}
|
||||
|
||||
/** 搜索 */
|
||||
export function searchEndpoints(keyword: string, projectId?: string) {
|
||||
return request({ url: '/apidoc/portal/search', method: 'get', params: { keyword, projectId } })
|
||||
}
|
||||
```
|
||||
## 五、部署架构
|
||||
|
||||
```
|
||||
┌──────────────────────────────────────────────────┐
|
||||
│ Nginx / Gateway │
|
||||
│ ├─ / → api-portal 静态资源 │
|
||||
│ ├─ /admin → admin-ui 静态资源 │
|
||||
│ └─ /api/apidoc/* → rui-service-apidoc │
|
||||
└──────────────────────────────────────────────────┘
|
||||
|
||||
api-portal 构建产物部署为静态资源,通过 Nginx 或 CDN 分发。
|
||||
rui-service-apidoc 注册到 Nacos,通过 Gateway 路由。
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 六、开发优先级
|
||||
|
||||
### Phase 1:MVP(最小可用)
|
||||
|
||||
1. 后端:项目/菜单/端点 CRUD + OpenAPI JSON 手动导入
|
||||
2. 前端:三栏布局 + 菜单导航 + 接口文档渲染
|
||||
|
||||
### Phase 2:增强
|
||||
|
||||
3. 后端:自动同步引擎(定时拉取 /v3/api-docs)
|
||||
4. 后端:文档补全管理
|
||||
5. 前端:搜索 + 深色模式
|
||||
|
||||
### Phase 3:AI + 高级功能
|
||||
|
||||
6. 后端:AI 专用结构化接口
|
||||
7. 后端:API 变更检测 + 版本管理
|
||||
8. 前端:"试一试" API 测试面板
|
||||
|
||||
---
|
||||
|
||||
## 七、参考风格
|
||||
|
||||
| 参考站点 | 地址 | 借鉴点 |
|
||||
|---------|------|--------|
|
||||
| VitePress | https://vitepress.dev | 整体风格、三栏布局、深色模式 |
|
||||
| Nuxt UI Pro | https://ui.nuxt.com/pro | 文档模板、导航设计 |
|
||||
| Stripe API | https://stripe.com/docs/api | 代码示例、交互体验 |
|
||||
| Scalar | https://scalar.com | 现代 API 文档 UI |
|
||||
|
||||
---
|
||||
|
||||
> 本文档仅涵盖设计,不涉及具体实现代码。实施前需团队审核确认。
|
||||
Reference in New Issue
Block a user