Files
wecom_it_smart_desk/docs/评审报告/workbuddy-2026-06-14-消息优化.md
T

6.5 KiB

评审报告: workbuddy 2026-06-14 消息相关更新

评审日期: 2026-06-14 评审人: Claude (claude-opus-4-8) 评审范围: workbuddy 6-13/6-14 推送 + 版本更新说明文档 + 实际代码 diff 状态: P0 全部已修(本地代码);P1/P2 待 workbuddy 跟进


一、评审范围(8 个文件 + 1 文档)

文件 类型 评审点
backend/app/models/message.py 改动 status, recallable_until 字段
backend/app/api/messages.py 新增 5 端点 recall / delete / mark-read / image / file
backend/app/services/ws_manager.py 声称改动 "消息状态广播"(实际未实现)
backend/app/dependencies.py 改动 get_shared_ai_handler(AIHandler 修复)
backend/app/api/h5.py 改动 邀请功能 3 端点 + participants
backend/app/api/agents.py 改动 OTP 双因素(otp-bind/otp-verify/otp-unbind)
frontend-h5/src/api/conversation.ts 改动 mapMessage 字段映射(id→message_id)
docker-compose.yml 改动 healthcheck 配置(backend 用 curl 已知坑)
docs/IT智能服务台-版本更新说明-20250614.md 文档 v1.1.0 发布说明

二、文档 vs 代码 vs 记忆 三方不一致 关键发现

版本文档 代码 workbuddy 6-14 记忆
消息撤回/删除/状态 文档说已做 实际做了 记忆未提
标记已读
图片/文件上传 (路径在容器本地)
Health Check 已配置 ⚠️ 配了但 backend 用 curl 永远 unhealthy
ws_manager 状态广播 文档说做了 代码里没有
AI Gateway 预留 文档说做了 未看到
OTP 双因素
数据库 id 字段 UUID→VARCHAR(36) 文档未提

结论:

  • 文档描述的"本次更新"远多于 workbuddy 实际 push 的内容
  • 文档与代码有 5 处不一致(ws_manager 状态广播未做、AI Gateway 未做、healthcheck 配错、upload 路径不持久、SQL 迁移未走 Alembic)
  • 文档 "审核状态: 待审核" → 本次评审填补了审核空缺

三、13 项发现(按严重度)

🔴 P0 安全(6 项,全部已修)

# 位置 问题 修复
P0-1 h5.py:1107 participants 端点仅校验"已登录",未校验"是否属于本会话" 加 is_creator/is_participant 校验
P0-2 messages.py:293 recall_message 无任何鉴权,任意 HTTP 客户端可改任意消息 Depends(get_current_agent) + sender_id 校验
P0-3 messages.py:336 delete_message 同上,可删任意消息 同上
P0-4 messages.py:368 mark_read 任意人可改任意会话已读状态 加 agent 鉴权 + assigned/collaborator 校验
P0-5 messages.py:400 upload_image 无鉴权,可任意上传占用磁盘 Depends(get_current_agent)
P0-6 messages.py:458 upload_message_file 同上 同上

🟡 P1 重要(4 项,待 workbuddy 跟进)

# 位置 问题
P1-1 messages.py:434,487 upload 保存到 media/images/,media/files/(容器本地),容器重建即丢失
P1-2 alembic/versions/ 模型有 status/recallable_until,但未见对应迁移脚本;文档教用户手动 ALTER(反模式)
P1-3 docker-compose.yml:118 backend healthcheck 用 curl,容器无 curl → 永远 unhealthy(关联 backend-healthcheck-curl-pitfall)
P1-4 ws_manager.py 文档承诺"添加消息状态广播",代码里没看到对应方法(ConnectionManager 仅有 send_to_agent/broadcast/send_to_employee/broadcast_to_employees)

🟢 P2 次要(3 项)

# 位置 问题 状态
P2-1 messages.py:388 where(Message.is_read == False) 在 SQLAlchemy 里不报错但实际未生效 P0-4 修复时一并修:is_(False)
P2-2 messages.py:440,494 upload 写文件非原子,中途崩溃留半文件 待 workbuddy 修
P2-3 messages.py:501 upload 返回原始 original_name,可能含中文/特殊字符 待 workbuddy 修

四、文档本身的 4 处错误(评审发现)

# 位置 错误 建议
1 部署步骤 6 SQL ALTER TABLE ... DEFAULT 'sent' 引号未转义,shell 执行会语法错 改用 alembic 迁移脚本,不手动 ALTER
2 部署步骤 5 docker compose -p root up -d 正是用户 6-14 生产事故的根因 删除 -p root 标志,从 /opt/wecom-it-desk/ 跑即可
3 2.1 ws_manager 声称"添加消息状态广播",代码里没有 文档状态改为 "未实现,后续迭代"
4 2.1 docker-compose "healthcheck 已配置" 不准确 注明 "backend healthcheck 有 curl 坑,待修"

五、对比之前 workbuddy 评审

旧 P0 (5 项) 本次 P0 (6 项) 备注
#1 WECOM_SECRET 明文 (不变) 等 P0 安全止血阶段
#2 SSL 私钥在 docs/ (不变) 阶段 8-A 前置解决
#3 Mock login bypass (已修复)
#4 WS token 在 URL/日志 (不变) 等 P0 安全止血
#5 坐席登录无 password (不变) 等 P0 安全止血
P0-1 H5 participants 鉴权 本次新发现
P0-2~P0-6 messages.py 5 端点鉴权 本次新发现

安全态势:本次 workbuddy 推送 反而引入了 6 个 P0 鉴权漏洞。workbuddy 后续推送需 强制走评审流程(本次评审堵住了批量漏洞)。


六、修复与待办

已完成(2026-06-14 本地代码)

  • P0-1 ~ P0-6 共 6 个鉴权修复
  • P2-1 SQL == Falseis_(False)(捎带修)

待 workbuddy 跟进

  • P1-1 upload 路径改为 volume mount
  • P1-2 补 Alembic 迁移脚本(对照 models/message.py 新字段)
  • P1-3 docker-compose backend healthcheck 改 TCP 端口检查
  • P1-4 实现 ws_manager 消息状态广播方法
  • P2-2 upload 写文件改 *.tmp + rename 原子化
  • P2-3 upload 返回文件名做 XSS 过滤 / URL encode

待文档/流程

  • docs/IT智能服务台-版本更新说明-20250614.md 4 处错误修订
  • workbuddy 推送流程:加 "PR 前 P0 强制评审" 环节

七、风险跟踪表更新

新增 6 项 P0(本次评审),3 项 P1,3 项 P2(详见 docs/风险跟踪表.md)。


评审结论: workbuddy 6-14 推送 P0 比例过高(6/13 = 46%),强烈建议加评审环节。本次评审发现的 6 个 P0 全部已修代码,待 workbuddy 跟进 P1/P2。