PLAN-FNOS-024 CodeBuddy 403 纳入账号切换
| 字段 | 内容 |
|---|---|
| 计划编号 | PLAN-FNOS-024 |
| 计划日期 | 2026-10-21 |
| 对应需求 | FNOS-024 CodeBuddy 403 纳入账号切换 |
| 本轮功能 | FNOS-024-01、FNOS-024-02 |
| 计划状态 | 已完成(阶段一完成;阶段二以适配器级集成验证替代界面走查) |
计划目标
把「其它 403」变成可切换的账号级失败:独立错误码 → 进入换号集合 → 可见提示。内容拦截与 401 的既有语义保持不变。
当前实现与目标设计
| 领域 | 当前实现 | 目标实现 | 迁移影响 |
|---|---|---|---|
| 403 分类 | `401 | 403统一映射AUTH` | |
| 换号触发 | 额度 / 限流 / 受限 | 追加 ACCOUNT_FORBIDDEN | 403 触发切换 |
| 自动切换偏好 | 拦住额度/限流;受限例外 | ACCOUNT_FORBIDDEN 同样例外(账号已被上游拒绝,保持原账号只会继续失败) | 偏好语义不变,例外集合扩大为「账号级失败」 |
| 切换提示 | 按原因分三类 | 追加「账号被上游拒绝(HTTP 403)」 | 提示更准确 |
| 受限集合 | 仅 11140 写入 | 不写入:403 可能是临时策略拒绝,长期排除会误伤 | 403 只在本次请求内排除(已尝试集合) |
为什么 403 要例外于自动切换偏好
与 FNOS-023 同一理由:该账号已被上游拒绝,继续用它只会重复失败;切换是恢复可用性的唯一手段,而可见提示保证用户知情。
为什么不把 403 记入受限集合
11140 是持续的账号状态(需重新登录),因此跨请求排除是合理的;其它 403 可能只是某次请求的策略拒绝(例如内容/来源判定),把它当作长期状态会让一个可用账号被永久跳过。因此只在本次请求内排除(复用既有的「已尝试」集合)。
影响范围分析
| 需求功能 | 代码模块 | 配置/数据 | 测试 | 文档 | 目标环境 |
|---|---|---|---|---|---|
| FNOS-024-01 | src/host/adapter.ts(分类、换号触发) | 无 | 分类与触发单测 | docs/plugins/dsh-codebuddy.md 补自动切换说明 | 本地构测 + DSH Web(桩注入) |
| FNOS-024-02 | src/host/adapter.ts(提示文案) | 无 | 文案单测 | 同上 | 本地构测 |
分阶段任务
阶段一:实现与本地验证
| 任务 ID | 对应需求/验收 | 修改内容 | 前置条件 | 验证方式 |
|---|---|---|---|---|
| PLAN-FNOS-024-T01-01 | FNOS-024-01 / AC-02 | 分类拆分:内容拦截 → CONTENT_BLOCKED;受限 → ACCOUNT_RESTRICTED;其余 403 → ACCOUNT_FORBIDDEN;401 → AUTH | 无 | 单测覆盖四种分支,互不混淆 |
| PLAN-FNOS-024-T01-02 | FNOS-024-01 / AC-01 | 把 ACCOUNT_FORBIDDEN 纳入换号集合,并与受限一样不受自动切换偏好限制 | T01-01 | 单测:偏好关闭时仍切换;额度/限流仍被偏好拦住 |
| PLAN-FNOS-024-T01-03 | FNOS-024-02 / AC-01 | 提示文案追加 403 原因分支 | T01-02 | 单测:四类原因文案正确 |
| PLAN-FNOS-024-T01-04 | FNOS-024-01 / AC-02 | 确认不把 403 写入受限集合(只在本次请求内排除) | T01-02 | 源码断言 + 单测:受限集合仅由 11140 写入 |
| PLAN-FNOS-024-T01-05 | 回归 | 插件全量测试与构建 | T01-01~T01-04 | 全部用例通过;typecheck 与 build 通过 |
阶段二:桩注入验证
| 任务 ID | 对应需求/验收 | 修改内容 | 前置条件 | 验证方式 |
|---|---|---|---|---|
| PLAN-FNOS-024-T02-01 | FNOS-024-01 / AC-01、AC-02 | 本地桩让聊天端点返回 403(不带业务码),活动账号指向该桩;其余请求代理到真实上游 | 阶段一完成 | DSH Web 中发送消息:自动切换至真实账号并完成,界面显示 403 原因的提示 |
执行进展
| 阶段 | 状态 | 说明 |
|---|---|---|
| 阶段一 实现与本地验证 | 已完成 | T01-01~T01-05 全部完成;插件 943 条用例全绿,typecheck 与 build 通过。 |
| 阶段二 桩注入验证 | 已完成 | 以适配器级集成验证执行(本地 DSH Web 的新建会话需先选工作区,自动化点击未能完成,改用等价且更直接的适配器级验证):桩 403 → 切到真实账号 → finish: stop,提示文本正确。 |
数据、权限和错误处理
- 无新增持久化数据、无权限变化。
- 错误处理变化:非受限 403 由
AUTH(不换号)变为ACCOUNT_FORBIDDEN(换号);内容拦截与 401 不变。
依赖、风险和决策
| 项 | 说明 |
|---|---|
| 依赖 | 无新增依赖 |
| 风险一 | 若上游用 403 表示「请求内容问题」,换号仍会失败并多消耗一次尝试。缓解:单次请求内尝试次数由账号数封顶(既有约束),失败如实抛出 |
| 风险二 | 误把内容拦截当 403 换号:已有业务码前置判定兜住(11128 先于 403 分支) |
| 决策 | 403 不写入受限集合 |
| 决策 | 403 与受限一样绕过自动切换偏好 |
测试、打包、发布和回滚
- 本地包级:typecheck、单测、构建;覆盖四类分类、触发、文案、不写入受限集合。
- 桩注入:DSH Web 中验证 403 触发切换与提示可见。
- 回滚:分类与触发同一处改动,回滚后 403 回到
AUTH不换号,无残留状态。 - 禁止删除:凭据、账号、会话数据不涉及。
参考资料
| 来源 | 用途 |
|---|---|
plugins/dsh-codebuddy-plugin 的错误分类与换号实现 | 现状取证 |
| FNOS-022、FNOS-023 | 内容拦截不换号、受限已换号的既有结论 |
仓库规范 docs/charter/*-spec.md | 文档与验证要求 |
变更记录
| 日期 | 变更 | 说明 |
|---|---|---|
| 2026-10-21 | 建立 PLAN-FNOS-024 | 两阶段 6 个任务:分类拆分、纳入换号、提示分支、不写入受限集合、回归、桩注入验证。登记 2 项风险与 2 条决策。 |
| 2026-10-21 | 实现完成并验证 | 按设计落地四类分类与换号触发;提示新增 403 分支。阶段二的界面走查被本地 Web 的「选择工作区」交互挡住,改为适配器级集成验证(假 session + 403 桩 + 真实上游账号),直接断言切换、完成状态与提示文本,结果通过。另记录两个与本改动无关的既有不稳定用例(旅行并发、登录 URL 网络用例)。 |