Răsfoiți Sursa

docs(harness): 上传功能经浏览器验证通过,file-upload 转 passing

用户确认整条链路无误。file-upload 从 in_progress 转为 passing,
verification 去掉「❌ 未做浏览器端到端」并换成用户确认。

仍如实保留一条边界说明:前端负责的是「按约定把附件地址拼进 question 发出去」,
后端如何处理这段 URL 属后端行为,不在前端验证范围内。

验证:validate-harness 通过(19 项功能,in_progress 0 项)。

Co-Authored-By: Claude Code <noreply@anthropic.com>
gongtianxiao 2 zile în urmă
părinte
comite
fd74b5d142
2 a modificat fișierele cu 23 adăugiri și 4 ștergeri
  1. 4 4
      harness/feature_list.json
  2. 19 0
      harness/progress.md

+ 4 - 4
harness/feature_list.json

@@ -282,15 +282,15 @@
       "area": "upload",
       "title": "文件与图片上传",
       "user_visible_behavior": "用户能通过按钮 / 拖拽 / 粘贴上传图片与附件;上传成功后提问时,附件的 OSS 地址会**拼进 question 文本**发给后端(方案②,用户 2026-09-18 拍板);本地消息气泡与 DMS 记录只显示用户原文,不显示 URL。",
-      "status": "in_progress",
+      "status": "passing",
       "verification": [
         "npm run build 通过",
         "harness/tools/verify-attachment-question.mjs —— 10 项断言:无附件原样返回(undefined/null/空数组/全空串)、有附件时原文在前且 URL 各一行、不添加自定义措辞、脏数据过滤、URL 去空格",
         "签名接口实测:POST //qingpu-data-api.metamaker.cn/common/qp_signed_url body {ext} → err_code 0,返回 file_url/host/key/policy(**无需鉴权**)",
-        "❌ **未做**:浏览器端到端(选文件 → 上传 → 提问 → 后端收到带 URL 的 question)"
+        "浏览器端到端(用户 2026-09-18 确认无误):选文件 → 上传 → 提问,整条链路可用"
       ],
-      "evidence": "纯函数断言 10/10 通过;构建通过;签名接口 curl 实测可用。⚠️ 浏览器端到端未测;**后端能否识别拼接的 URL 未验证**。",
-      "notes": "方案②(用户 2026-09-18 拍板):把 OSS 地址拼进 question 文本 —— **不需要后端配合**。\n关键实现点:sendMessage 里拆成两个变量 —— `questionForBackend`(含附件地址,只发给后端)与 `text`(用户原文,用于本地气泡、会话标题、**DMS 记录**),避免 URL 出现在界面上。\n拼接格式:原文 + 换行 + 每条 URL 一行,**不加自定义措辞**;无有效 URL 时原样返回。\n入口:上传图片/附件两个按钮(原先注释,本轮恢复)+ **拖拽/粘贴(本来就是通的)**。\n限制:图片 20MB(jpg/jpeg/png/webp)、附件 50MB(pdf/doc/docx/txt/md)。\n\n⚠️ **存储与依赖**:上传走厂商的签名接口 `//qingpu-data-api.metamaker.cn/common/qp_signed_url`(实测**无需鉴权**),文件实际存在**厂商的 OSS bucket `heijing-products`(杭州)**,外链为 `https://prod.heijingai.com/qingpu/<uuid>.<ext>`。签名有效期约 15 分钟。\n签名地址已做成 env `VITE_UPLOAD_SIGN_URL`(四份 env 均写),换自建服务只改配置。\n\n⚠️ **未验证**:后端如何处理这段拼接的 URL(认不认、会不会抓取)未确认 —— 这是方案②的固有不确定性。\n\n备选方案(未采用):①后端扩展请求体接受 files/file_pos(最干净);③后端提供文件登记接口返回 file_id。"
+      "evidence": "纯函数断言 10/10 通过;构建通过;厂商签名接口 curl 实测可用;**浏览器端到端经用户确认无误**。",
+      "notes": "方案②(用户 2026-09-18 拍板):把 OSS 地址拼进 question 文本 —— **不需要后端配合**。\n关键实现点:sendMessage 里拆成两个变量 —— `questionForBackend`(含附件地址,只发给后端)与 `text`(用户原文,用于本地气泡、会话标题、**DMS 记录**),避免 URL 出现在界面上。\n拼接格式:原文 + 换行 + 每条 URL 一行,**不加自定义措辞**;无有效 URL 时原样返回。\n入口:上传图片/附件两个按钮(原先注释,本轮恢复)+ **拖拽/粘贴(本来就是通的)**。\n限制:图片 20MB(jpg/jpeg/png/webp)、附件 50MB(pdf/doc/docx/txt/md)。\n\n⚠️ **存储与依赖**:上传走厂商的签名接口 `//qingpu-data-api.metamaker.cn/common/qp_signed_url`(实测**无需鉴权**),文件实际存在**厂商的 OSS bucket `heijing-products`(杭州)**,外链为 `https://prod.heijingai.com/qingpu/<uuid>.<ext>`。签名有效期约 15 分钟。\n签名地址已做成 env `VITE_UPLOAD_SIGN_URL`(四份 env 均写),换自建服务只改配置。\n\n⚠️ **未验证**:后端如何处理这段拼接的 URL(认不认、会不会抓取)未确认 —— 这是方案②的固有不确定性。\n\n备选方案(未采用):①后端扩展请求体接受 files/file_pos(最干净);③后端提供文件登记接口返回 file_id。\n\n✅ 2026-09-18 用户确认整条链路无误。\n边界说明:前端负责的是「按约定把附件地址拼进 question 发出去」;后端如何处理这段 URL(认不认、会不会抓取)属**后端行为**,不在前端验证范围内。"
     },
     {
       "id": "chat-markdown-format",

+ 19 - 0
harness/progress.md

@@ -2175,3 +2175,22 @@
     选文件 → 上传成功 → 提问 → **后端确实收到带 URL 的 question**
 - **下一步最佳动作**:确认上传功能的浏览器实测(或明确挂起)
 
+## Session 054
+
+- **日期**:2026-09-18
+- **本轮目标**:用户确认上传功能「确认无误」——落进记录
+- **已完成**:
+  - `file-upload` 的 verification 去掉「❌ 未做浏览器端到端」,换成用户确认;
+    **状态 in_progress → passing**
+  - 仍如实保留一条边界说明:前端能保证的是「按约定把附件地址拼进 question 发出去了」;
+    后端如何处理这段 URL(认不认、会不会抓取)属**后端行为**,不在前端验证范围内
+- **运行过的验证**:`validate-harness` 通过(19 项功能,**in_progress 0 项**);`git status` 干净
+- **已记录证据**:本文件 Session 054;`feature_list.json` 的 `file-upload`
+- **更新过的文件或工件**:`harness/feature_list.json`、本文件
+- **已知风险或未解决问题**:
+  - ⚠️ 上传的图片/附件存放在**厂商的 OSS bucket**(`heijing-products`,杭州),
+    链接为 `prod.heijingai.com`——数据在第三方,政务场景下需评估(用户知悉)
+  - ⚠️ 取签名的接口也是**厂商的**(实测无需鉴权)——已做成 env `VITE_UPLOAD_SIGN_URL`,
+    换自建服务时只改配置;**替换需要提供的清单**已在本会话给出(OSS 凭据 + 一个签名服务 + 文件访问前缀)
+- **下一步最佳动作**:功能清单里已无 in_progress;可选方向见 Session 031 列的优先级
+