2026-04-19-03-03-55 修复AI撰写体验:API endpoint斜杠净化、模型列表下拉栏、聊天记录持久化存储

This commit is contained in:
2026-04-19 03:09:46 +08:00
parent d5cbbf9137
commit 9173aa7733
6 changed files with 293 additions and 20 deletions

View File

@@ -544,3 +544,47 @@ SystemSettings 需要支持 4 个服务商Kimi/DeepSeek/OpenAI/自定义)
**D. 后续如何避免问题**
- 当一组配置具有"同构多实例"特征时(多个服务商、多个环境、多个账号),优先使用 `Record<string, Config>` 而非平铺字段。
- 动态表单的 `onChange` 必须注意不可变更新:先浅拷贝外层字典,再浅拷贝当前项,最后修改目标字段。直接 `settings.aiProviders[k].endpoint = x` 会触发 React 引用比较优化导致不刷新。
---
## 记录 26API Endpoint 尾部斜杠导致 404
**A. 具体问题**
SystemSettings 中测试连接成功(`/models` 返回 200但 ReportEditor 中调用 `/chat/completions` 报 404。用户输入的 Base URL 末尾带有 `/`,导致拼接后路径为 `https://api.xxx.com/v1//chat/completions`。
**B. 产生问题原因**
用户从文档复制 Base URL 时,末尾可能带斜杠;代码中直接做字符串拼接 `${apiEndpoint}/chat/completions`,未做净化处理。
**C. 解决问题方案**
在 `handleAIGenerate` 和 `testApi` 中统一对 endpoint 做尾部斜杠移除:
```ts
const apiEndpoint = (provider?.endpoint || 'https://api.moonshot.cn/v1').replace(/\/+$/, '');
```
**D. 后续如何避免问题**
- 任何从用户输入拼接 URL 的场景,都必须先对基础路径做 `.replace(/\/+$/, '')` 或 `new URL(path, base)` 标准化处理。
- 测试连通性(`/models`)和实际业务调用(`/chat/completions`)应使用同一套 endpoint 净化逻辑,避免"测试通过、调用失败"的认知落差。
---
## 记录 27State 未纳入 Ref 导致自动保存遗漏
**A. 具体问题**
AI 撰写面板的 `chatMessages` 在路由切换后全部丢失。因为 `saveDraftToStorage` 从 `stateRef.current` 读取数据快照,而 `chatMessages` 从未被同步到 `stateRef`。
**B. 产生问题原因**
ReportEditor 采用 `useRef` 作为自动保存的数据快照机制(避免 React state 闭包陷阱)。新增 `chatMessages` state 时,只关注了 UI 渲染,遗漏了与 `stateRef` 的同步。
**C. 解决问题方案**
1. `stateRef` 初始化时包含 `chatMessages`
2. `saveDraftToStorage` 保存对象中增加 `chatMessages: stateRef.current.chatMessages`
3. 增加 `useEffect` 监听 `chatMessages` 变化,实时同步到 `stateRef.current.chatMessages`
4. 所有草稿恢复分支(初始化 useEffect 的 2 处 + useLayoutEffect 的 2 处)均增加 `chatMessages` 的恢复和 ref 同步
**D. 后续如何避免问题**
- 在 `ReportEditor.tsx` 中新增任何 `useState` 时,必须同时问自己三个问题:
1. 这个 state 是否需要持久化到 draft
2. 若需要,是否已加入 `stateRef` 初始化?
3. 若需要,是否已在 `saveDraftToStorage`、所有恢复分支、以及 state→ref 同步 effect 中补齐?
- 建议维护一份 "Draft 持久化字段清单" 注释在 `stateRef` 定义附近,作为新增 state 时的检查单。