@tea-agent/loop-agent 0.42.0-next.12 → 0.42.0-next.14

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (84) hide show
  1. package/CHANGELOG.md +25 -2
  2. package/dist/build-stamp.json +3 -3
  3. package/dist/worker/console/chat/routes.js +14 -11
  4. package/dist/worker/console/chat/sdd-data-alignment.js +13 -2
  5. package/dist/worker/console/chat/session-store.js +5 -1
  6. package/dist/worker/console/chat/turn-process.js +1 -0
  7. package/dist/worker/console/static/assets/{abnfDiagram-N423BO3Z-CcS17TBr.js → abnfDiagram-N423BO3Z-BGMbAdAG.js} +1 -1
  8. package/dist/worker/console/static/assets/{arc-COptKq2S.js → arc-CJu1LND8.js} +1 -1
  9. package/dist/worker/console/static/assets/{architectureDiagram-T3A2C74G-h4LKMHjP.js → architectureDiagram-T3A2C74G-BmJh9gMQ.js} +1 -1
  10. package/dist/worker/console/static/assets/{blockDiagram-VBNYF7ZC-COA1MOH0.js → blockDiagram-VBNYF7ZC-BWjaX3ZF.js} +1 -1
  11. package/dist/worker/console/static/assets/{c4Diagram-5PPSVZJV-DJUf0QPm.js → c4Diagram-5PPSVZJV-CLEOAxLB.js} +1 -1
  12. package/dist/worker/console/static/assets/channel-DOsaUk1k.js +1 -0
  13. package/dist/worker/console/static/assets/{chunk-2GRJ4B5K-mtWfKrUX.js → chunk-2GRJ4B5K-CydnyQUX.js} +1 -1
  14. package/dist/worker/console/static/assets/{chunk-2Q5K7J3B-B8pXsxDQ.js → chunk-2Q5K7J3B-tjJ1IoZ1.js} +1 -1
  15. package/dist/worker/console/static/assets/{chunk-5RXB4S5H-ipKzByl1.js → chunk-5RXB4S5H-DR358Phd.js} +1 -1
  16. package/dist/worker/console/static/assets/{chunk-5VM5RSS4-DYi3Ald_.js → chunk-5VM5RSS4-B-LuWFZD.js} +1 -1
  17. package/dist/worker/console/static/assets/{chunk-6Q2QTUOP-DQtGYoty.js → chunk-6Q2QTUOP-FG53fA6v.js} +1 -1
  18. package/dist/worker/console/static/assets/{chunk-GF5L2VYU-BU0qS2YV.js → chunk-GF5L2VYU-Bkt-w8SZ.js} +1 -1
  19. package/dist/worker/console/static/assets/{chunk-JWPE2WC7-DVH9dIGE.js → chunk-JWPE2WC7-WxHo0z2I.js} +1 -1
  20. package/dist/worker/console/static/assets/{chunk-KBJHAD2P-Dt60SmgM.js → chunk-KBJHAD2P-CqHrBJhp.js} +1 -1
  21. package/dist/worker/console/static/assets/{chunk-RYQCIY6F-BoaUGuEY.js → chunk-RYQCIY6F-D4MVae_f.js} +1 -1
  22. package/dist/worker/console/static/assets/{chunk-XXDRQBXY-_WHFDTp2.js → chunk-XXDRQBXY-CamBh0Ll.js} +1 -1
  23. package/dist/worker/console/static/assets/classDiagram-JCYQIIEL-D4-D49vY.js +1 -0
  24. package/dist/worker/console/static/assets/classDiagram-v2-OCEON4UE-D4-D49vY.js +1 -0
  25. package/dist/worker/console/static/assets/{cose-bilkent-JH36ORCC-BxkbTIRd.js → cose-bilkent-JH36ORCC-C3qheCuW.js} +1 -1
  26. package/dist/worker/console/static/assets/{cynefin-VYW2F7L2-Bf2UVnoG.js → cynefin-VYW2F7L2-DQlWfkS7.js} +1 -1
  27. package/dist/worker/console/static/assets/{cynefinDiagram-MW4NZA55-Bo23q1J_.js → cynefinDiagram-MW4NZA55-BAxa9rFb.js} +1 -1
  28. package/dist/worker/console/static/assets/{dagre-VZM6K2ZE-Dd_UU49i.js → dagre-VZM6K2ZE-YM09nLJw.js} +1 -1
  29. package/dist/worker/console/static/assets/{diagram-7IWD3JNH-ebUa1a9y.js → diagram-7IWD3JNH-I4W9EJj2.js} +1 -1
  30. package/dist/worker/console/static/assets/{diagram-B4RE2ZJO-BucthU8r.js → diagram-B4RE2ZJO-DH8eJ8Ff.js} +1 -1
  31. package/dist/worker/console/static/assets/{diagram-LBJQPF4R-BgqNpAkm.js → diagram-LBJQPF4R-D0D0ntDW.js} +1 -1
  32. package/dist/worker/console/static/assets/{diagram-Q27KOJAE-DC4q5NGa.js → diagram-Q27KOJAE-BIISKq1s.js} +1 -1
  33. package/dist/worker/console/static/assets/{diagram-UB23O5K3-CBqCaMeb.js → diagram-UB23O5K3--xyAWj0w.js} +1 -1
  34. package/dist/worker/console/static/assets/{ebnfDiagram-BXEA7PRR-CGtnbQ3-.js → ebnfDiagram-BXEA7PRR-B3sYXLJ4.js} +1 -1
  35. package/dist/worker/console/static/assets/{erDiagram-JOGREHBK-CG3LUao5.js → erDiagram-JOGREHBK-zRSYWhJP.js} +1 -1
  36. package/dist/worker/console/static/assets/{flowDiagram-UKHOOZJN-D2ZVgoFS.js → flowDiagram-UKHOOZJN-BUYlie03.js} +1 -1
  37. package/dist/worker/console/static/assets/{ganttDiagram-PKOTCBZU-DoYFZiKt.js → ganttDiagram-PKOTCBZU-DP4kzzrM.js} +1 -1
  38. package/dist/worker/console/static/assets/{gitGraphDiagram-DS77QQ5N-CKoP1s6j.js → gitGraphDiagram-DS77QQ5N-CAPoUxTF.js} +1 -1
  39. package/dist/worker/console/static/assets/index-CWhTyxvc.js +449 -0
  40. package/dist/worker/console/static/assets/{index-CAZ2fC_X.css → index-Dh0Gh4X0.css} +1 -1
  41. package/dist/worker/console/static/assets/{infoDiagram-6WML65LV-Duofv8p2.js → infoDiagram-6WML65LV-BXPfjekV.js} +1 -1
  42. package/dist/worker/console/static/assets/{ishikawaDiagram-WSZJBQD7-D2nlCkA1.js → ishikawaDiagram-WSZJBQD7-aOI3pV6t.js} +1 -1
  43. package/dist/worker/console/static/assets/{journeyDiagram-NVQOT4AX-Dd4IHdus.js → journeyDiagram-NVQOT4AX-DAPZuvi4.js} +1 -1
  44. package/dist/worker/console/static/assets/{kanban-definition-27J2QSJJ-Bi20AOdt.js → kanban-definition-27J2QSJJ-atwDzL3C.js} +1 -1
  45. package/dist/worker/console/static/assets/{linear-D59YJ9kB.js → linear-D5E09qji.js} +1 -1
  46. package/dist/worker/console/static/assets/{mermaid.core-Bl13LpNa.js → mermaid.core-CE4idY-s.js} +5 -5
  47. package/dist/worker/console/static/assets/{mindmap-definition-FAOFIHXS-C6DLP5eY.js → mindmap-definition-FAOFIHXS-CbZxtPca.js} +1 -1
  48. package/dist/worker/console/static/assets/{pegDiagram-VL7TDLO6-BjO4cy64.js → pegDiagram-VL7TDLO6-De-FYEte.js} +1 -1
  49. package/dist/worker/console/static/assets/{pieDiagram-7S7Q4E2Y-D7i2qZTG.js → pieDiagram-7S7Q4E2Y-Bs0USobz.js} +1 -1
  50. package/dist/worker/console/static/assets/{quadrantDiagram-CIZ2JOQS-Dx8o_h0y.js → quadrantDiagram-CIZ2JOQS-Bq3ZrGCJ.js} +1 -1
  51. package/dist/worker/console/static/assets/{railroadDiagram-AXF67PYL-B55orI_t.js → railroadDiagram-AXF67PYL-Bk8ojyIj.js} +1 -1
  52. package/dist/worker/console/static/assets/{requirementDiagram-LRYGKXZP-zWaehp6f.js → requirementDiagram-LRYGKXZP-CGhoyws1.js} +1 -1
  53. package/dist/worker/console/static/assets/{sankeyDiagram-W5VNT64P-CcA-pjvD.js → sankeyDiagram-W5VNT64P-DmVSQs3b.js} +1 -1
  54. package/dist/worker/console/static/assets/{sequenceDiagram-SI44F4Z6-BOFbzNHI.js → sequenceDiagram-SI44F4Z6-C80h1u0Q.js} +1 -1
  55. package/dist/worker/console/static/assets/{sizeCapture-X5ZJPWSS-BjAejah1.js → sizeCapture-X5ZJPWSS-CcbksQVZ.js} +1 -1
  56. package/dist/worker/console/static/assets/{stateDiagram-OKZ733FA-DXYwxJwZ.js → stateDiagram-OKZ733FA-CFTTTQKj.js} +1 -1
  57. package/dist/worker/console/static/assets/stateDiagram-v2-UEYNNEHI-C4YCesmi.js +1 -0
  58. package/dist/worker/console/static/assets/{swimlanes-SLNWSIFB-OYiOch8n.js → swimlanes-SLNWSIFB-Cw7Jr7Tg.js} +2 -2
  59. package/dist/worker/console/static/assets/swimlanesDiagram-ULZ7WXOC-lN2U_DLl.js +8 -0
  60. package/dist/worker/console/static/assets/{timeline-definition-Z64GVDOM-cZfH3nmU.js → timeline-definition-Z64GVDOM-CVcdTVa5.js} +1 -1
  61. package/dist/worker/console/static/assets/{vennDiagram-T6HMQDX7-BDE7b3E1.js → vennDiagram-T6HMQDX7-BpLbmWp9.js} +1 -1
  62. package/dist/worker/console/static/assets/{wardleyDiagram-T6FBY63Y-kyyGy9WJ.js → wardleyDiagram-T6FBY63Y-6PXfbwj-.js} +1 -1
  63. package/dist/worker/console/static/assets/{xychartDiagram-ELKLHX3M-CJj6VTog.js → xychartDiagram-ELKLHX3M-Bjkcz4ih.js} +1 -1
  64. package/dist/worker/console/static/index.html +2 -2
  65. package/dist/worker/console/static-src/chat-view-types.js +1 -1
  66. package/dist/worker/console/static-src/operator-chat/chat-sse-events.js +23 -0
  67. package/dist/worker/console/static-src/operator-chat/pending-user-message.js +32 -0
  68. package/dist/worker/console/static-src/operator-chat/turn-stream-controller.js +2 -0
  69. package/dist/worker/console/static-src/operator-chat/useChatStream.js +30 -14
  70. package/dist/worker/console/static-src/operator-chat/useChatThread.js +21 -1
  71. package/dist/worker/console/static-src/shell/workspace-route.js +4 -0
  72. package/dist/worker/observe/static/styles.css +42 -7
  73. package/dist/worker/observe/static/views/dag-inspector.js +8 -1
  74. package/dist/workflows/dag/frontend-implementation-contract.js +21 -0
  75. package/dist/workflows/dag/frontend-recovery-run.js +36 -1
  76. package/harness.json +1 -1
  77. package/package.json +1 -1
  78. package/skills/frontend-plan/references/decision-contract.md +22 -0
  79. package/dist/worker/console/static/assets/channel-DdBCaOJ6.js +0 -1
  80. package/dist/worker/console/static/assets/classDiagram-JCYQIIEL-DZFra1GO.js +0 -1
  81. package/dist/worker/console/static/assets/classDiagram-v2-OCEON4UE-DZFra1GO.js +0 -1
  82. package/dist/worker/console/static/assets/index-vbTcFnFs.js +0 -449
  83. package/dist/worker/console/static/assets/stateDiagram-v2-UEYNNEHI-Clg3V9t1.js +0 -1
  84. package/dist/worker/console/static/assets/swimlanesDiagram-ULZ7WXOC-DX1dxAAW.js +0 -8
package/CHANGELOG.md CHANGED
@@ -5,10 +5,15 @@
5
5
  ### 新增
6
6
 
7
7
  - 具备 Aimax 凭证的用户可以在对话输入框中使用 `/sdd-bingo` 完成 SDD 数据对齐。
8
+ - `/sdd-bingo` 不指定名称时会自动选择一个 SDD 分析类别;上报成功提示会显示实际使用的类别。
8
9
 
9
10
  ### 改进
10
11
 
12
+ - 修复顶部一级「观测」入口被恢复工作区残留的 DAG 或上次观测对象劫持的问题:现在点击该入口始终回到当前 Workspace 的运行总览,具体 DAG 仍通过「全屏观测」等显式入口打开。
13
+ - 修复节点检查器通俗字段旁的问号只有图标、悬浮时看不到具体说明的问题;问号现在支持鼠标悬浮和键盘聚焦,并显示对应字段含义及原技术字段。
11
14
  - Next 发布测试升级到 Vitest 4.1.11,采用上游 worker RPC 修复,避免所有断言通过后仍因 `onTaskUpdate` 通讯超时阻断发包;同时隔离会改写构建产物的 package-surface 测试,并恢复两条此前被错误嵌套、实际未执行的 Console 更新回归;发布门禁继续严格检查 unhandled errors。
15
+ - 前端计划契约新增确定性锚定校验(恶劣网关冒烟 4 轮 design 拒绝的主因):behavior 验证目标必须至少引用一个 requirement,且在契约声明了 UI 状态或交互时必须引用至少一个已声明的 UI 状态(纯逻辑契约豁免)。校验位于共享 schema refine,plan 节点的自修阶梯当场拿到精确到字段的报错并修复,不再烧一整轮 design-review 才发现映射缺失;`skills/frontend-plan` 决策契约参考同步补充 canonical 示例(behavior target 形态、状态名逐字引用、stylingStrategy 禁止承诺任务源非目标能力)。
16
+ - 修复前端 design 拒绝后自动恢复子 run 无法启动的问题(恶劣网关前端冒烟三轮复现):staging 物化 child state 时现在按 child spec 写入 `frontendShapeState` 冻结拓扑绑定(此前 execute 前的绑定断言以 `frontend topology binding is missing` 在 398ms 内 fail-closed),并把父 run 中已导入边界节点(contract/scout 等 FINISHED 导入节点)的 committed shape facts 一并继承——否则 child 会在首个 shape 门禁以 `frontend-shape-fact-invalid` 整体 SKIPPED;reset 边界由重跑节点重新提交。同时修复 recovery child runId 派生误传参导致碰撞安全后缀失效、可与已归档 run 同名的问题(默认 `buildDagRunId` 现在正确收到 `{ cwd }` options)。
12
17
  - 修复 backend-test N2 把 provider `stopReason=length` 的截断 Markdown 计划误判为 `FINISHED`、继而延迟到 N3 `missing-module-index` 的问题:长度截断现在在 producer 节点归类为 `output-too-large`;正常结束但缺少必需 heading、Module Index 八列表/模块行或使用代码围栏时归类为 `invalid-output`。两类失败均使用有界 artifact-first retry,下一 attempt 只携带控制器生成的限长协议诊断;N3 ownership/path/模块数门禁与业务 pytest 单次执行不放宽。
13
18
  - 可选依赖 `@agent-context/sift` 从 `0.0.1-alpha.6` 精确 pin 升级到 `0.0.1-alpha.7`:新增 `retrieveLines` 行级分片取回与省略点内联 stash 路径/起始行号(模型可直接换算 read 行号),纯文本压缩策略更保守(不同编号/状态的内容不因句式相似而合并);桥接层沿用既有 `createSift`/`siftRequest`/`retrieve` API,行为与回退开关不变,仍不投影 init。
14
19
  - 修复后端实现 DAG Pi 扩展 resolver 无法解析版本 pin spec 的问题:`packageNameFromSpec` 现在剥除尾部 `@<version>`/`@<dist-tag>`(保留 scoped 包名开头的 `@`),与 Console 插件面语义对齐。此前 settings 中的 `npm:pi-lens@3.8.72`(Console 升级插件写入的形式)会被当作包名 `pi-lens@3.8.72`,永远匹配不上别名表,读侧节点(contract/scout/plan/verify)的 `pi-lens` 全部静默降级为 `not-installed`;`pi-extensions.json` 观测产物可鉴别此场景。
@@ -16,7 +21,8 @@
16
21
  - 冒烟再暴露 writeSet 授权缺口:冻结验证命令引用的基建文件(如 `--config` 的 vitest 配置)不在 plan verification targets 内时,writer 被具体 writeSet 拦住无法创建、verify-shell 必然失败。现在 admission 生效边界确定性并入冻结命令引用的文件(机械提取、仍受 allowedPaths/forbiddenPaths 约束),writer 聚焦检查失败后可自行补齐基建文件。
17
22
  - 前端 verification contract v2:plan 不再手写五值 `type`,改为引用生成期冻结命令目录的 `commandId`,`mode(static|behavior)` 与 `commandLabel` 由 runtime 在物化时解析——`type: component + npm run build` 这类非法组合在 Plan 工具边界(`verification-target-unknown-command`)与物化校验(`verification-target-phase-mismatch`,behavior 命令必须绑定测试文件)即被拒绝,不再拖到 writer focused-check 才以 `invalid-output` 失败;展示用的 `scope` 不参与控制流。
18
23
  - 修复 /inspect/* 静态资源(operator-chrome.js/css、观测文档)缺少 Cache-Control 的问题:现在与 Console SPA 一律 `no-store`。此前浏览器启发式缓存会让 Console 更新/重启后继续挂旧版导航模块,表现为顶部导航「回退」到只有操作/观测、缺少对话入口的旧版布局。
19
- - 新建、删除和切换对话的反馈更及时,较长的会话列表也更容易浏览。
24
+ - 新建、删除和切换对话的反馈更及时;会话列表默认展示 5 条,“展开其余会话”和“收起”也更整齐易用。
25
+ - 发送消息后会立即显示在对话流中,完成回合的过程摘要也更清晰,长时间等待连接时不会让输入内容消失。
20
26
  - 文件预览支持页面内交互和独立窗口阅读,大型 HTML 内容也能完整打开。
21
27
  - 模型配置更新后,继续使用旧会话时会自动采用最新认证信息,消息流顺序也更加稳定。
22
28
  - 执行记录默认跟随最新内容,也可以暂停自动滚动并保留当前阅读位置。
@@ -25,7 +31,7 @@
25
31
  <details>
26
32
  <summary>实现细节(开发者参考)</summary>
27
33
 
28
- - Operator Chat 会话列表默认收敛为最近 10 条,支持按工作区展开其余会话;长历史会话改为分页加载,并在加载更早消息后保持原有滚动位置。
34
+ - Operator Chat 会话列表默认收敛为最近 5 条;展开与收起控件采用稳定的整行布局,折叠工作区后恢复默认列表;长历史会话改为分页加载,并在加载更早消息后保持原有滚动位置。
29
35
  - Operator Chat 长会话增量构建活动 turn、复用已完成过程节点,并支持对已完成且无错误的历史 turn 进行 Compact,降低长消息流的渲染开销。
30
36
  - 修复 backend-test Manifest 把模型生成的 Module Stem 展示单元格当成模块身份真源、导致 low-tier 输出(缺 `test_` 前缀或整段 Markdown 链接)在 N3 `module-markdown-path-mismatch` 反复失败的问题:N3 现在先解析唯一合法 Markdown Path 与 `<stem>.md` 相对链接作为 canonical 身份,再校验业务 ownership/split 与路径安全;Stem 单元格只作冗余展示并能确定性重写为 canonical 文件名 stem。strict `backendTest.moduleLayout` 改为先按唯一 required Markdown Path 定位模块,再恢复冻结 Markdown/Pytest path pair,避免错误 stem 提前丢弃整行,同时保留 Plan-only pytest path 修复。Markdown Path 缺失/多候选/越界或与 strict path pair 冲突、以及多行 canonicalize 后同 identity(`duplicate-canonical-module-stem`)继续 fail-closed,不再静默去重。同步加强 N2 prompt(Stem 单元格仅允许纯文件名 stem)。
31
37
  - 修复 Next Release 的 io-heavy 测试不稳定:在保留发布单 worker、完整测试集合和严格 unhandled-error 门禁的同时,将 Vitest 升级到包含上游 RPC settlement 修复的 4.1.11,避免全绿测试因 `onTaskUpdate` timeout 退出 1;会重建共享 `dist/**` 的 package-surface 测试改由单 worker integration 池持有,避免与 controller identity 指纹检查竞态;并把误嵌套在 `dagDoctor` stub 中的 `consoleUpdateAndInit` suite 移回顶层、补齐 `workspaceId` 契约,使两条回归重新进入真实执行。
@@ -43,6 +49,23 @@
43
49
 
44
50
  </details>
45
51
 
52
+ ## [0.41.3] - 2026-09-04
53
+
54
+ ### 改进
55
+
56
+ - 完善了本发布周期内的日常使用体验和运行稳定性。
57
+
58
+ ### 修复
59
+
60
+ - 修复了部分功能在特定环境下无法正常使用的问题。
61
+
62
+ ## [0.41.2] - 2026-09-04
63
+
64
+ ### 修复
65
+
66
+ - 修复了 DAG 扩展解析、会话恢复和观测页面资源缓存等问题,让任务执行和对话页面在更新后更加可靠。
67
+ - 修复了孤儿会话和观测入口偶发失效的问题,重启或刷新后可以继续使用原有会话。
68
+
46
69
  ## [0.41.1] - 2026-09-02
47
70
 
48
71
  ### 修复
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "schemaVersion": 1,
3
- "version": "0.42.0-next.12",
4
- "gitSha": "907aac820949bd92fc9c243014ba0de90efb2b3f",
5
- "builtAt": "2026-09-04T06:03:35.121Z"
3
+ "version": "0.42.0-next.14",
4
+ "gitSha": "b1c1d87c7406517f7973e4572add16edb79d6adb",
5
+ "builtAt": "2026-09-04T15:59:41.906Z"
6
6
  }
@@ -1139,19 +1139,18 @@ export async function handleSteerDeferredTurn(req, res, deps, sessionId, clientR
1139
1139
  }
1140
1140
  }
1141
1141
  async function persistAcceptedSteering(deps, sessionId, turnId, userMessage, clientRequestId) {
1142
+ emitUserMessageEvent(deps, sessionId, turnId, userMessage, clientRequestId, true);
1143
+ await emitDeferredTurnUpdate(deps, sessionId, turnId, undefined, 0);
1144
+ }
1145
+ function emitUserMessageEvent(deps, sessionId, turnId, userMessage, clientRequestId, steering = false) {
1142
1146
  deps.events.append(sessionId, turnId, {
1143
1147
  kind: "user_message",
1144
1148
  data: {
1145
- clientRequestId,
1146
- steering: true,
1147
- message: {
1148
- id: userMessage.id,
1149
- text: userMessage.text,
1150
- at: userMessage.at,
1151
- },
1149
+ ...(clientRequestId ? { clientRequestId } : {}),
1150
+ ...(steering ? { steering: true } : {}),
1151
+ message: { id: userMessage.id, text: userMessage.text, at: userMessage.at },
1152
1152
  },
1153
1153
  });
1154
- await emitDeferredTurnUpdate(deps, sessionId, turnId, undefined, 0);
1155
1154
  }
1156
1155
  /** Lightweight busy-truth endpoint for the client reconcile loop (pi-web
1157
1156
  * get_state equivalent): exposes the active turn + the latest turn's durable
@@ -1695,7 +1694,8 @@ export async function handleChatPrompt(req, res, deps, sessionId) {
1695
1694
  text,
1696
1695
  images,
1697
1696
  signal: ac.signal,
1698
- onUserMessagePersisted: (record) => {
1697
+ onUserMessagePersisted: (record, userMessage) => {
1698
+ emitUserMessageEvent(deps, sessionId, turnId, userMessage);
1699
1699
  const users = record.messages.filter((message) => message.role === "user");
1700
1700
  if (users.length !== 1)
1701
1701
  return;
@@ -2005,9 +2005,12 @@ export async function handleCreateChatTurn(req, res, deps, sessionId, trustedPay
2005
2005
  sessionId,
2006
2006
  turnId: turn.turnId,
2007
2007
  text,
2008
+ clientRequestId,
2008
2009
  images,
2009
2010
  signal: controller.signal,
2010
2011
  onUserMessagePersisted: async (record, userMessage) => {
2012
+ if (!trustedPayload)
2013
+ emitUserMessageEvent(deps, sessionId, turn.turnId, userMessage, clientRequestId);
2011
2014
  await trustedPayload?.onUserMessagePersisted?.(turn.turnId, userMessage);
2012
2015
  const users = record.messages.filter((message) => message.role === "user");
2013
2016
  if (users.length !== 1)
@@ -2850,8 +2853,8 @@ async function handleSddBingo(req, res, deps, sessionId) {
2850
2853
  if (Object.keys(body).some((key) => key !== "skillName")) {
2851
2854
  throw new SddDataAlignmentError("SDD_INVALID_SKILL_NAME", "请求体只允许 skillName 字段", 400);
2852
2855
  }
2853
- await deps.sddDataAlignment.report(sessionId, body.skillName);
2854
- sendJson(res, 200, { ok: true });
2856
+ const result = await deps.sddDataAlignment.report(sessionId, body.skillName);
2857
+ sendJson(res, 200, { ok: true, skillName: result.skillName });
2855
2858
  }
2856
2859
  catch (error) {
2857
2860
  if (error instanceof SddDataAlignmentError) {
@@ -2,6 +2,12 @@ import { randomBytes } from "node:crypto";
2
2
  import { readFile, stat } from "node:fs/promises";
3
3
  import os from "node:os";
4
4
  import path from "node:path";
5
+ export const SDD_SKILL_NAMES = [
6
+ "SDD-design-analysis",
7
+ "SDD-implementation-test-review",
8
+ "SDD-requirement-analysis",
9
+ ];
10
+ /** Backward-compatible name for callers that need a stable representative value. */
5
11
  export const SDD_DEFAULT_SKILL_NAME = "SDD-implementation-test-review";
6
12
  export const SDD_TELEMETRY_URL = "https://wizard-ai.paic.com.cn/code_pilot/api/skill-usage-log";
7
13
  export const SDD_TELEMETRY_SIGN = "52aad0c09e6b46818a11ee702d6fe0ba";
@@ -80,12 +86,16 @@ export class SddDataAlignmentError extends Error {
80
86
  this.name = "SddDataAlignmentError";
81
87
  }
82
88
  }
83
- export function normalizeSddSkillName(value) {
89
+ export function selectRandomSddSkillName(random = Math.random) {
90
+ const index = Math.min(SDD_SKILL_NAMES.length - 1, Math.max(0, Math.floor(random() * SDD_SKILL_NAMES.length)));
91
+ return SDD_SKILL_NAMES[index];
92
+ }
93
+ export function normalizeSddSkillName(value, random = Math.random) {
84
94
  if (value !== undefined && typeof value !== "string") {
85
95
  throw new SddDataAlignmentError("SDD_INVALID_SKILL_NAME", "skillName 必须是字符串", 400);
86
96
  }
87
97
  const raw = value ?? "";
88
- const normalized = raw.trim() || SDD_DEFAULT_SKILL_NAME;
98
+ const normalized = raw.trim() || selectRandomSddSkillName(random);
89
99
  if ([...normalized].length > 256 || /[\u0000-\u001f\u007f]/u.test(raw)) {
90
100
  throw new SddDataAlignmentError("SDD_INVALID_SKILL_NAME", "skillName 不能超过 256 个字符或包含控制字符", 400);
91
101
  }
@@ -149,6 +159,7 @@ export class SddDataAlignmentService {
149
159
  if (!response.ok || body?.ret !== 0 || body.succ !== true) {
150
160
  throw new SddDataAlignmentError("SDD_UPSTREAM_FAILED", "SDD 数据对齐上报失败", 502);
151
161
  }
162
+ return { skillName };
152
163
  }
153
164
  }
154
165
  async function readBoundedTelemetryJson(response) {
@@ -589,7 +589,11 @@ export async function runChatTurn(options) {
589
589
  };
590
590
  }
591
591
  if (options.persistUserMessage !== false) {
592
- const userMessage = await store.appendMessage(sessionId, { role: "user", text });
592
+ const userMessage = await store.appendMessage(sessionId, {
593
+ role: "user",
594
+ text,
595
+ ...(options.clientRequestId ? { clientRequestId: options.clientRequestId } : {}),
596
+ });
593
597
  const afterUserMessage = await store.get(sessionId);
594
598
  if (afterUserMessage)
595
599
  await options.onUserMessagePersisted?.(afterUserMessage, userMessage);
@@ -41,6 +41,7 @@ export function hydrateSessionThread(raw) {
41
41
  role: "user",
42
42
  text: item.text,
43
43
  createdAt,
44
+ ...(item.clientRequestId ? { clientRequestId: item.clientRequestId } : {}),
44
45
  ...(item.eventSeq === undefined ? {} : { eventSeq: item.eventSeq }),
45
46
  ...(item.turnId ? { turnId: item.turnId } : {}),
46
47
  });
@@ -1 +1 @@
1
- import{g as p,r as u,d as a}from"./chunk-6Q2QTUOP-DQtGYoty.js";import{p as f}from"./chunk-JWPE2WC7-DVH9dIGE.js";import{_ as n,l as o}from"./mermaid.core-Bl13LpNa.js";import{M as c,b as d}from"./cynefin-VYW2F7L2-Bf2UVnoG.js";import"./index-vbTcFnFs.js";var v=d().RailroadAbnf.parser.LangiumParser,i=n(e=>{const r=e.alternatives.map(g);return r.length===1?r[0]:{type:"choice",alternatives:r}},"transformAlternation"),g=n(e=>{const r=e.elements.map(y);return r.length===1?r[0]:{type:"sequence",elements:r}},"transformConcatenation"),b=n(e=>{if(e.includes("*")){const[t,s]=e.split("*"),l=t?parseInt(t,10):0,m=s?parseInt(s,10):1/0;return{min:l,max:m}}const r=parseInt(e,10);return{min:r,max:r}},"parseRepeat"),y=n(e=>{const r=A(e.primary);if(!e.repeat)return r;const{min:t,max:s}=b(e.repeat);return t===0&&s===1?{type:"optional",element:r}:{type:"repetition",element:r,min:t,max:s}},"transformElement"),A=n(e=>{switch(e.$type){case"AbnfStringLiteral":return{type:"terminal",value:e.value};case"AbnfNumVal":return{type:"terminal",value:e.value};case"AbnfRuleName":return{type:"nonterminal",name:e.name};case"AbnfGroup":return i(e.element);case"AbnfOptionalGroup":return{type:"optional",element:i(e.element)};default:throw new Error(`Unsupported ABNF primary node: ${e.$type}`)}},"transformPrimary"),P=n(e=>({name:e.name,definition:i(e.definition)}),"transformRule"),h=n(e=>{f(e,a),e.title&&a.setTitle(e.title),e.rules.map(r=>a.addRule(P(r)))},"populateDb"),R={parse:n(e=>{a.clear(),o.debug("[ABNF Parser] Starting Langium parse");const r=v.parse(e);if(r.lexerErrors.length>0||r.parserErrors.length>0)throw new c(r);const t=r.value;o.debug("[ABNF Parser] Parsed rules:",t.rules.length),h(t),o.debug("[ABNF Parser] Parse complete")},"parse"),parser:{yy:a}},B={parser:R,db:a,renderer:u,styles:p};export{B as diagram};
1
+ import{g as p,r as u,d as a}from"./chunk-6Q2QTUOP-FG53fA6v.js";import{p as f}from"./chunk-JWPE2WC7-WxHo0z2I.js";import{_ as n,l as o}from"./mermaid.core-CE4idY-s.js";import{M as c,b as d}from"./cynefin-VYW2F7L2-DQlWfkS7.js";import"./index-CWhTyxvc.js";var v=d().RailroadAbnf.parser.LangiumParser,i=n(e=>{const r=e.alternatives.map(g);return r.length===1?r[0]:{type:"choice",alternatives:r}},"transformAlternation"),g=n(e=>{const r=e.elements.map(y);return r.length===1?r[0]:{type:"sequence",elements:r}},"transformConcatenation"),b=n(e=>{if(e.includes("*")){const[t,s]=e.split("*"),l=t?parseInt(t,10):0,m=s?parseInt(s,10):1/0;return{min:l,max:m}}const r=parseInt(e,10);return{min:r,max:r}},"parseRepeat"),y=n(e=>{const r=A(e.primary);if(!e.repeat)return r;const{min:t,max:s}=b(e.repeat);return t===0&&s===1?{type:"optional",element:r}:{type:"repetition",element:r,min:t,max:s}},"transformElement"),A=n(e=>{switch(e.$type){case"AbnfStringLiteral":return{type:"terminal",value:e.value};case"AbnfNumVal":return{type:"terminal",value:e.value};case"AbnfRuleName":return{type:"nonterminal",name:e.name};case"AbnfGroup":return i(e.element);case"AbnfOptionalGroup":return{type:"optional",element:i(e.element)};default:throw new Error(`Unsupported ABNF primary node: ${e.$type}`)}},"transformPrimary"),P=n(e=>({name:e.name,definition:i(e.definition)}),"transformRule"),h=n(e=>{f(e,a),e.title&&a.setTitle(e.title),e.rules.map(r=>a.addRule(P(r)))},"populateDb"),R={parse:n(e=>{a.clear(),o.debug("[ABNF Parser] Starting Langium parse");const r=v.parse(e);if(r.lexerErrors.length>0||r.parserErrors.length>0)throw new c(r);const t=r.value;o.debug("[ABNF Parser] Parsed rules:",t.rules.length),h(t),o.debug("[ABNF Parser] Parse complete")},"parse"),parser:{yy:a}},B={parser:R,db:a,renderer:u,styles:p};export{B as diagram};
@@ -1 +1 @@
1
- import{Y as ln,$ as an,a0 as F,a1 as q,a2 as j,a3 as un,a4 as y,a5 as tn,a6 as J,a7 as _,a8 as rn,a9 as o,aa as on,ab as sn,ac as fn}from"./mermaid.core-Bl13LpNa.js";function cn(l){return l.innerRadius}function yn(l){return l.outerRadius}function gn(l){return l.startAngle}function dn(l){return l.endAngle}function mn(l){return l&&l.padAngle}function pn(l,h,I,D,v,A,z,a){var O=I-l,i=D-h,n=z-v,d=a-A,u=d*O-n*i;if(!(u*u<y))return u=(n*(h-A)-d*(l-v))/u,[l+u*O,h+u*i]}function U(l,h,I,D,v,A,z){var a=l-I,O=h-D,i=(z?A:-A)/J(a*a+O*O),n=i*O,d=-i*a,u=l+n,s=h+d,f=I+n,c=D+d,B=(u+f)/2,t=(s+c)/2,m=f-u,g=c-s,R=m*m+g*g,T=v-A,P=u*c-f*s,S=(g<0?-1:1)*J(on(0,T*T*R-P*P)),Y=(P*g-m*S)/R,$=(-P*m-g*S)/R,w=(P*g+m*S)/R,p=(-P*m+g*S)/R,x=Y-B,e=$-t,r=w-B,C=p-t;return x*x+e*e>r*r+C*C&&(Y=w,$=p),{cx:Y,cy:$,x01:-n,y01:-d,x11:Y*(v/T-1),y11:$*(v/T-1)}}function hn(){var l=cn,h=yn,I=j(0),D=null,v=gn,A=dn,z=mn,a=null,O=ln(i);function i(){var n,d,u=+l.apply(this,arguments),s=+h.apply(this,arguments),f=v.apply(this,arguments)-un,c=A.apply(this,arguments)-un,B=rn(c-f),t=c>f;if(a||(a=n=O()),s<u&&(d=s,s=u,u=d),!(s>y))a.moveTo(0,0);else if(B>tn-y)a.moveTo(s*F(f),s*q(f)),a.arc(0,0,s,f,c,!t),u>y&&(a.moveTo(u*F(c),u*q(c)),a.arc(0,0,u,c,f,t));else{var m=f,g=c,R=f,T=c,P=B,S=B,Y=z.apply(this,arguments)/2,$=Y>y&&(D?+D.apply(this,arguments):J(u*u+s*s)),w=_(rn(s-u)/2,+I.apply(this,arguments)),p=w,x=w,e,r;if($>y){var C=sn($/u*q(Y)),K=sn($/s*q(Y));(P-=C*2)>y?(C*=t?1:-1,R+=C,T-=C):(P=0,R=T=(f+c)/2),(S-=K*2)>y?(K*=t?1:-1,m+=K,g-=K):(S=0,m=g=(f+c)/2)}var G=s*F(m),H=s*q(m),L=u*F(T),M=u*q(T);if(w>y){var N=s*F(g),Q=s*q(g),V=u*F(R),W=u*q(R),E;if(B<an)if(E=pn(G,H,V,W,N,Q,L,M)){var X=G-E[0],Z=H-E[1],b=N-E[0],k=Q-E[1],nn=1/q(fn((X*b+Z*k)/(J(X*X+Z*Z)*J(b*b+k*k)))/2),en=J(E[0]*E[0]+E[1]*E[1]);p=_(w,(u-en)/(nn-1)),x=_(w,(s-en)/(nn+1))}else p=x=0}S>y?x>y?(e=U(V,W,G,H,s,x,t),r=U(N,Q,L,M,s,x,t),a.moveTo(e.cx+e.x01,e.cy+e.y01),x<w?a.arc(e.cx,e.cy,x,o(e.y01,e.x01),o(r.y01,r.x01),!t):(a.arc(e.cx,e.cy,x,o(e.y01,e.x01),o(e.y11,e.x11),!t),a.arc(0,0,s,o(e.cy+e.y11,e.cx+e.x11),o(r.cy+r.y11,r.cx+r.x11),!t),a.arc(r.cx,r.cy,x,o(r.y11,r.x11),o(r.y01,r.x01),!t))):(a.moveTo(G,H),a.arc(0,0,s,m,g,!t)):a.moveTo(G,H),!(u>y)||!(P>y)?a.lineTo(L,M):p>y?(e=U(L,M,N,Q,u,-p,t),r=U(G,H,V,W,u,-p,t),a.lineTo(e.cx+e.x01,e.cy+e.y01),p<w?a.arc(e.cx,e.cy,p,o(e.y01,e.x01),o(r.y01,r.x01),!t):(a.arc(e.cx,e.cy,p,o(e.y01,e.x01),o(e.y11,e.x11),!t),a.arc(0,0,u,o(e.cy+e.y11,e.cx+e.x11),o(r.cy+r.y11,r.cx+r.x11),t),a.arc(r.cx,r.cy,p,o(r.y11,r.x11),o(r.y01,r.x01),!t))):a.arc(0,0,u,T,R,t)}if(a.closePath(),n)return a=null,n+""||null}return i.centroid=function(){var n=(+l.apply(this,arguments)+ +h.apply(this,arguments))/2,d=(+v.apply(this,arguments)+ +A.apply(this,arguments))/2-an/2;return[F(d)*n,q(d)*n]},i.innerRadius=function(n){return arguments.length?(l=typeof n=="function"?n:j(+n),i):l},i.outerRadius=function(n){return arguments.length?(h=typeof n=="function"?n:j(+n),i):h},i.cornerRadius=function(n){return arguments.length?(I=typeof n=="function"?n:j(+n),i):I},i.padRadius=function(n){return arguments.length?(D=n==null?null:typeof n=="function"?n:j(+n),i):D},i.startAngle=function(n){return arguments.length?(v=typeof n=="function"?n:j(+n),i):v},i.endAngle=function(n){return arguments.length?(A=typeof n=="function"?n:j(+n),i):A},i.padAngle=function(n){return arguments.length?(z=typeof n=="function"?n:j(+n),i):z},i.context=function(n){return arguments.length?(a=n??null,i):a},i}export{hn as d};
1
+ import{Y as ln,$ as an,a0 as F,a1 as q,a2 as j,a3 as un,a4 as y,a5 as tn,a6 as J,a7 as _,a8 as rn,a9 as o,aa as on,ab as sn,ac as fn}from"./mermaid.core-CE4idY-s.js";function cn(l){return l.innerRadius}function yn(l){return l.outerRadius}function gn(l){return l.startAngle}function dn(l){return l.endAngle}function mn(l){return l&&l.padAngle}function pn(l,h,I,D,v,A,z,a){var O=I-l,i=D-h,n=z-v,d=a-A,u=d*O-n*i;if(!(u*u<y))return u=(n*(h-A)-d*(l-v))/u,[l+u*O,h+u*i]}function U(l,h,I,D,v,A,z){var a=l-I,O=h-D,i=(z?A:-A)/J(a*a+O*O),n=i*O,d=-i*a,u=l+n,s=h+d,f=I+n,c=D+d,B=(u+f)/2,t=(s+c)/2,m=f-u,g=c-s,R=m*m+g*g,T=v-A,P=u*c-f*s,S=(g<0?-1:1)*J(on(0,T*T*R-P*P)),Y=(P*g-m*S)/R,$=(-P*m-g*S)/R,w=(P*g+m*S)/R,p=(-P*m+g*S)/R,x=Y-B,e=$-t,r=w-B,C=p-t;return x*x+e*e>r*r+C*C&&(Y=w,$=p),{cx:Y,cy:$,x01:-n,y01:-d,x11:Y*(v/T-1),y11:$*(v/T-1)}}function hn(){var l=cn,h=yn,I=j(0),D=null,v=gn,A=dn,z=mn,a=null,O=ln(i);function i(){var n,d,u=+l.apply(this,arguments),s=+h.apply(this,arguments),f=v.apply(this,arguments)-un,c=A.apply(this,arguments)-un,B=rn(c-f),t=c>f;if(a||(a=n=O()),s<u&&(d=s,s=u,u=d),!(s>y))a.moveTo(0,0);else if(B>tn-y)a.moveTo(s*F(f),s*q(f)),a.arc(0,0,s,f,c,!t),u>y&&(a.moveTo(u*F(c),u*q(c)),a.arc(0,0,u,c,f,t));else{var m=f,g=c,R=f,T=c,P=B,S=B,Y=z.apply(this,arguments)/2,$=Y>y&&(D?+D.apply(this,arguments):J(u*u+s*s)),w=_(rn(s-u)/2,+I.apply(this,arguments)),p=w,x=w,e,r;if($>y){var C=sn($/u*q(Y)),K=sn($/s*q(Y));(P-=C*2)>y?(C*=t?1:-1,R+=C,T-=C):(P=0,R=T=(f+c)/2),(S-=K*2)>y?(K*=t?1:-1,m+=K,g-=K):(S=0,m=g=(f+c)/2)}var G=s*F(m),H=s*q(m),L=u*F(T),M=u*q(T);if(w>y){var N=s*F(g),Q=s*q(g),V=u*F(R),W=u*q(R),E;if(B<an)if(E=pn(G,H,V,W,N,Q,L,M)){var X=G-E[0],Z=H-E[1],b=N-E[0],k=Q-E[1],nn=1/q(fn((X*b+Z*k)/(J(X*X+Z*Z)*J(b*b+k*k)))/2),en=J(E[0]*E[0]+E[1]*E[1]);p=_(w,(u-en)/(nn-1)),x=_(w,(s-en)/(nn+1))}else p=x=0}S>y?x>y?(e=U(V,W,G,H,s,x,t),r=U(N,Q,L,M,s,x,t),a.moveTo(e.cx+e.x01,e.cy+e.y01),x<w?a.arc(e.cx,e.cy,x,o(e.y01,e.x01),o(r.y01,r.x01),!t):(a.arc(e.cx,e.cy,x,o(e.y01,e.x01),o(e.y11,e.x11),!t),a.arc(0,0,s,o(e.cy+e.y11,e.cx+e.x11),o(r.cy+r.y11,r.cx+r.x11),!t),a.arc(r.cx,r.cy,x,o(r.y11,r.x11),o(r.y01,r.x01),!t))):(a.moveTo(G,H),a.arc(0,0,s,m,g,!t)):a.moveTo(G,H),!(u>y)||!(P>y)?a.lineTo(L,M):p>y?(e=U(L,M,N,Q,u,-p,t),r=U(G,H,V,W,u,-p,t),a.lineTo(e.cx+e.x01,e.cy+e.y01),p<w?a.arc(e.cx,e.cy,p,o(e.y01,e.x01),o(r.y01,r.x01),!t):(a.arc(e.cx,e.cy,p,o(e.y01,e.x01),o(e.y11,e.x11),!t),a.arc(0,0,u,o(e.cy+e.y11,e.cx+e.x11),o(r.cy+r.y11,r.cx+r.x11),t),a.arc(r.cx,r.cy,p,o(r.y11,r.x11),o(r.y01,r.x01),!t))):a.arc(0,0,u,T,R,t)}if(a.closePath(),n)return a=null,n+""||null}return i.centroid=function(){var n=(+l.apply(this,arguments)+ +h.apply(this,arguments))/2,d=(+v.apply(this,arguments)+ +A.apply(this,arguments))/2-an/2;return[F(d)*n,q(d)*n]},i.innerRadius=function(n){return arguments.length?(l=typeof n=="function"?n:j(+n),i):l},i.outerRadius=function(n){return arguments.length?(h=typeof n=="function"?n:j(+n),i):h},i.cornerRadius=function(n){return arguments.length?(I=typeof n=="function"?n:j(+n),i):I},i.padRadius=function(n){return arguments.length?(D=n==null?null:typeof n=="function"?n:j(+n),i):D},i.startAngle=function(n){return arguments.length?(v=typeof n=="function"?n:j(+n),i):v},i.endAngle=function(n){return arguments.length?(A=typeof n=="function"?n:j(+n),i):A},i.padAngle=function(n){return arguments.length?(z=typeof n=="function"?n:j(+n),i):z},i.context=function(n){return arguments.length?(a=n??null,i):a},i}export{hn as d};