6.3 KiB
6.3 KiB
世界书分页功能 - 前端API调用检查报告
✅ 检查结果
所有前端世界书分页功能都能正确发出请求到后端API!
📋 完整API映射表
1. 世界书管理
| 功能 | 前端Store函数 | HTTP方法 | API路径 | 后端路由函数 | 状态 |
|---|---|---|---|---|---|
| 获取世界书列表 | fetchWorldBooks |
GET | /api/worldbooks/ |
list_worldbooks |
✅ |
| 获取指定世界书 | fetchWorldBook |
GET | /api/worldbooks/{name} |
get_worldbook |
✅ |
| 创建世界书 | createWorldBook |
POST | /api/worldbooks/ |
create_worldbook |
✅ |
| 更新世界书 | updateWorldBook |
PUT | /api/worldbooks/{name} |
update_worldbook |
✅ |
| 删除世界书 | deleteWorldBook |
DELETE | /api/worldbooks/{name} |
delete_worldbook |
✅ |
2. 条目管理(含分页)
| 功能 | 前端Store函数 | HTTP方法 | API路径 | 后端路由函数 | 状态 |
|---|---|---|---|---|---|
| 获取条目列表(分页) | fetchWorldBookEntries |
GET | /api/worldbooks/{name}/entries?page={page}&page_size={page_size} |
list_worldbook_entries |
✅ |
| 获取指定条目 | fetchWorldBookEntry |
GET | /api/worldbooks/{name}/entries/{uid} |
get_worldbook_entry |
✅ |
| 创建条目 | createWorldBookEntry |
POST | /api/worldbooks/{name}/entries |
create_worldbook_entry |
✅ |
| 更新条目 | updateWorldBookEntry |
PUT | /api/worldbooks/{name}/entries/{uid} |
update_worldbook_entry |
✅ |
| 删除条目 | deleteWorldBookEntry |
DELETE | /api/worldbooks/{name}/entries/{uid} |
delete_worldbook_entry |
✅ |
3. 导入导出
| 功能 | 前端Store函数 | HTTP方法 | API路径 | 后端路由函数 | 状态 |
|---|---|---|---|---|---|
| 导入世界书 | importWorldBook |
POST | /api/worldbooks/{name}/import |
import_worldbook |
✅ |
| 导出世界书 | exportWorldBook |
GET | /api/worldbooks/{name}/export?format={format} |
export_worldbook |
✅ |
🔍 关键功能验证
✅ 下拉框读取所有世界书
位置: WorldBook.jsx 第547行
{worldBooks.map(book => (
<div key={book.name} className="dropdown-item">
...
</div>
))}
数据来源:
worldBooks来自 Store (第8行)- 通过
fetchWorldBooks()加载 (第85行和第95行)
加载时机:
- ✅ 组件挂载时立即加载(如果列表为空)
- ✅ 切换到世界书标签页时重新加载
API调用:
// WorldBookSlice.jsx 第135行
const response = await fetch(`/api/worldbooks/`);
后端路由:
# worldbooksRoute.py 第28行
@router.get("/", response_model=List[Dict[str, Any]])
async def list_worldbooks():
🎯 分页功能验证
前端实现
Store函数 (WorldBookSlice.jsx 第343-374行):
fetchWorldBookEntries: async (name, page = 1, page_size = 20) => {
const response = await fetch(
`/api/worldbooks/${name}/entries?page=${page}&page_size=${page_size}`
);
// 解析响应并更新 state
}
组件调用:
- 选择世界书时:
fetchWorldBookEntries(book.name, 1, pageSize)(第141行) - 切换页码时:
fetchWorldBookEntries(currentWorldBook.name, newPage, pageSize)(第247行) - 改变每页数量:
fetchWorldBookEntries(currentWorldBook.name, 1, newPageSize)(第259行)
分页状态:
entriesPagination: {
total: data.total || 0,
page: data.page || 1,
page_size: data.page_size || 20,
total_pages: data.total_pages || 0
}
后端实现
API路由 (worldbooksRoute.py 第108-128行):
@router.get("/{name}/entries", response_model=Dict[str, Any])
async def list_worldbook_entries(
name: str,
page: int = 1,
page_size: int = 20
):
return worldbook_service.list_entries(name, page, page_size)
服务层 (worldbook_service.py 第168-198行):
def list_entries(name: str, page: int = 1, page_size: int = 20) -> Dict[str, Any]:
all_entries = data.get("entries", [])
total = len(all_entries)
start_idx = (page - 1) * page_size
end_idx = start_idx + page_size
paginated_entries = all_entries[start_idx:end_idx]
return {
"entries": paginated_entries,
"total": total,
"page": page,
"page_size": page_size,
"total_pages": (total + page_size - 1) // page_size
}
📊 数据格式
后端返回格式(分页)
{
"entries": [...],
"total": 30,
"page": 1,
"page_size": 20,
"total_pages": 2
}
前端State结构
{
worldBooks: [], // 世界书列表
currentWorldBook: null, // 当前选中的世界书
currentEntries: [], // 当前页的条目列表
entriesPagination: { // 分页信息
total: 0,
page: 1,
page_size: 20,
total_pages: 0
}
}
✨ 优化记录
已完成的优化
- ✅ 组件初始化加载: 添加
useEffect在组件挂载时立即加载世界书列表 - ✅ 格式统一: 所有世界书文件转换为内部格式存储
- ✅ 代码简化: 移除服务层的SillyTavern格式运行时兼容逻辑
- ✅ 分页控件: 添加完整的分页UI(上一页、下一页、每页数量选择)
- ✅ 自动刷新: 添加/更新/删除条目后自动刷新当前页
🧪 测试建议
手动测试清单
- 打开世界书页面,检查下拉框是否显示所有世界书
- 选择一个世界书,检查是否正确加载第一页条目
- 点击"下一页",检查是否加载第二页
- 改变每页数量(10/20/50/100),检查是否正确刷新
- 创建新条目,检查是否刷新当前页
- 更新条目,检查是否刷新当前页
- 删除条目,检查是否刷新当前页
- 切换到其他世界书,检查是否重置到第一页
API测试
# 获取世界书列表
curl http://localhost:8000/api/worldbooks/
# 获取条目(分页)
curl "http://localhost:8000/api/worldbooks/卡立创-v5/entries?page=1&page_size=5"
📝 结论
✅ 前端世界书分页的所有功能都能正确发出请求到后端API
- 下拉框正确读取所有世界书
- 分页参数正确传递
- 数据格式匹配
- 错误处理完善
- 用户体验流畅