Files
user-system/docs/code-review/REMEDIATION_PLAN_2026-05-30.md
2026-05-30 21:29:24 +08:00

13 KiB
Raw Permalink Blame History

user-system 修复执行计划(按 P0 / P1 / P2 排序)

计划日期2026-05-30
输入依据docs/code-review/FULL_REVIEW_2026-05-30.md
目标:修复本轮 review 暴露出的安全、正确性、测试与文档一致性问题,并形成新的可审计验证证据。


一、执行原则

  1. 先修协议与契约,再修测试与文档
    • 先修 SSO / Swagger / 路由契约错误
    • 再收敛测试与静态检查
  2. 每一类问题修完都必须立即验证
  3. 文档只能反映已验证事实,不能提前宣称完成
  4. 对外可见契约必须单点真实
    • 路由
    • Swagger
    • 前端调用
    • 测试断言
    • 状态文档
  5. 修复计划必须覆盖 review 报告中的全部问题
    • 不能只修“代表性问题”
    • 必须处理系统性问题源头

二、P0 修复计划(必须最优先)

P0-1把空壳 Swagger 修成真实有效文档

目标

/swagger/*any 对应的不是空 paths,而是真实可用 OpenAPI 文档。

具体动作

  1. 梳理 Swagger 生成入口与当前生成流程
  2. 确认 swag init 或项目既定生成方式
  3. 生成有效 docs/swagger.go / docs/docs.go
  4. 校验 paths 非空
  5. 校验至少以下路径存在:
    • /api/v1/auth/login
    • /api/v1/auth/register
    • /api/v1/admin/users/export
    • /api/v1/users/{id}

验证

  • 生成 Swagger
  • 检查 docs/swagger.gopaths 非空
  • 如可本地启动,验证 /swagger/index.html/swagger/doc.json 可用

P0-2系统性修正 Swagger 注释与真实路由的漂移

这是对报告中“系统性契约漂移”的完整修复,不再只处理导入导出接口。

目标

统一以下来源的 API 契约:

  • internal/api/router/router.go
  • internal/api/handler/*.go 中全部 @Router
  • docs/API.md
  • 前端调用与测试
  • 生成后的 Swagger 文档

具体动作

  1. 全量审计并修复以下类别的 @Router 漂移:
    • export/importadmin 路径
    • refresh/refresh-token/refresh
    • email-code login/login-by-email-code/login/email-code
    • resend activation/resend-activation-email/resend-activation
    • TOTP/auth/totp/*/auth/2fa/*
    • captcha/captcha/*/auth/captcha*
    • password reset/auth/password/*/forgot-password / /reset-password / phone 变体
    • custom fields/fields/*/custom-fields/*
    • logs/users/me/*logs/logs/*/me
    • admins/users/admins/admin/admins
    • users/me 绑定类接口bind-email / bind-phone / social accounts
  2. 修复 HTTP method 漂移:
    • AssignRolesPOSTPUT
    • AssignPermissionsPOSTPUT
    • SetupTOTP:注释 method 与真实 method 对齐
  3. 对照 router.go 做一次全量注释-路由对账,直到关键差异清零
  4. 更新 docs/API.md 中对应路径
  5. 重新生成 Swagger 文档

验证

  • go test ./internal/api/handler ./internal/api/router -count=1
  • 生成 Swagger 后检查关键路径与 method 全部正确
  • 使用脚本或审查清单确认:关键业务路由不再存在注释/注册漂移

P0-3修复 SSO 授权码模式未绑定 redirect_uri 的问题

目标

让 authorization code 与 client / redirect URI 形成强绑定。

具体动作

  1. internal/auth/sso.goSSOSession 中加入 RedirectURI
  2. GenerateAuthorizationCode(...) 保存该字段
  3. Token(...) 兑换令牌时校验:
    • session.ClientID == req.ClientID
    • session.RedirectURI == req.RedirectURI
  4. 对不匹配场景返回明确错误
  5. 为此补回归测试

验证

  • go test ./internal/auth ./internal/api/handler -count=1
  • 增加测试覆盖:
    • 正确 client + redirect_uri 成功
    • 错误 redirect_uri 失败
    • 错误 client_id 失败

P0-4禁用 implicit flow

目标

系统只支持更安全的授权码模式,不再通过 fragment 返回 access token。

具体动作

  1. 修改 internal/api/handler/sso_handler.go
  2. response_type=token
    • 返回 400 unsupported response_type
    • 或仅允许 code
  3. 清理相应的宽松测试
  4. 同步文档说明只支持 code flow

验证

  • response_type=token 应明确失败
  • response_type=code 正常工作

P0-5重构 SSO 路由分组与鉴权模型,使 /token/introspect/revoke/userinfo 语义正确

这是第二轮新增问题若不修P0-3/P0-4 仍不完整。

目标

让 SSO/OAuth 相关端点符合正确的访问控制模型,而不是错误复用平台用户 BearerAuth。

具体动作

  1. 将 SSO 路由按语义拆分,不再整体挂在 protected
  2. 至少区分:
    • /authorize:需要当前平台登录用户完成授权
    • /token:客户端凭证 + 授权码模型,不依赖当前平台 BearerAuth
    • /introspect:客户端认证模型
    • /revoke:客户端认证模型或 token-owner 受控模型,必须明确
    • /userinfo:基于 SSO access token而不是平台 JWT 上下文
  3. /token/introspect/revoke 设计明确的 client auth 机制
  4. 修正 UserInfo 的 token 解析来源,不能继续直接读平台 auth middleware 的 user_id
  5. 同步更新测试与文档

验证

  • /token 在无平台 BearerAuth、仅有正确 client/code 条件下可成功
  • /introspect / /revoke 不接受任意平台登录用户代操作
  • /userinfo 返回的是 SSO token subject而不是平台当前 session user

三、P1 修复计划(紧随 P0

P1-1修复 go vet ./... 失败并收口静态分析门禁

目标

让项目重新具备诚实宣称 go vet 通过的资格。

具体动作

  1. 修复:
    • internal/api/handler/avatar_handler_test.go
    • internal/api/handler/export_handler_test.go
  2. 所有 resp 使用前先检查 err
  3. 扫描同类 helper/测试模式,避免只修报错行

验证

  • go vet ./...
  • go test ./... -count=1

P1-2把宽松状态码测试改成严格契约测试

目标

让测试真正约束行为,而不是“什么都算通过”。

具体动作

  1. 优先重写以下测试文件:
    • internal/api/handler/export_handler_test.go
    • internal/api/handler/sso_handler_test.go
  2. 逐场景收紧断言:
    • 未认证 → 401
    • 未授权 → 403
    • 参数错误 → 400
    • 成功 → 200 / 302
  3. 删除允许 500 的正常断言路径
  4. 对有环境差异的场景,先修被测逻辑,再收紧测试
  5. 针对 SSO 补充协议级回归测试:
    • /token 不再被平台 BearerAuth 门禁误拦
    • /introspect / /revoke 权限模型正确
    • /userinfo 基于 SSO token而不是平台 session
  6. 对关键契约类 handler 增加“路由/方法/状态码固定断言”

验证

  • 受影响包 go test -count=1
  • 必须确保断言收紧后仍稳定通过

P1-3强化 JWT secret 治理为启动硬门禁

目标

让 release 模式下的 JWT 配置符合项目自身文档标准。

具体动作

  1. 明确 config.Load() 下的正常启动规则
  2. 在 release/standard 服务路径中强制:
    • secret 缺失 → fail fast
    • weak secret → fail fast
  3. 保留 LoadForBootstrap() 仅用于初始化场景
  4. 增加配置单元测试

验证

  • go test ./internal/config -count=1
  • 缺失/弱 secret 场景必须失败

P1-4接通用户状态 / 权限变更后的缓存失效链路

目标

避免密码、状态、角色、权限变更后继续使用陈旧缓存。

具体动作

  1. 梳理以下写路径:
    • ChangePassword
    • UpdateStatus
    • BatchUpdateStatus
    • AssignRoles
    • DeleteAdmin
    • AssignPermissions
  2. 设计缓存失效注入方式
    • 推荐通过依赖注入引入失效能力
    • 不要让 service 直接依赖具体 middleware 实现细节
  3. 在写路径完成后主动失效:
    • user_state
    • user_perms
    • 受影响角色下的用户权限缓存

验证

  • 增加回归测试:
    • 改密码后旧 token / 旧状态缓存失效
    • 改角色/权限后权限即时生效

P1-5清理拟真 secret 示例

目标

恢复文档敏感边界清洁度。

具体动作

  1. 清理 docs/archive/OAUTH_INTEGRATION.md 中拟真值
  2. 全仓搜索其它类似格式示例
  3. 统一替换为显式占位符

验证

  • 搜索确认无拟真 secret 示例残留

四、P2 修复计划(在 P0/P1 收口后处理)

P2-1修复 strconvAtoi 吞错问题

目标

非法 status 参数返回显式错误,而不是静默当作 0。

动作

  1. 修改 internal/api/handler/export_handler.gostrconvAtoi
  2. 非数字输入返回 error
  3. ExportUsers 中对非法 status 返回 400
  4. 增加回归测试

验证

  • status=abc → 400

P2-2头像上传改为流式写盘

目标

消除不必要的整块内存分配。

动作

  1. os.Create + io.Copy 代替 Read + WriteFile
  2. 保持现有 magic bytes 校验逻辑
  3. 确保失败时清理半成品文件

验证

  • 头像上传相关测试通过
  • 文件写入失败场景仍能回滚

P2-3头像上传响应改为明确 struct

目标

让返回 schema 与注释一致。

动作

  1. 引入明确响应 struct
  2. 更新 Swagger 注释 / handler 返回值
  3. 同步前端类型

验证

  • 相关 handler test
  • 前端编译通过

P2-4前端构建大 chunk 警告优化

目标

降低主包体积,改善生产可维护性。

动作

  1. 识别大 chunk 页面
  2. 做路由级动态拆分
  3. 必要时拆分 antd 重型页面模块

验证

  • npm run build
  • 观察 chunk 体积变化

五、修复计划完整性审核

本节用于确认:计划是否覆盖 review 报告中的全部问题

Review 问题 计划覆盖项 覆盖状态
Swagger 空壳 P0-1 已覆盖
Swagger 注释与真实路由系统性漂移 P0-2 已覆盖
SSO code 未绑定 redirect_uri P0-3 已覆盖
SSO implicit flow P0-4 已覆盖
SSO /token /introspect /revoke /userinfo 鉴权模型错误 P0-5 已覆盖
宽松状态码测试掩盖问题 P1-2 已覆盖
go vet 不通过 P1-1 已覆盖
JWT secret 硬门禁不足 P1-3 已覆盖
状态 / 权限缓存失效未接入 P1-4 已覆盖
拟真 secret 示例 P1-5 已覆盖
strconvAtoi 吞错 P2-1 已覆盖
头像整块读入内存 P2-2 已覆盖
头像响应 schema 漂移 P2-3 已覆盖

审核结论

当前修复计划已经覆盖 review 报告中的全部问题项
其中最关键的改进是:

  • 不再把“Swagger 路由错误”视为单点问题,而是按系统性契约漂移处理
  • 新增 P0-5明确修复 SSO route group / auth model 的结构性错误

这两点补齐后,计划才具备“能够完整修复 review 报告问题”的条件。


六、推荐执行顺序

阶段 1协议与契约止血

  1. P0-5 修 SSO route group / auth model
  2. P0-3 修 SSO code / redirect_uri 绑定
  3. P0-4 禁 implicit flow
  4. P0-2 系统性修正 Swagger 注释与真实路由漂移
  5. P0-1 生成有效 Swagger

阶段 2质量门禁与测试收口

  1. P1-1 修复 go vet
  2. P1-2 收紧 export / sso / 契约类 handler 测试
  3. P1-3 强化 JWT secret 启动门禁

阶段 3一致性与边界治理

  1. P1-4 接通缓存失效链路
  2. P1-5 清理拟真 secret 示例

阶段 4实现质量优化

  1. P2-1 修 status 参数吞错
  2. P2-2 头像流式写盘
  3. P2-3 头像响应 struct 化
  4. P2-4 前端 chunk 优化

七、每阶段完成后的最小验证矩阵

P0 阶段后

go test ./internal/auth ./internal/api/handler ./internal/api/router -count=1
go build ./cmd/server

并检查 Swagger 生成结果。

P1 阶段后

go vet ./...
go test ./... -count=1
go build ./cmd/server
cd frontend/admin && env -u NODE_ENV npm run test:run
cd frontend/admin && env -u NODE_ENV npm run build

P2 阶段后

按受影响范围重跑:

go test ./internal/api/handler ./internal/service ./internal/repository -count=1
cd frontend/admin && env -u NODE_ENV npm run build

八、完成标准

只有同时满足以下条件,才能把本轮问题标记为“已收口”:

  1. SSO code flow 绑定完整implicit flow 已禁用
  2. SSO /token/introspect/revoke/userinfo 的访问控制模型正确
  3. Swagger 文档非空且关键路径正确
  4. 注释 / 路由 / 文档 / 前端 / 测试中的 API 契约一致
  5. go vet ./... 通过
  6. handler 关键测试不再接受互斥状态码混过
  7. JWT secret 治理与项目文档标准一致
  8. 缓存失效链路有真实接入与回归测试
  9. 状态文档与 README 只保留已验证事实