minimal-agent 0.10.0 → 0.12.0

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 (573) hide show
  1. package/README.md +11 -3
  2. package/package.json +52 -5
  3. package/plugins/computer_use/.claude-plugin/plugin.json +6 -0
  4. package/plugins/computer_use/README.md +94 -0
  5. package/plugins/computer_use/app/_template.md +142 -0
  6. package/plugins/computer_use/app/chrome.md +165 -0
  7. package/plugins/computer_use/app/finder.md +76 -0
  8. package/plugins/computer_use/app/macos-system-settings.md +81 -0
  9. package/plugins/computer_use/app/microsoft-excel.md +80 -0
  10. package/plugins/computer_use/app/microsoft-powerpoint.md +80 -0
  11. package/plugins/computer_use/app/microsoft-word.md +79 -0
  12. package/plugins/computer_use/app/wechat.md +413 -0
  13. package/plugins/computer_use/app/weread.md +319 -0
  14. package/plugins/computer_use/commands/computeruse.md +25 -0
  15. package/plugins/computer_use/commands/cu.md +9 -0
  16. package/plugins/computer_use/plugin.js +26 -0
  17. package/plugins/computer_use/plugin.ts +30 -0
  18. package/plugins/computer_use/src/capture.js +90 -0
  19. package/plugins/computer_use/src/capture.ts +104 -0
  20. package/plugins/computer_use/src/commands.js +91 -0
  21. package/plugins/computer_use/src/commands.ts +103 -0
  22. package/plugins/computer_use/src/daemon.js +134 -0
  23. package/plugins/computer_use/src/daemon.ts +161 -0
  24. package/plugins/computer_use/src/manuals.js +135 -0
  25. package/plugins/computer_use/src/manuals.ts +159 -0
  26. package/plugins/computer_use/src/verify.js +168 -0
  27. package/plugins/computer_use/src/verify.ts +219 -0
  28. package/plugins/computer_use/test/commands.test.ts +73 -0
  29. package/plugins/cron-runner/plugin.ts +38 -0
  30. package/plugins/cron-runner/src/commands.ts +373 -0
  31. package/plugins/cron-runner/src/cronTime.ts +155 -0
  32. package/plugins/cron-runner/src/lock.ts +79 -0
  33. package/plugins/cron-runner/src/runs.ts +99 -0
  34. package/plugins/cron-runner/src/scheduleEngine.ts +76 -0
  35. package/plugins/cron-runner/src/scheduler.ts +376 -0
  36. package/plugins/cron-runner/src/schema.ts +139 -0
  37. package/plugins/cron-runner/src/service.ts +193 -0
  38. package/plugins/cron-runner/src/store.ts +333 -0
  39. package/plugins/cron-runner/src/types.ts +141 -0
  40. package/plugins/cron-runner/test/cronTime.test.ts +41 -0
  41. package/plugins/cron-runner/test/plugin-integration.test.ts +47 -0
  42. package/plugins/cron-runner/test/scheduleEngine.test.ts +41 -0
  43. package/plugins/cron-runner/test/service.test.ts +76 -0
  44. package/plugins/cron-runner/test/store-and-scheduler.test.ts +501 -0
  45. package/plugins/workflow-runner/plugin.js +56 -2
  46. package/plugins/workflow-runner/plugin.ts +113 -0
  47. package/plugins/workflow-runner/src/agentCommon.js +43 -4
  48. package/plugins/workflow-runner/src/agentCommon.ts +435 -0
  49. package/plugins/workflow-runner/src/controlFlow/branch.js +40 -0
  50. package/plugins/workflow-runner/src/controlFlow/branch.ts +46 -0
  51. package/plugins/workflow-runner/src/controlFlow/loop.js +211 -0
  52. package/plugins/workflow-runner/src/controlFlow/loop.ts +248 -0
  53. package/plugins/workflow-runner/src/controlFlow/pause.js +129 -0
  54. package/plugins/workflow-runner/src/controlFlow/pause.ts +141 -0
  55. package/plugins/workflow-runner/src/controlFlow/signal.js +21 -0
  56. package/plugins/workflow-runner/src/controlFlow/signal.ts +29 -0
  57. package/plugins/workflow-runner/src/controlFlow/types.js +18 -0
  58. package/plugins/workflow-runner/src/controlFlow/types.ts +63 -0
  59. package/plugins/workflow-runner/src/dslManifest.ts +127 -0
  60. package/plugins/workflow-runner/src/expressions.ts +622 -0
  61. package/plugins/workflow-runner/src/index.js +13 -4
  62. package/plugins/workflow-runner/src/index.ts +338 -0
  63. package/plugins/workflow-runner/src/jsonPayload.ts +84 -0
  64. package/plugins/workflow-runner/src/loader.js +23 -0
  65. package/plugins/workflow-runner/src/loader.ts +721 -0
  66. package/plugins/workflow-runner/src/multimodal.js +2 -1
  67. package/plugins/workflow-runner/src/multimodal.ts +64 -0
  68. package/plugins/workflow-runner/src/recovery.ts +149 -0
  69. package/plugins/workflow-runner/src/runner.js +75 -659
  70. package/plugins/workflow-runner/src/runner.ts +604 -0
  71. package/plugins/workflow-runner/src/stepExecutors/agent.ts +234 -0
  72. package/plugins/workflow-runner/src/stepExecutors/assert.ts +50 -0
  73. package/plugins/workflow-runner/src/stepExecutors/echo.js +31 -0
  74. package/plugins/workflow-runner/src/stepExecutors/echo.ts +38 -0
  75. package/plugins/workflow-runner/src/stepExecutors/llm.ts +133 -0
  76. package/plugins/workflow-runner/src/stepExecutors/set.js +49 -0
  77. package/plugins/workflow-runner/src/stepExecutors/set.ts +56 -0
  78. package/plugins/workflow-runner/src/stepExecutors/skill.js +5 -6
  79. package/plugins/workflow-runner/src/stepExecutors/skill.ts +140 -0
  80. package/plugins/workflow-runner/src/stepExecutors/tool.js +80 -8
  81. package/plugins/workflow-runner/src/stepExecutors/tool.ts +256 -0
  82. package/plugins/workflow-runner/src/stepExecutors/verify.ts +68 -0
  83. package/plugins/workflow-runner/src/stepPipeline.js +277 -0
  84. package/plugins/workflow-runner/src/stepPipeline.ts +366 -0
  85. package/plugins/workflow-runner/src/taskIdentity.ts +405 -0
  86. package/plugins/workflow-runner/src/toolRuntime.js +48 -0
  87. package/plugins/workflow-runner/src/toolRuntime.ts +64 -0
  88. package/plugins/workflow-runner/src/types.js +37 -1
  89. package/plugins/workflow-runner/src/types.ts +602 -0
  90. package/plugins/workflow-runner/src/workflowState.ts +733 -0
  91. package/plugins/workflow-runner/test/agent.test.ts +587 -0
  92. package/plugins/workflow-runner/test/agentLlmError.test.ts +373 -0
  93. package/plugins/workflow-runner/test/bashBlacklist.sweep.test.ts +65 -0
  94. package/plugins/workflow-runner/test/captureMisbind.test.ts +99 -0
  95. package/plugins/workflow-runner/test/cli.e2e.test.ts +147 -0
  96. package/plugins/workflow-runner/test/context-files.test.ts +320 -0
  97. package/plugins/workflow-runner/test/e2e.test.ts +370 -0
  98. package/plugins/workflow-runner/test/engineRobustness.test.ts +226 -0
  99. package/plugins/workflow-runner/test/expressions.test.ts +397 -0
  100. package/plugins/workflow-runner/test/foundation.test.ts +126 -0
  101. package/plugins/workflow-runner/test/graceful.test.ts +139 -0
  102. package/plugins/workflow-runner/test/greedyInputs.load.test.ts +47 -0
  103. package/plugins/workflow-runner/test/hostCapability.test.ts +108 -0
  104. package/plugins/workflow-runner/test/illustrate.load.test.ts +183 -0
  105. package/plugins/workflow-runner/test/jsonPayload.test.ts +83 -0
  106. package/plugins/workflow-runner/test/loader.test.ts +617 -0
  107. package/plugins/workflow-runner/test/maxTurnsRetryDelay.test.ts +33 -0
  108. package/plugins/workflow-runner/test/multimodal.test.ts +342 -0
  109. package/plugins/workflow-runner/test/output-schema.test.ts +213 -0
  110. package/plugins/workflow-runner/test/parseWorkflowArgs.test.ts +87 -0
  111. package/plugins/workflow-runner/test/pluginRunner.isolation.test.ts +269 -0
  112. package/plugins/workflow-runner/test/ppt.load.test.ts +1220 -0
  113. package/plugins/workflow-runner/test/ralphLoop.e2e.test.ts +220 -0
  114. package/plugins/workflow-runner/test/recovery.test.ts +265 -0
  115. package/plugins/workflow-runner/test/runner.test.ts +911 -0
  116. package/plugins/workflow-runner/test/runnerPreflight.test.ts +379 -0
  117. package/plugins/workflow-runner/test/skillTurnDone.test.ts +71 -0
  118. package/plugins/workflow-runner/test/stateLifecycle.test.ts +150 -0
  119. package/plugins/workflow-runner/test/stepPipeline.test.ts +114 -0
  120. package/plugins/workflow-runner/test/taskArbitration.test.ts +338 -0
  121. package/plugins/workflow-runner/test/taskIdentity.test.ts +237 -0
  122. package/plugins/workflow-runner/test/taskLifecycle.test.ts +270 -0
  123. package/plugins/workflow-runner/test/toolArtifactOverwrite.test.ts +221 -0
  124. package/plugins/workflow-runner/test/toolCapabilityBoundary.test.ts +29 -0
  125. package/plugins/workflow-runner/test/toolRuntimeIntegration.test.ts +168 -0
  126. package/plugins/workflow-runner/test/webppt.load.test.ts +250 -0
  127. package/plugins/workflow-runner/test/word.load.test.ts +208 -0
  128. package/plugins/workflow-runner/test/workflows.smoke.test.ts +76 -0
  129. package/plugins/workflow-runner/test/yamlGuardConditions.test.ts +207 -0
  130. package/skills/browser-automation/SKILL.md +9 -19
  131. package/skills/web-crawler/SKILL.md +9 -11
  132. package/src/askBridge.ts +249 -0
  133. package/src/bootstrap/cwdArg.js +10 -3
  134. package/src/bootstrap/cwdArg.ts +31 -0
  135. package/src/bootstrap/workingDir.ts +48 -0
  136. package/src/cli/args.js +70 -7
  137. package/src/cli/args.ts +146 -0
  138. package/src/cli/computerUse.js +185 -0
  139. package/src/cli/computerUse.ts +221 -0
  140. package/src/cli/configMenu.js +274 -202
  141. package/src/cli/configMenu.tsx +521 -0
  142. package/src/cli/memoryAccess.js +45 -0
  143. package/src/cli/memoryAccess.ts +53 -0
  144. package/src/cli/print.js +119 -5
  145. package/src/cli/print.ts +597 -0
  146. package/src/cli/quickModelSetup.js +60 -0
  147. package/src/cli/quickModelSetup.tsx +96 -0
  148. package/src/cli/streamJson.js +80 -4
  149. package/src/cli/streamJson.ts +433 -0
  150. package/src/cli/wizards/advisorWizard.js +1 -0
  151. package/src/cli/wizards/advisorWizard.tsx +195 -0
  152. package/src/cli/wizards/agentRuntimeWizard.js +84 -0
  153. package/src/cli/wizards/agentRuntimeWizard.tsx +134 -0
  154. package/src/cli/wizards/browserWizard.js +55 -0
  155. package/src/cli/wizards/browserWizard.tsx +77 -0
  156. package/src/cli/wizards/contextAdvisorWizard.js +84 -0
  157. package/src/cli/wizards/contextAdvisorWizard.tsx +124 -0
  158. package/src/cli/wizards/fieldForm.js +7 -4
  159. package/src/cli/wizards/fieldForm.tsx +250 -0
  160. package/src/cli/wizards/imageWizard.js +4 -5
  161. package/src/cli/wizards/imageWizard.tsx +96 -0
  162. package/src/cli/wizards/openRouterWizard.tsx +48 -0
  163. package/src/cli/wizards/providerPresets.js +1 -8
  164. package/src/cli/wizards/providerPresets.ts +106 -0
  165. package/src/cli/wizards/providerWizard.js +152 -205
  166. package/src/cli/wizards/providerWizard.tsx +266 -0
  167. package/src/cli/wizards/searchWizard.tsx +47 -0
  168. package/src/cli/wizards/ttsWizard.js +4 -3
  169. package/src/cli/wizards/ttsWizard.tsx +61 -0
  170. package/src/config/configDefaults.js +25 -0
  171. package/src/config/configDefaults.ts +33 -0
  172. package/src/config/configDiagnostics.js +117 -0
  173. package/src/config/configDiagnostics.ts +166 -0
  174. package/src/config/configFile.js +52 -32
  175. package/src/config/configFile.ts +633 -0
  176. package/src/config/configManagement.js +126 -0
  177. package/src/config/configManagement.ts +159 -0
  178. package/src/config/configService.js +66 -11
  179. package/src/config/configService.ts +554 -0
  180. package/src/config/numericLimits.js +61 -0
  181. package/src/config/numericLimits.ts +80 -0
  182. package/src/config.ts +109 -0
  183. package/src/context/agentHome.ts +11 -0
  184. package/src/context/archive.ts +144 -0
  185. package/src/context/budgetPlan.js +54 -0
  186. package/src/context/budgetPlan.ts +88 -0
  187. package/src/context/compact.js +179 -106
  188. package/src/context/compact.ts +584 -0
  189. package/src/context/contextBundle.js +119 -0
  190. package/src/context/contextBundle.ts +176 -0
  191. package/src/context/contextLock.ts +84 -0
  192. package/src/context/microCompactLite.ts +218 -0
  193. package/src/context/persistContext.ts +177 -0
  194. package/src/context/reactiveCompact.js +19 -4
  195. package/src/context/reactiveCompact.ts +240 -0
  196. package/src/context/recentDirs.ts +42 -0
  197. package/src/context/sessionPath.ts +206 -0
  198. package/src/context/sessionRegistry.js +8 -2
  199. package/src/context/sessionRegistry.ts +414 -0
  200. package/src/context/snipCompact.ts +163 -0
  201. package/src/context/tokenCounter.ts +106 -0
  202. package/src/context/workspaceIndex.js +2 -2
  203. package/src/context/workspaceIndex.ts +751 -0
  204. package/src/entry.compiled.tsx +20 -0
  205. package/src/harness/claimValidation.js +9 -0
  206. package/src/harness/claimValidation.ts +22 -0
  207. package/src/harness/evidenceLedger.js +92 -0
  208. package/src/harness/evidenceLedger.ts +96 -0
  209. package/src/harness/stallGuard.js +60 -0
  210. package/src/harness/stallGuard.ts +81 -0
  211. package/src/humanIntervention.js +129 -0
  212. package/src/humanIntervention.ts +216 -0
  213. package/src/infra/verification.ts +295 -0
  214. package/src/irreversible/rules.js +216 -0
  215. package/src/irreversible/rules.ts +261 -0
  216. package/src/llm/client.js +40 -3
  217. package/src/llm/client.ts +621 -0
  218. package/src/llm/promptCache.js +27 -0
  219. package/src/llm/promptCache.ts +41 -0
  220. package/src/llm/providers/anthropicFormat.js +41 -5
  221. package/src/llm/providers/anthropicFormat.ts +290 -0
  222. package/src/llm/providers/openaiFormat.js +186 -8
  223. package/src/llm/providers/openaiFormat.ts +428 -0
  224. package/src/loop.js +614 -63
  225. package/src/loop.ts +1454 -0
  226. package/src/main.js +67 -10
  227. package/src/main.tsx +344 -0
  228. package/src/memory/codec.js +204 -0
  229. package/src/memory/codec.ts +249 -0
  230. package/src/memory/constants.js +34 -0
  231. package/src/memory/constants.ts +50 -0
  232. package/src/memory/episodicMemory.js +684 -0
  233. package/src/memory/episodicMemory.ts +815 -0
  234. package/src/memory/fileStore.js +148 -0
  235. package/src/memory/fileStore.ts +184 -0
  236. package/src/memory/memoryService.js +570 -0
  237. package/src/memory/memoryService.ts +859 -0
  238. package/src/memory/migration.js +128 -0
  239. package/src/memory/migration.ts +160 -0
  240. package/src/memory/repository.js +789 -0
  241. package/src/memory/repository.ts +893 -0
  242. package/src/memory/retrieval.js +108 -0
  243. package/src/memory/retrieval.ts +145 -0
  244. package/src/memory/searchIndex.js +107 -0
  245. package/src/memory/searchIndex.ts +153 -0
  246. package/src/memory/topicView.js +82 -0
  247. package/src/memory/topicView.ts +95 -0
  248. package/src/memory/turnJournal.js +95 -0
  249. package/src/memory/turnJournal.ts +120 -0
  250. package/src/memory/types.js +2 -0
  251. package/src/memory/types.ts +186 -0
  252. package/src/messageQueue.ts +123 -0
  253. package/src/multimodal.js +128 -46
  254. package/src/multimodal.ts +349 -0
  255. package/src/plugin-sdk.js +21 -1
  256. package/src/plugin-sdk.ts +134 -0
  257. package/src/plugins/builtinPluginIds.js +47 -0
  258. package/src/plugins/builtinPluginIds.ts +51 -0
  259. package/src/plugins/builtinRegistry.ts +43 -0
  260. package/src/plugins/commandRouter.js +40 -26
  261. package/src/plugins/commandRouter.ts +261 -0
  262. package/src/plugins/hookEngine.ts +341 -0
  263. package/src/plugins/pluginApi.ts +133 -0
  264. package/src/plugins/pluginLifecycle.ts +34 -0
  265. package/src/plugins/pluginLoader.ts +147 -0
  266. package/src/plugins/pluginManifest.js +127 -0
  267. package/src/plugins/pluginManifest.ts +152 -0
  268. package/src/plugins/pluginRunner.js +47 -2
  269. package/src/plugins/pluginRunner.ts +207 -0
  270. package/src/plugins/transcript.ts +208 -0
  271. package/src/prompts/lint.js +169 -0
  272. package/src/prompts/lint.ts +220 -0
  273. package/src/prompts/pluginList.js +32 -16
  274. package/src/prompts/pluginList.ts +86 -0
  275. package/src/prompts/policyRegistry.js +318 -0
  276. package/src/prompts/policyRegistry.ts +358 -0
  277. package/src/prompts/projectInstructions.js +24 -0
  278. package/src/prompts/projectInstructions.ts +81 -0
  279. package/src/prompts/promptAssembly.js +311 -202
  280. package/src/prompts/promptAssembly.ts +510 -0
  281. package/src/prompts/skillList.js +106 -45
  282. package/src/prompts/skillList.ts +198 -0
  283. package/src/prompts/system.js +31 -6
  284. package/src/prompts/system.ts +81 -0
  285. package/src/runtime/agentRuntimeContext.js +53 -0
  286. package/src/runtime/agentRuntimeContext.ts +112 -0
  287. package/src/session/runAgentTurn.js +71 -12
  288. package/src/session/runAgentTurn.ts +181 -0
  289. package/src/session/runTurn.js +29 -0
  290. package/src/session/runTurn.ts +160 -0
  291. package/src/session/runtimeStore.js +149 -0
  292. package/src/session/runtimeStore.ts +197 -0
  293. package/src/session/sessionState.js +79 -3
  294. package/src/session/sessionState.ts +134 -0
  295. package/src/toolGate.ts +50 -0
  296. package/src/tools/advisor/advisor.js +76 -15
  297. package/src/tools/advisor/advisor.ts +512 -0
  298. package/src/tools/agent/agent.js +245 -29
  299. package/src/tools/agent/agent.ts +837 -0
  300. package/src/tools/agent/agentTaskService.js +60 -0
  301. package/src/tools/agent/agentTaskService.ts +113 -0
  302. package/src/tools/agent/agentTypes.js +20 -8
  303. package/src/tools/agent/agentTypes.ts +94 -0
  304. package/src/tools/agent/coordinator.ts +111 -0
  305. package/src/tools/agent/worktree.ts +296 -0
  306. package/src/tools/ask/ask.js +17 -0
  307. package/src/tools/ask/ask.ts +122 -0
  308. package/src/tools/bash/attachImage.js +223 -0
  309. package/src/tools/bash/attachImage.ts +281 -0
  310. package/src/tools/bash/bash.js +132 -14
  311. package/src/tools/bash/bash.ts +642 -0
  312. package/src/tools/bash/semantics.ts +103 -0
  313. package/src/tools/bash/warnings.js +17 -11
  314. package/src/tools/bash/warnings.ts +117 -0
  315. package/src/tools/capabilities.js +42 -0
  316. package/src/tools/capabilities.ts +69 -0
  317. package/src/tools/computeruse/accessibilityPermission.js +261 -0
  318. package/src/tools/computeruse/accessibilityPermission.ts +294 -0
  319. package/src/tools/computeruse/axSearch.js +96 -0
  320. package/src/tools/computeruse/axSearch.ts +120 -0
  321. package/src/tools/computeruse/axSnap.js +272 -0
  322. package/src/tools/computeruse/axSnap.ts +349 -0
  323. package/src/tools/computeruse/capabilityLabels.js +95 -0
  324. package/src/tools/computeruse/capabilityLabels.ts +115 -0
  325. package/src/tools/computeruse/computerUseService.js +2235 -0
  326. package/src/tools/computeruse/computerUseService.ts +2686 -0
  327. package/src/tools/computeruse/computeruse.js +2742 -0
  328. package/src/tools/computeruse/computeruse.ts +3265 -0
  329. package/src/tools/computeruse/diagnosticTrace.js +154 -0
  330. package/src/tools/computeruse/diagnosticTrace.ts +195 -0
  331. package/src/tools/computeruse/diagnostics.js +369 -0
  332. package/src/tools/computeruse/diagnostics.ts +453 -0
  333. package/src/tools/computeruse/grants.js +53 -0
  334. package/src/tools/computeruse/grants.ts +70 -0
  335. package/src/tools/computeruse/humanBoundary.js +159 -0
  336. package/src/tools/computeruse/humanBoundary.ts +199 -0
  337. package/src/tools/computeruse/intervention.js +77 -0
  338. package/src/tools/computeruse/intervention.ts +110 -0
  339. package/src/tools/computeruse/manualSchema.js +709 -0
  340. package/src/tools/computeruse/manualSchema.ts +916 -0
  341. package/src/tools/computeruse/observationImages.js +705 -0
  342. package/src/tools/computeruse/observationImages.ts +889 -0
  343. package/src/tools/computeruse/protocol.js +60 -0
  344. package/src/tools/computeruse/protocol.ts +515 -0
  345. package/src/tools/computeruse/telemetryLog.js +57 -0
  346. package/src/tools/computeruse/telemetryLog.ts +67 -0
  347. package/src/tools/computeruse/vision/appGuide.js +325 -0
  348. package/src/tools/computeruse/vision/appGuide.ts +482 -0
  349. package/src/tools/computeruse/vision/focus.js +291 -0
  350. package/src/tools/computeruse/vision/focus.ts +382 -0
  351. package/src/tools/computeruse/vision/frames.js +248 -0
  352. package/src/tools/computeruse/vision/frames.ts +329 -0
  353. package/src/tools/computeruse/vision/geometry.js +131 -0
  354. package/src/tools/computeruse/vision/geometry.ts +163 -0
  355. package/src/tools/computeruse/vision/imaging.js +201 -0
  356. package/src/tools/computeruse/vision/imaging.ts +281 -0
  357. package/src/tools/computeruse/vision/png.js +274 -0
  358. package/src/tools/computeruse/vision/png.ts +317 -0
  359. package/src/tools/computeruse/vision/raster.js +320 -0
  360. package/src/tools/computeruse/vision/raster.ts +408 -0
  361. package/src/tools/computeruse/vision/settle.js +131 -0
  362. package/src/tools/computeruse/vision/settle.ts +220 -0
  363. package/src/tools/computeruse/vision/telemetry.js +196 -0
  364. package/src/tools/computeruse/vision/telemetry.ts +241 -0
  365. package/src/tools/computeruse/visionOcr.js +115 -0
  366. package/src/tools/computeruse/visionOcr.ts +128 -0
  367. package/src/tools/computeruse/waitFor.js +237 -0
  368. package/src/tools/computeruse/waitFor.ts +291 -0
  369. package/src/tools/download/download.js +10 -6
  370. package/src/tools/download/download.ts +187 -0
  371. package/src/tools/edit/edit.js +30 -18
  372. package/src/tools/edit/edit.ts +349 -0
  373. package/src/tools/edit/multi-edit.js +25 -14
  374. package/src/tools/edit/multi-edit.ts +223 -0
  375. package/src/tools/effectiveToolSet.js +73 -0
  376. package/src/tools/effectiveToolSet.ts +91 -0
  377. package/src/tools/genimage/genimage.ts +257 -0
  378. package/src/tools/genspeech/genspeech.ts +83 -0
  379. package/src/tools/glob/glob.js +176 -29
  380. package/src/tools/glob/glob.ts +283 -0
  381. package/src/tools/grep/grep.js +61 -19
  382. package/src/tools/grep/grep.ts +239 -0
  383. package/src/tools/grep/rgPath.ts +206 -0
  384. package/src/tools/index.js +99 -5
  385. package/src/tools/index.ts +293 -0
  386. package/src/tools/lsp/config.js +113 -0
  387. package/src/tools/lsp/config.ts +113 -0
  388. package/src/tools/lsp/lsp.js +256 -0
  389. package/src/tools/lsp/lsp.ts +274 -0
  390. package/src/tools/lsp/service.js +303 -0
  391. package/src/tools/lsp/service.ts +296 -0
  392. package/src/tools/memory/memory.js +520 -0
  393. package/src/tools/memory/memory.ts +625 -0
  394. package/src/tools/memory/policy.js +53 -0
  395. package/src/tools/memory/policy.ts +72 -0
  396. package/src/tools/notebook/notebookEdit.js +114 -0
  397. package/src/tools/notebook/notebookEdit.ts +126 -0
  398. package/src/tools/powershell/powershell.js +210 -0
  399. package/src/tools/powershell/powershell.ts +239 -0
  400. package/src/tools/presentresult/presentresult.js +145 -0
  401. package/src/tools/presentresult/presentresult.ts +156 -0
  402. package/src/tools/read/read.js +371 -163
  403. package/src/tools/read/read.ts +558 -0
  404. package/src/tools/shared/diffSummary.js +44 -0
  405. package/src/tools/shared/diffSummary.ts +63 -0
  406. package/src/tools/shared/fileActivity.js +51 -0
  407. package/src/tools/shared/fileActivity.ts +66 -0
  408. package/src/tools/shared/fileMutationBus.js +13 -0
  409. package/src/tools/shared/fileMutationBus.ts +14 -0
  410. package/src/tools/shared/fileState.js +73 -65
  411. package/src/tools/shared/fileState.ts +145 -0
  412. package/src/tools/shared/fileUtils.js +81 -4
  413. package/src/tools/shared/fileUtils.ts +504 -0
  414. package/src/tools/shared/killTree.ts +50 -0
  415. package/src/tools/shared/permanentDeleteGuard.js +26 -0
  416. package/src/tools/shared/permanentDeleteGuard.ts +34 -0
  417. package/src/tools/shared/schemas.ts +20 -0
  418. package/src/tools/shared/toolOutputStore.js +97 -0
  419. package/src/tools/shared/toolOutputStore.ts +110 -0
  420. package/src/tools/skill/skill.js +86 -0
  421. package/src/tools/skill/skill.ts +94 -0
  422. package/src/tools/snip/snip.js +67 -0
  423. package/src/tools/snip/snip.ts +80 -0
  424. package/src/tools/tasks/backgroundTaskService.js +275 -0
  425. package/src/tools/tasks/backgroundTaskService.ts +369 -0
  426. package/src/tools/tasks/processEvidence.js +24 -0
  427. package/src/tools/tasks/processEvidence.ts +34 -0
  428. package/src/tools/tasks/taskManagement.js +163 -0
  429. package/src/tools/tasks/taskManagement.ts +180 -0
  430. package/src/tools/tasks/taskOutput.js +113 -0
  431. package/src/tools/tasks/taskOutput.ts +145 -0
  432. package/src/tools/tasks/taskStop.js +74 -0
  433. package/src/tools/tasks/taskStop.ts +99 -0
  434. package/src/tools/tasks/taskStore.js +46 -0
  435. package/src/tools/tasks/taskStore.ts +77 -0
  436. package/src/tools/terminal/terminalCapture.js +167 -0
  437. package/src/tools/terminal/terminalCapture.ts +179 -0
  438. package/src/tools/trash/trash.js +233 -0
  439. package/src/tools/trash/trash.ts +283 -0
  440. package/src/tools/types.js +1 -1
  441. package/src/tools/types.ts +24 -0
  442. package/src/tools/webbrowser/agentBrowserPath.ts +286 -0
  443. package/src/tools/webbrowser/browser.js +214 -11
  444. package/src/tools/webbrowser/browser.ts +293 -0
  445. package/src/tools/webbrowser/browserControl.js +153 -48
  446. package/src/tools/webbrowser/browserControl.ts +262 -0
  447. package/src/tools/webbrowser/browserDaemon.js +147 -39
  448. package/src/tools/webbrowser/browserDaemon.ts +270 -0
  449. package/src/tools/webbrowser/browserOutcome.js +273 -0
  450. package/src/tools/webbrowser/browserOutcome.ts +306 -0
  451. package/src/tools/webbrowser/browserRunRegistry.js +150 -0
  452. package/src/tools/webbrowser/browserRunRegistry.ts +179 -0
  453. package/src/tools/webbrowser/browserService.js +20 -6
  454. package/src/tools/webbrowser/browserService.ts +56 -0
  455. package/src/tools/webbrowser/browserStream.js +30 -1
  456. package/src/tools/webbrowser/browserStream.ts +216 -0
  457. package/src/tools/webbrowser/browserTabs.js +143 -0
  458. package/src/tools/webbrowser/browserTabs.ts +210 -0
  459. package/src/tools/webbrowser/webbrowser.js +831 -150
  460. package/src/tools/webbrowser/webbrowser.ts +1537 -0
  461. package/src/tools/webfetch/preapproved.ts +274 -0
  462. package/src/tools/webfetch/webfetch.js +24 -23
  463. package/src/tools/webfetch/webfetch.ts +383 -0
  464. package/src/tools/websearch/websearch.js +12 -11
  465. package/src/tools/websearch/websearch.ts +292 -0
  466. package/src/tools/worktree/sessionWorktree.js +128 -0
  467. package/src/tools/worktree/sessionWorktree.ts +158 -0
  468. package/src/tools/write/write.js +27 -44
  469. package/src/tools/write/write.ts +136 -0
  470. package/src/types.ts +960 -0
  471. package/src/ui/App.js +216 -12
  472. package/src/ui/App.tsx +879 -0
  473. package/src/ui/AskQuestion.tsx +300 -0
  474. package/src/ui/InputBox.js +77 -1
  475. package/src/ui/InputBox.tsx +567 -0
  476. package/src/ui/LiveArea.tsx +344 -0
  477. package/src/ui/MessageList.js +27 -6
  478. package/src/ui/MessageList.tsx +559 -0
  479. package/src/ui/ModelPicker.tsx +107 -0
  480. package/src/ui/QueuedMessagesBanner.tsx +51 -0
  481. package/src/ui/Root.js +6 -8
  482. package/src/ui/Root.tsx +100 -0
  483. package/src/ui/SessionPicker.tsx +169 -0
  484. package/src/ui/StatusLine.js +22 -1
  485. package/src/ui/StatusLine.tsx +145 -0
  486. package/src/ui/WorkspacePicker.tsx +84 -0
  487. package/src/ui/advisorCommand.js +54 -0
  488. package/src/ui/advisorCommand.ts +63 -0
  489. package/src/ui/computerCommand.js +19 -0
  490. package/src/ui/computerCommand.ts +35 -0
  491. package/src/ui/figures.ts +45 -0
  492. package/src/ui/hooks/askSlot.ts +112 -0
  493. package/src/ui/hooks/useChat.js +271 -7
  494. package/src/ui/hooks/useChat.ts +1578 -0
  495. package/src/ui/hooks/useInputHistory.ts +235 -0
  496. package/src/ui/hooks/usePasteHandler.ts +220 -0
  497. package/src/ui/hooks/useTerminalSize.ts +41 -0
  498. package/src/ui/hooks/useTextBuffer.ts +108 -0
  499. package/src/ui/hooks/useTokenUsage.ts +44 -0
  500. package/src/ui/liveViewport.ts +189 -0
  501. package/src/ui/markdown.ts +230 -0
  502. package/src/ui/textBuffer.ts +239 -0
  503. package/src/ui/theme.ts +35 -0
  504. package/src/utils/clipboardImage.js +358 -0
  505. package/src/utils/clipboardImage.ts +420 -0
  506. package/src/utils/debugLog.ts +50 -0
  507. package/src/utils/greenRoot.ts +35 -0
  508. package/src/utils/packageRoot.ts +40 -0
  509. package/src/utils/pathContains.js +28 -0
  510. package/src/utils/pathContains.ts +31 -0
  511. package/src/utils/resourcePaths.ts +71 -0
  512. package/src/utils/stripThink.ts +49 -0
  513. package/src/utils/zodToJson.ts +73 -0
  514. package/src/web/browserBridge.js +365 -66
  515. package/src/web/browserBridge.ts +672 -0
  516. package/src/web/protocol.ts +1804 -0
  517. package/vendor/computer-use/arm64-darwin/cu-helperd +0 -0
  518. package/workflows/ppt.yaml +13 -2
  519. package/workflows/wechat-reading-shots.yaml +315 -0
  520. package/workflows/word.yaml +11 -1
  521. package/skills/docx/scripts/office/helpers/__pycache__/__init__.cpython-314.pyc +0 -0
  522. package/skills/docx/scripts/office/helpers/__pycache__/merge_runs.cpython-314.pyc +0 -0
  523. package/skills/docx/scripts/office/helpers/__pycache__/simplify_redlines.cpython-314.pyc +0 -0
  524. package/skills/docx/scripts/office/validators/__pycache__/__init__.cpython-314.pyc +0 -0
  525. package/skills/docx/scripts/office/validators/__pycache__/base.cpython-314.pyc +0 -0
  526. package/skills/docx/scripts/office/validators/__pycache__/docx.cpython-314.pyc +0 -0
  527. package/skills/docx/scripts/office/validators/__pycache__/pptx.cpython-314.pyc +0 -0
  528. package/skills/docx/scripts/office/validators/__pycache__/redlining.cpython-314.pyc +0 -0
  529. package/skills/image-stats/scripts/__pycache__/image_stats.cpython-314.pyc +0 -0
  530. package/skills/image-stats/scripts/__pycache__/image_stats_test.cpython-314.pyc +0 -0
  531. package/skills/ui-design/scripts/__pycache__/assemble_material.cpython-314.pyc +0 -0
  532. package/skills/ui-design/scripts/__pycache__/assemble_material_test.cpython-314.pyc +0 -0
  533. package/skills/ui-design/scripts/__pycache__/chart_sanity_check.cpython-314.pyc +0 -0
  534. package/skills/ui-design/scripts/__pycache__/check_language_policy.cpython-314.pyc +0 -0
  535. package/skills/ui-design/scripts/__pycache__/check_ui_artifact.cpython-314.pyc +0 -0
  536. package/skills/ui-design/scripts/__pycache__/check_ui_artifact_pptx_test.cpython-314.pyc +0 -0
  537. package/skills/ui-design/scripts/__pycache__/deck_pages_check.cpython-314.pyc +0 -0
  538. package/skills/ui-design/scripts/__pycache__/deck_pages_check_test.cpython-314.pyc +0 -0
  539. package/skills/ui-design/scripts/__pycache__/deck_visual_style_check.cpython-314.pyc +0 -0
  540. package/skills/ui-design/scripts/__pycache__/deck_visual_style_check_test.cpython-314.pyc +0 -0
  541. package/skills/ui-design/scripts/__pycache__/design_budget_check.cpython-314.pyc +0 -0
  542. package/skills/ui-design/scripts/__pycache__/design_budget_check_test.cpython-314.pyc +0 -0
  543. package/skills/ui-design/scripts/__pycache__/design_repair_hints.cpython-314.pyc +0 -0
  544. package/skills/ui-design/scripts/__pycache__/design_repair_hints_test.cpython-314.pyc +0 -0
  545. package/skills/ui-design/scripts/__pycache__/design_style_check.cpython-314.pyc +0 -0
  546. package/skills/ui-design/scripts/__pycache__/design_style_check_test.cpython-314.pyc +0 -0
  547. package/skills/ui-design/scripts/__pycache__/draft_coverage_check.cpython-314.pyc +0 -0
  548. package/skills/ui-design/scripts/__pycache__/extract_source_assets.cpython-314.pyc +0 -0
  549. package/skills/ui-design/scripts/__pycache__/extract_source_assets_test.cpython-314.pyc +0 -0
  550. package/skills/ui-design/scripts/__pycache__/generated_image_review_collect.cpython-314.pyc +0 -0
  551. package/skills/ui-design/scripts/__pycache__/generated_image_review_collect_test.cpython-314.pyc +0 -0
  552. package/skills/ui-design/scripts/__pycache__/image_plan_lint.cpython-314.pyc +0 -0
  553. package/skills/ui-design/scripts/__pycache__/image_plan_lint_test.cpython-314.pyc +0 -0
  554. package/skills/ui-design/scripts/__pycache__/image_prompt_rewrite.cpython-314.pyc +0 -0
  555. package/skills/ui-design/scripts/__pycache__/image_prompt_rewrite_test.cpython-314.pyc +0 -0
  556. package/skills/ui-design/scripts/__pycache__/layout_balance.cpython-314.pyc +0 -0
  557. package/skills/ui-design/scripts/__pycache__/layout_balance_test.cpython-314.pyc +0 -0
  558. package/skills/ui-design/scripts/__pycache__/normalize_design_json.cpython-314.pyc +0 -0
  559. package/skills/ui-design/scripts/__pycache__/normalize_design_json_test.cpython-314.pyc +0 -0
  560. package/skills/ui-design/scripts/__pycache__/plan_source_layout.cpython-314.pyc +0 -0
  561. package/skills/ui-design/scripts/__pycache__/plan_source_layout_test.cpython-314.pyc +0 -0
  562. package/skills/ui-design/scripts/__pycache__/resolve_source_hint.cpython-314.pyc +0 -0
  563. package/skills/ui-design/scripts/__pycache__/resolve_source_hint_test.cpython-314.pyc +0 -0
  564. package/skills/ui-design/scripts/__pycache__/resolve_source_input.cpython-314.pyc +0 -0
  565. package/skills/ui-design/scripts/__pycache__/resolve_source_input_test.cpython-314.pyc +0 -0
  566. package/skills/ui-design/scripts/__pycache__/scaffold_ui_artifact.cpython-314.pyc +0 -0
  567. package/skills/ui-design/scripts/__pycache__/source_usage_check.cpython-314.pyc +0 -0
  568. package/skills/ui-design/scripts/__pycache__/source_usage_check_test.cpython-314.pyc +0 -0
  569. package/skills/ui-design/scripts/__pycache__/text_readability_pixel.cpython-314.pyc +0 -0
  570. package/skills/ui-design/scripts/__pycache__/visual_quality_gate.cpython-314.pyc +0 -0
  571. package/skills/ui-design/scripts/__pycache__/visual_quality_gate_test.cpython-314.pyc +0 -0
  572. /package/skills/ai-image/scripts/{generate_test.mjs → generate.selftest.mjs} +0 -0
  573. /package/skills/ai-image/scripts/{generate_from_plan_test.mjs → generate_from_plan.selftest.mjs} +0 -0
@@ -0,0 +1,1804 @@
1
+ /**
2
+ * ============================================================
3
+ * src/web/protocol.ts —— Web/Gateway WebSocket 线路协议(ClientFrame/ServerFrame)
4
+ * ------------------------------------------------------------
5
+ * ⚠️ 不变量:本文件必须保持**纯 type-only**(只有 `import type` / `export type` /
6
+ * `export interface`,零运行时 import/export)。webchat(浏览器)靠
7
+ * `export type … from '../../src/web/protocol.js'` **单一真源**引用这里,
8
+ * 而它能安全 import 后端目录的唯一原因是:整条链全是 type,打包器(Vite/esbuild)
9
+ * 在编译期把它擦除干净,绝不把 `node:*` 依赖拉进浏览器 bundle。
10
+ *
11
+ * 一旦这里出现**任何运行时** import/export(哪怕一个 helper 函数),
12
+ * webchat bundle 就会顺着链把 `src/types.ts`→`plugins/**` 的 node 代码拖进浏览器 →
13
+ * **静默**打断前端构建。`test/webProtocolTypeOnly.test.ts` 守这条线(改动会报红)。
14
+ *
15
+ * 同理它 `import type` 了具体插件 `cron-runner` 的类型:仅因 type-only 才不构成
16
+ * 内核对插件的运行时耦合;下游若要新增插件资源帧,务必同样只引 type。
17
+ * ============================================================
18
+ */
19
+
20
+ import type { AskAnswer, AskOption, AskQuestionSpec, AskSource } from '../askBridge.js';
21
+ import type { PluginEvent } from '../plugins/pluginApi.js';
22
+ import type { AgentResultMetadata, ConversationFilePurpose, DeliverableManifest, FileActivityMetadata, LoopEvent, Message, MessageAttachmentRef, MessageBrowserReference, ProgressStage, SubagentProgress, ToolCall, ToolProgressDetail, ToolResultMetadata } from '../types.js';
23
+ import type { ConversationSearchResult, MemoryCategory, MemoryDiagnostic, MemoryEditablePatch, MemoryRecord, MemorySettings, MemoryUpdate, PersonaDocument } from '../memory/memoryService.js';
24
+ import type { HumanInterventionReason } from '../humanIntervention.js';
25
+
26
+ /**
27
+ * 桌面控制的**线路观测形状**(协议自持,不 import 具体工具)。
28
+ *
29
+ * 为什么不直接引 `tools/computeruse/protocol.ts` 的 `ComputerState`:
30
+ * 那会让协议真值反向依赖某一个工具的内部模块,而 desktop / server 都从这里
31
+ * 取类型 —— 一个工具的重构会顺着协议波及两个消费方。方向必须是
32
+ * **工具依赖协议**,不是协议依赖工具。
33
+ *
34
+ * 为什么不写成 `unknown`:desktop 面板真的在读 `activeApp?.name` /
35
+ * `windows.length` / `screenshot?.path`,降级成 unknown 只是把破坏推给消费方。
36
+ * 所以这里声明**结构子集**:协议承诺的字段写在这儿,工具侧那份更丰富的
37
+ * `ComputerState` 由 `tools/computeruse/protocol.ts` 的编译期断言自证兼容
38
+ * (搜 `ComputerObservation` 找到那处断言)。两边一旦漂移,编译就红。
39
+ */
40
+ export interface ComputerObservation {
41
+ revision: string;
42
+ epoch: number;
43
+ /** Transport metadata is exposed for diagnostics; clients must not infer authority from it. */
44
+ backend?: 'native' | 'degraded' | 'mock';
45
+ displays?: unknown[];
46
+ activeApp?: { id?: string; name?: string };
47
+ windows: unknown[];
48
+ screenshot?: { path: string; width: number; height: number };
49
+ changedRegions?: unknown[];
50
+ }
51
+
52
+ /**
53
+ * 浏览器控制权状态(协议自持)。
54
+ *
55
+ * 与上面的 `ComputerObservation` 同一条理由,但这里是**真搬过来**而不是声明子集:
56
+ * 它是个判别联合,desktop 会按 `status` 逐分支读 `reason`/`interventionId`/
57
+ * `resumeToken` 等字段,写子集会漏掉分支之间的关联。整体搬迁后
58
+ * `tools/webbrowser/browserControl.ts` 改为从这里 re-export,
59
+ * 工具侧所有既有 import 路径不变。
60
+ */
61
+ export type BrowserControlState =
62
+ | { owner: 'none'; status: 'idle' }
63
+ | { owner: 'agent'; status: 'running'; runId: string; conversationKey?: string; action?: string }
64
+ | {
65
+ owner: 'user';
66
+ status: 'waiting_human';
67
+ runId: string;
68
+ conversationKey: string;
69
+ reason: HumanInterventionReason;
70
+ interventionId: string;
71
+ resumeToken: string;
72
+ ownerId: string;
73
+ }
74
+ | { owner: 'user'; status: 'interactive'; runId?: string; conversationKey?: string };
75
+
76
+ export type {
77
+ ConversationFilePurpose,
78
+ DeliverableManifest,
79
+ FileActivityMetadata,
80
+ MessageAttachmentRef,
81
+ ResultManifestMetadata,
82
+ } from '../types.js';
83
+ export type {
84
+ ConversationSearchResult,
85
+ MemoryCategory,
86
+ MemoryRecord,
87
+ MemoryEditablePatch,
88
+ MemorySettings,
89
+ MemoryUpdate,
90
+ PersonaDocument,
91
+ } from '../memory/memoryService.js';
92
+ import type {
93
+ CronMissedRecord,
94
+ CronRunRecord,
95
+ CronTask,
96
+ CronTaskDraft,
97
+ CronTaskPatch,
98
+ CronListFilter,
99
+ } from '../../plugins/cron-runner/src/types.js';
100
+
101
+ export type AgentEvent = LoopEvent | PluginEvent;
102
+
103
+ export interface RecentDir {
104
+ workspaceId?: string;
105
+ path: string;
106
+ name: string;
107
+ lastUsedAt: number;
108
+ title?: string;
109
+ available?: boolean;
110
+ }
111
+
112
+ export interface MemoryRecordView extends MemoryRecord {
113
+ version: string;
114
+ }
115
+
116
+ export interface MemoryPersonaView extends PersonaDocument {
117
+ version: string;
118
+ }
119
+
120
+ export interface MemoryWorkspaceSummary {
121
+ workspaceId: string;
122
+ name: string;
123
+ path: string;
124
+ available: boolean;
125
+ total: number;
126
+ active: number;
127
+ needsReview: number;
128
+ superseded: number;
129
+ }
130
+
131
+ export interface MemoryOverview {
132
+ total: number;
133
+ active: number;
134
+ needsReview: number;
135
+ superseded: number;
136
+ globalCount: number;
137
+ workspaceCount: number;
138
+ categories: Record<MemoryCategory, number>;
139
+ workspaces: MemoryWorkspaceSummary[];
140
+ diagnostics: MemoryDiagnostic[];
141
+ }
142
+
143
+ export interface MemoryManagementState {
144
+ records: MemoryRecordView[];
145
+ overview: MemoryOverview;
146
+ settings: MemorySettings;
147
+ settingsVersion: string;
148
+ persona: MemoryPersonaView | null;
149
+ refreshedAt: number;
150
+ }
151
+
152
+ export type MemoryLifecycleFilter = 'all' | 'active' | 'review' | 'superseded';
153
+
154
+ export interface MemoryScopeSummary {
155
+ total: number;
156
+ active: number;
157
+ needsReview: number;
158
+ superseded: number;
159
+ diagnostics: MemoryDiagnostic[];
160
+ }
161
+
162
+ export interface MemoryWorkspaceDescriptor {
163
+ workspaceId: string;
164
+ name: string;
165
+ path: string;
166
+ available: boolean;
167
+ sessionIds: string[];
168
+ summary?: MemoryScopeSummary;
169
+ }
170
+
171
+ export interface MemoryCenterOverview {
172
+ personal: MemoryScopeSummary;
173
+ currentWorkspaceId?: string;
174
+ currentWorkspace?: MemoryScopeSummary;
175
+ workspaces: MemoryWorkspaceDescriptor[];
176
+ settings: MemorySettings;
177
+ settingsVersion: string;
178
+ persona: MemoryPersonaView | null;
179
+ refreshedAt: number;
180
+ }
181
+
182
+ /** A list-safe topic projection. Sensitive statement text is intentionally omitted. */
183
+ export interface MemoryTopicSummary {
184
+ id: string;
185
+ topicKey: string;
186
+ scope: 'personal' | 'workspace';
187
+ workspaceId?: string;
188
+ category: MemoryCategory;
189
+ subject: string;
190
+ statementPreview?: string;
191
+ sensitivity: 'normal' | 'sensitive';
192
+ lifecycle: Exclude<MemoryLifecycleFilter, 'all'>;
193
+ revision: number;
194
+ updatedAt: number;
195
+ lastConfirmedAt: number;
196
+ supersededCount: number;
197
+ }
198
+
199
+ export interface MemoryTopicPage {
200
+ scope: 'personal' | 'workspace';
201
+ workspaceId?: string;
202
+ snapshotGeneration: string;
203
+ topics: MemoryTopicSummary[];
204
+ total: number;
205
+ nextCursor?: string;
206
+ }
207
+
208
+ export interface MemoryTopicDetail {
209
+ topicKey: string;
210
+ current: MemoryRecordView;
211
+ history: MemoryRecordView[];
212
+ editable: boolean;
213
+ }
214
+
215
+ export interface ContextStatusView {
216
+ target: { kind: 'plain' | 'workspace'; sessionId: string; dir?: string };
217
+ model?: string;
218
+ usedTokens: number;
219
+ contextWindow: number;
220
+ remainingTokens: number;
221
+ compactThreshold: number;
222
+ source: 'actual' | 'estimated';
223
+ cachedPromptTokens?: number;
224
+ cacheMissTokens?: number;
225
+ cacheWriteTokens?: number;
226
+ promptCacheUsage?: import('../types.js').PromptCacheUsage;
227
+ }
228
+
229
+ export type MemoryManagementAction =
230
+ | 'load'
231
+ | 'update'
232
+ | 'confirm'
233
+ | 'persona-update'
234
+ | 'persona-clear'
235
+ | 'settings-update'
236
+ | 'forget'
237
+ | 'clear';
238
+
239
+ export interface WorkspaceTreeEntry extends RecentDir {
240
+ workspaceId: string;
241
+ activeSessionId?: string;
242
+ sessions: SessionSummary[];
243
+ }
244
+
245
+ export interface SkillInfo {
246
+ name: string;
247
+ description: string;
248
+ source?: 'builtin' | 'workspace';
249
+ }
250
+
251
+ export type ApiFormat = 'openai' | 'anthropic';
252
+
253
+ /** 模型列表的一个条目(脱敏视图——apiKey 只给 configured 布尔位,不下发原文)。 */
254
+ export interface ModelView {
255
+ id: string;
256
+ apiFormat: ApiFormat;
257
+ displayName?: string;
258
+ baseURL: string;
259
+ apiKeyConfigured: boolean;
260
+ model: string;
261
+ contextWindow: number;
262
+ maxTokens?: number;
263
+ supportsVision?: boolean;
264
+ promptCache?: { mode: 'auto' | 'session-key' | 'disabled' };
265
+ enabled: boolean;
266
+ updatedAt: number;
267
+ }
268
+
269
+ export interface WebchatConfig {
270
+ /** Stable cross-process revision. Backed by config.json savedAt. */
271
+ revision?: number;
272
+ models: ModelView[];
273
+ /** 当前被标记为基座(主循环)的模型 id;null = 尚未选定。 */
274
+ baseModelId: string | null;
275
+ compactRatio?: number;
276
+ /**
277
+ * 只读镜像:解析出的当前基座 model/contextWindow——让「显示当前用的什么模型」这类
278
+ * 读取点(cron 草稿标签、ScheduledTasksView 等)不用学会去 models[] 按 baseModelId 查。
279
+ * 不是独立可编辑字段,改基座走 baseModelId patch。
280
+ */
281
+ model?: string;
282
+ contextWindow?: number;
283
+ tavilyApiKey?: string;
284
+ tavilyApiKeyConfigured?: boolean;
285
+ clearTavilyApiKey?: boolean;
286
+ source?: 'json' | 'environment' | 'none';
287
+ readOnly?: boolean;
288
+ /** Incomplete sections persisted securely without replacing the active config. */
289
+ draftFields?: string[];
290
+ advisor?: {
291
+ configured: boolean;
292
+ enabled: boolean;
293
+ mode: 'auto' | 'manual';
294
+ /** 引用 models[].id;null = 未选。顾问不再自带一整套独立凭据。 */
295
+ modelId: string | null;
296
+ contextPolicy: 'full-relevant';
297
+ shareSensitive: boolean;
298
+ inputTokenBudget: number;
299
+ timeoutMs: number;
300
+ };
301
+ subagents?: {
302
+ enabled: boolean;
303
+ maxCallsPerTurn: number;
304
+ maxConcurrent: number;
305
+ defaultWriteIsolation: 'none' | 'worktree';
306
+ timeoutMs: number;
307
+ exploreMaxTurns: number;
308
+ generalMaxTurns: number;
309
+ };
310
+ browser?: {
311
+ enabled: boolean;
312
+ profileId: 'default';
313
+ developerMode: boolean;
314
+ allowedCdpOrigins: string[];
315
+ };
316
+ computerUse?: {
317
+ enabled: boolean;
318
+ imagePolicy: 'single-adaptive';
319
+ maxImagePixels: number;
320
+ observationFrames: number;
321
+ };
322
+ tools?: {
323
+ webSearch: ToolConfigView;
324
+ imageGeneration: ToolConfigView & {
325
+ provider?: string;
326
+ baseURL?: string;
327
+ model?: string;
328
+ protocol?: 'auto' | 'chat' | 'images';
329
+ };
330
+ openRouter: ToolConfigView;
331
+ textToSpeech: ToolConfigView & { groupIdConfigured?: boolean };
332
+ };
333
+ toolInput?: {
334
+ webSearchApiKey?: string;
335
+ clearWebSearch?: boolean;
336
+ imageProvider?: string;
337
+ imageBaseURL?: string;
338
+ imageApiKey?: string;
339
+ imageModel?: string;
340
+ imageProtocol?: 'auto' | 'chat' | 'images';
341
+ clearImageGeneration?: boolean;
342
+ openRouterApiKey?: string;
343
+ clearOpenRouter?: boolean;
344
+ ttsApiKey?: string;
345
+ ttsGroupId?: string;
346
+ clearTextToSpeech?: boolean;
347
+ };
348
+ }
349
+
350
+ export interface ModelPatchFields {
351
+ apiFormat?: ApiFormat;
352
+ displayName?: string;
353
+ baseURL?: string;
354
+ apiKey?: string;
355
+ clearApiKey?: boolean;
356
+ model?: string;
357
+ contextWindow?: number;
358
+ maxTokens?: number;
359
+ supportsVision?: boolean;
360
+ promptCache?: { mode: 'auto' | 'session-key' | 'disabled' };
361
+ enabled?: boolean;
362
+ }
363
+
364
+ export type ModelPatchOp =
365
+ | { op: 'add'; model: ModelPatchFields }
366
+ | { op: 'update'; id: string; patch: ModelPatchFields }
367
+ | { op: 'remove'; id: string };
368
+
369
+ export interface WebchatConfigPatch {
370
+ models?: ModelPatchOp[];
371
+ /** 设为基座模型;null = 清空(正常流程不会用到,保留给完整性)。 */
372
+ baseModelId?: string | null;
373
+ compactRatio?: number;
374
+ advisor?: {
375
+ clear?: boolean;
376
+ enabled?: boolean;
377
+ mode?: 'auto' | 'manual';
378
+ modelId?: string | null;
379
+ shareSensitive?: boolean;
380
+ inputTokenBudget?: number;
381
+ timeoutMs?: number;
382
+ };
383
+ subagents?: Partial<NonNullable<WebchatConfig['subagents']>>;
384
+ browser?: Partial<NonNullable<WebchatConfig['browser']>>;
385
+ computerUse?: Partial<NonNullable<WebchatConfig['computerUse']>>;
386
+ tools?: NonNullable<WebchatConfig['toolInput']>;
387
+ }
388
+
389
+ export interface ToolConfigView {
390
+ state: 'unconfigured' | 'configured' | 'incomplete' | 'error';
391
+ configured: boolean;
392
+ message?: string;
393
+ }
394
+
395
+ export type ToolConfigName = 'advisor' | 'webSearch' | 'imageGeneration' | 'openRouter' | 'textToSpeech';
396
+ /** 'provider' 分区已删除——models/baseModelId/advisor 都走立即生效的 config/update,不再自动保存。 */
397
+ export type ConfigAutosaveSection = 'general' | 'tools' | 'browser';
398
+
399
+ export interface ArchiveEntry {
400
+ id: string;
401
+ updatedAt: number;
402
+ msgCount: number;
403
+ firstUserPreview: string;
404
+ }
405
+
406
+ export interface DirEntry {
407
+ name: string;
408
+ path: string;
409
+ kind?: 'home' | 'desktop' | 'documents' | 'downloads' | 'cloud' | 'volume' | 'network' | 'root';
410
+ }
411
+
412
+ export interface DirListing {
413
+ cwd: string;
414
+ parent: string | null;
415
+ entries: DirEntry[];
416
+ roots: DirEntry[];
417
+ error?: string;
418
+ }
419
+
420
+ export interface FileBrowserEntry {
421
+ name: string;
422
+ path: string;
423
+ kind: 'directory' | 'file';
424
+ size?: number;
425
+ modifiedAt?: number;
426
+ }
427
+
428
+ export interface FileBrowserListing {
429
+ cwd: string;
430
+ parent: string | null;
431
+ entries: FileBrowserEntry[];
432
+ roots: DirEntry[];
433
+ error?: string;
434
+ }
435
+
436
+ /**
437
+ * Stable, conversation-scoped reference to an element in the supervised browser.
438
+ * Credentials, cookies and arbitrary DOM HTML are deliberately excluded.
439
+ */
440
+ export type BrowserElementReference = MessageBrowserReference;
441
+
442
+ export interface SessionSummary {
443
+ id: string;
444
+ active: boolean;
445
+ title: string;
446
+ createdAt: number;
447
+ updatedAt: number;
448
+ lastMessagePreview?: string;
449
+ modelId?: string;
450
+ }
451
+
452
+ export type ConversationTarget =
453
+ | { kind: 'plain' }
454
+ | { kind: 'workspace'; path: string };
455
+
456
+ export interface ConversationStartResult {
457
+ requestId: string;
458
+ runId: string;
459
+ conversationKind: 'plain' | 'workspace';
460
+ sessionId: string;
461
+ session: SessionSummary;
462
+ sessions: SessionSummary[];
463
+ workspace?: RecentDir;
464
+ workspacePath?: string;
465
+ workspaceDisplayName?: string;
466
+ }
467
+
468
+ export interface QueuedUserInput {
469
+ id: string;
470
+ target: { kind: 'plain' } | { kind: 'workspace'; dir: string };
471
+ sessionId: string;
472
+ text: string;
473
+ attachmentIds: string[];
474
+ browserReferences?: BrowserElementReference[];
475
+ priority: 'next' | 'interrupt';
476
+ createdAt: number;
477
+ /** Restored entries require an explicit user action before execution. */
478
+ restored?: boolean;
479
+ }
480
+
481
+ export type LocalConversationRef =
482
+ | { kind: 'plain'; sessionId: string }
483
+ | { kind: 'workspace'; workspaceId: string; dir: string; sessionId: string };
484
+
485
+ export type ConversationRunStatus =
486
+ | 'queued'
487
+ | 'running'
488
+ | 'waiting_user'
489
+ | 'waiting_human'
490
+ | 'completed'
491
+ | 'failed'
492
+ | 'cancelled'
493
+ | 'interrupted';
494
+
495
+ export interface PendingAskSummary {
496
+ requestId: string;
497
+ title?: string;
498
+ questionCount: number;
499
+ source?: AskSource;
500
+ }
501
+
502
+ export interface PendingHumanInterventionSummary {
503
+ id: string;
504
+ surface: 'browser' | 'computer';
505
+ reason:
506
+ | 'password'
507
+ | 'otp'
508
+ | 'captcha'
509
+ | 'qr_login'
510
+ | 'login'
511
+ | 'permission'
512
+ | 'security_warning'
513
+ | 'blocked'
514
+ | 'manual';
515
+ sanitizedSummary: string;
516
+ requestedAt: number;
517
+ target?: {
518
+ tabId?: string;
519
+ origin?: string;
520
+ appId?: string;
521
+ windowId?: string;
522
+ };
523
+ }
524
+
525
+ /**
526
+ * Reconnect-safe, in-memory view of the current turn. Events are bounded by the
527
+ * Desktop Runtime and are never persisted to the run-state file.
528
+ */
529
+ export interface LiveTurnSnapshot {
530
+ sequence: number;
531
+ /** Current turn projected into render-ready state. */
532
+ userMessage?: Extract<Message, { role: 'user' }>;
533
+ committedMessages: Message[];
534
+ streamingText: string;
535
+ reasoningText: string;
536
+ tools: LiveToolSnapshot[];
537
+ progressStage?: ProgressStage;
538
+ contextUsage?: Extract<LoopEvent, { type: 'context_usage' }>;
539
+ pendingAsk?: PendingAskSummary;
540
+ ask?: Extract<LoopEvent, { type: 'ask' }>;
541
+ /** Compatibility/debug tail. The materialized fields above are authoritative. */
542
+ events: AgentEvent[];
543
+ }
544
+
545
+ export interface LiveToolSnapshot {
546
+ toolCallId: string;
547
+ toolName: string;
548
+ status: 'running' | 'ok' | 'error';
549
+ argsPreview?: string;
550
+ argsFriendly?: string;
551
+ progress?: string;
552
+ progressDetail?: ToolProgressDetail;
553
+ content?: string;
554
+ ok?: boolean;
555
+ metadata?: ToolResultMetadata;
556
+ startedAt?: number;
557
+ durationMs?: number;
558
+ }
559
+
560
+ export interface ConversationRunSnapshot {
561
+ conversation: LocalConversationRef;
562
+ runId: string;
563
+ status: ConversationRunStatus;
564
+ phase?: string;
565
+ queuePosition?: number;
566
+ startedAt?: number;
567
+ finishedAt?: number;
568
+ elapsedMs?: number;
569
+ pendingInputCount: number;
570
+ unreadResult: boolean;
571
+ error?: string;
572
+ pendingAsk?: PendingAskSummary;
573
+ pendingHuman?: PendingHumanInterventionSummary;
574
+ live: LiveTurnSnapshot;
575
+ }
576
+
577
+ export interface LocalAttachmentRef {
578
+ id: string;
579
+ name: string;
580
+ mime: string;
581
+ size: number;
582
+ sha256: string;
583
+ previewUrl?: string;
584
+ image: boolean;
585
+ }
586
+
587
+ export interface CronTaskWithRuns {
588
+ task: CronTask;
589
+ recentRuns: CronRunRecord[];
590
+ unreadCount: number;
591
+ }
592
+
593
+ export interface CronDraftResult {
594
+ requestId: string;
595
+ task: CronTaskDraft | null;
596
+ missing: Array<'workspace' | 'session' | 'schedule' | 'action'>;
597
+ error?: string;
598
+ scheduleHuman?: string;
599
+ nextRunAt?: string;
600
+ }
601
+
602
+ export interface ToolStatusState {
603
+ toolName: string;
604
+ argsPreview: string;
605
+ status: 'running';
606
+ argsFriendly?: string;
607
+ }
608
+
609
+ // ---- 社交层:账号 / 好友(webchat 自建,见 web/adapter.ts + core/social/*) ----
610
+
611
+ export interface UserProfile {
612
+ id: string;
613
+ email: string;
614
+ /** 旧版账号兼容显示;新账号不再依赖 username 作为身份。 */
615
+ username?: string;
616
+ displayName: string;
617
+ createdAt: number;
618
+ /** 站长(首个注册用户):可操作服务器本地工作目录/配置/cron;普通用户经 Agent Node 挂自己的 agent。 */
619
+ isAdmin?: boolean;
620
+ }
621
+
622
+ export interface FriendEntry {
623
+ id: string;
624
+ email: string;
625
+ username?: string;
626
+ displayName: string;
627
+ status: 'accepted' | 'pending_outgoing' | 'pending_incoming';
628
+ }
629
+
630
+ // ---- 社交层:群组(webchat 自建,见 core/social/groups.ts + core/social/messages.ts) ----
631
+ // 成员 id 用带前缀字符串做多态标识:'user:<userId>' | 'agent:<workspaceAgentId>'。
632
+ // agent 成员只剩远程 Session Agent 一种(本机 cwd agent 已随中央服务收敛删除):
633
+ // 经 group/addAgent(workspaceSessionId)填充,workspaceAgentId/workspaceSessionId/
634
+ // groupPolicy 字段有值,cwd/sessionId 为历史遗留、新成员不再写入。
635
+
636
+ export interface GroupMemberEntry {
637
+ id: string;
638
+ kind: 'human' | 'agent';
639
+ displayName: string;
640
+ cwd?: string;
641
+ ownerUserId?: string;
642
+ workspaceAgentId?: string;
643
+ workspaceSessionId?: string;
644
+ groupPolicy?: 'mention' | 'proactive' | 'all' | 'disabled';
645
+ /** agent 成员透明度:该 agent 同时还在几个别的群(共享同一份工作目录上下文)。 */
646
+ otherGroupCount?: number;
647
+ }
648
+
649
+ export interface DirectConversationSummary {
650
+ id: string;
651
+ peer: UserProfile;
652
+ /** 会话创建时间:统一消息列表的排序兜底(尚无消息的新会话不沉底)。 */
653
+ createdAt?: number;
654
+ lastMessageAt?: number;
655
+ lastMessagePreview?: string;
656
+ unreadCount: number;
657
+ writable: boolean;
658
+ }
659
+
660
+ export interface DirectChatMessage {
661
+ id: string;
662
+ conversationId: string;
663
+ senderId: string;
664
+ senderName: string;
665
+ text: string;
666
+ attachments?: GroupMessageAttachment[];
667
+ createdAt: number;
668
+ }
669
+
670
+ export interface WorkspaceAgent {
671
+ id: string;
672
+ ownerUserId: string;
673
+ nodeId: string;
674
+ workspaceKey: string;
675
+ displayName: string;
676
+ status: 'online' | 'offline' | 'busy';
677
+ lastActiveAt?: number;
678
+ }
679
+
680
+ /** A publishable Agent identity: one local workspace plus one isolated session. */
681
+ export interface WorkspaceSessionAgent {
682
+ id: string;
683
+ workspaceAgentId: string;
684
+ ownerUserId: string;
685
+ displayName: string;
686
+ status: 'online' | 'offline' | 'busy';
687
+ boundGroupId?: string;
688
+ lastActiveAt?: number;
689
+ }
690
+
691
+ export interface AgentNodeSummary {
692
+ id: string;
693
+ name: string;
694
+ status: 'online' | 'offline';
695
+ lastSeenAt?: number;
696
+ }
697
+
698
+ export interface AgentDirectMessage {
699
+ id: string;
700
+ workspaceSessionId: string;
701
+ ownerUserId: string;
702
+ role: 'user' | 'assistant';
703
+ text: string;
704
+ createdAt: number;
705
+ }
706
+
707
+ export interface ConversationActionSuggestion {
708
+ id: string;
709
+ label: string;
710
+ prompt: string;
711
+ reason: string;
712
+ source: 'ai' | 'system';
713
+ }
714
+
715
+ export interface NavigationConversation {
716
+ kind: 'group' | 'project-space';
717
+ id: string;
718
+ projectId?: string;
719
+ title: string;
720
+ preview?: string;
721
+ unreadCount: number;
722
+ mentioned: boolean;
723
+ lastActivityAt?: number;
724
+ }
725
+
726
+ export interface NavigationWorkspace {
727
+ id: string;
728
+ displayName: string;
729
+ source: 'gateway-local' | 'agent-node';
730
+ status: 'online' | 'offline' | 'busy';
731
+ lastActivityAt?: number;
732
+ directTarget: {
733
+ kind: 'local' | 'agent';
734
+ id: string;
735
+ };
736
+ sessions?: WorkspaceSessionAgent[];
737
+ conversations: NavigationConversation[];
738
+ }
739
+
740
+ export interface ConversationNavigation {
741
+ workspaces: NavigationWorkspace[];
742
+ capabilities: {
743
+ canManageProvider: boolean;
744
+ canManageCron: boolean;
745
+ canUseGatewayLocalDirs: boolean;
746
+ };
747
+ }
748
+
749
+ // ---- 项目协作层:项目 / 角色 / 工作项 / 交接 / 决策 ----
750
+
751
+ export type ProjectStatus = 'active' | 'archived';
752
+ export type ProjectProvider = 'github' | 'gitlab' | 'local-git';
753
+ export type ParticipantKind = 'human' | 'agent';
754
+ export type RoleScope = 'project' | 'task';
755
+ export type WorkItemStatus = 'backlog' | 'ready' | 'in_progress' | 'review' | 'blocked' | 'done';
756
+ export type CollaborationMode = 'parallel' | 'alternative' | 'pair' | 'review';
757
+ export type HandoffStatus = 'offered' | 'accepted' | 'changes_requested' | 'completed';
758
+
759
+ export interface ProjectRepository {
760
+ id: string;
761
+ projectId: string;
762
+ provider: ProjectProvider;
763
+ remoteUrl: string;
764
+ defaultBranch: string;
765
+ name: string;
766
+ createdAt: number;
767
+ }
768
+
769
+ export interface RoleAssignment {
770
+ id: string;
771
+ projectId: string;
772
+ memberId: string;
773
+ roleKey: string;
774
+ roleName: string;
775
+ scope: RoleScope;
776
+ taskId?: string;
777
+ responsibilities: string[];
778
+ createdAt: number;
779
+ }
780
+
781
+ export interface ProjectParticipant {
782
+ memberId: string;
783
+ kind: ParticipantKind;
784
+ displayName: string;
785
+ ownerUserId?: string;
786
+ workspaceAgentId?: string;
787
+ roles: RoleAssignment[];
788
+ joinedAt: number;
789
+ }
790
+
791
+ export interface WorkspaceRepositoryStatus {
792
+ workspaceAgentId: string;
793
+ /** 本机归一化仓库 remote 的不可逆指纹;联合 workspaceAgentId 唯一标识状态。 */
794
+ repositoryFingerprint?: string;
795
+ repositoryId?: string;
796
+ remoteFingerprint?: string;
797
+ branch?: string;
798
+ headSha?: string;
799
+ dirty: boolean;
800
+ ahead?: number;
801
+ behind?: number;
802
+ sparseScopes?: string[];
803
+ checkedAt: number;
804
+ }
805
+
806
+ export type DelegationScope = 'discussion' | 'read' | 'execute';
807
+
808
+ export interface DelegationGrant {
809
+ scope: DelegationScope;
810
+ /** Workspace-relative paths or directory prefixes approved by the Agent owner. */
811
+ readScopes: string[];
812
+ /** Explicit capabilities approved for this delegation, such as Bash or Write. */
813
+ capabilities: string[];
814
+ expiresAt?: number;
815
+ }
816
+
817
+ export interface ProjectSummary {
818
+ id: string;
819
+ name: string;
820
+ description?: string;
821
+ status: ProjectStatus;
822
+ ownerUserId: string;
823
+ primarySpaceId?: string;
824
+ participantCount: number;
825
+ openWorkItemCount: number;
826
+ updatedAt: number;
827
+ createdAt: number;
828
+ }
829
+
830
+ export interface ProjectDetail extends ProjectSummary {
831
+ repositories: ProjectRepository[];
832
+ participants: ProjectParticipant[];
833
+ spaceIds: string[];
834
+ }
835
+
836
+ export interface WorkItem {
837
+ id: string;
838
+ projectId: string;
839
+ title: string;
840
+ description: string;
841
+ acceptanceCriteria: string[];
842
+ status: WorkItemStatus;
843
+ collaborationMode?: CollaborationMode;
844
+ ownerMemberId: string;
845
+ contributorIds: string[];
846
+ reviewerIds: string[];
847
+ dependencies: string[];
848
+ repositoryId?: string;
849
+ branch?: string;
850
+ fileScopes: string[];
851
+ sourceMessageId?: string;
852
+ dueAt?: number;
853
+ createdBy: string;
854
+ createdAt: number;
855
+ updatedAt: number;
856
+ }
857
+
858
+ export interface WorkItemDraft {
859
+ id?: string;
860
+ projectId: string;
861
+ title: string;
862
+ description?: string;
863
+ acceptanceCriteria?: string[];
864
+ status?: WorkItemStatus;
865
+ collaborationMode?: CollaborationMode;
866
+ ownerMemberId: string;
867
+ contributorIds?: string[];
868
+ reviewerIds?: string[];
869
+ dependencies?: string[];
870
+ repositoryId?: string;
871
+ branch?: string;
872
+ fileScopes?: string[];
873
+ sourceMessageId?: string;
874
+ dueAt?: number;
875
+ }
876
+
877
+ export interface ProjectHandoff {
878
+ id: string;
879
+ projectId: string;
880
+ workItemId: string;
881
+ fromMemberId: string;
882
+ toMemberIds: string[];
883
+ status: HandoffStatus;
884
+ summary: string;
885
+ changedFiles: string[];
886
+ tests: string[];
887
+ risks: string[];
888
+ commitSha?: string;
889
+ branch?: string;
890
+ pullRequestUrl?: string;
891
+ artifactIds: string[];
892
+ createdAt: number;
893
+ updatedAt: number;
894
+ }
895
+
896
+ export interface ProjectDecision {
897
+ id: string;
898
+ projectId: string;
899
+ title: string;
900
+ summary: string;
901
+ rationale: string;
902
+ sourceMessageIds: string[];
903
+ createdBy: string;
904
+ confirmedBy?: string;
905
+ createdAt: number;
906
+ updatedAt: number;
907
+ }
908
+
909
+ export interface ProjectActivity {
910
+ id: string;
911
+ projectId: string;
912
+ actorMemberId: string;
913
+ kind: string;
914
+ entityType: string;
915
+ entityId: string;
916
+ summary: string;
917
+ createdAt: number;
918
+ }
919
+
920
+ export interface ProjectArtifact {
921
+ id: string;
922
+ projectId: string;
923
+ workItemId?: string;
924
+ kind: 'diff' | 'commit' | 'pull_request' | 'test_report' | 'document' | 'design' | 'database_script' | 'file';
925
+ title: string;
926
+ contentHash?: string;
927
+ attachmentId?: string;
928
+ metadata: Record<string, unknown>;
929
+ createdBy: string;
930
+ createdAt: number;
931
+ }
932
+
933
+ export interface WorkConflict {
934
+ workItemId: string;
935
+ conflictsWithId: string;
936
+ overlappingScopes: string[];
937
+ reason: 'file_scope' | 'branch';
938
+ }
939
+
940
+ export interface ProjectWorkspace {
941
+ project: ProjectDetail;
942
+ workItems: WorkItem[];
943
+ handoffs: ProjectHandoff[];
944
+ decisions: ProjectDecision[];
945
+ activities: ProjectActivity[];
946
+ artifacts: ProjectArtifact[];
947
+ workspaceStatuses: WorkspaceRepositoryStatus[];
948
+ conflicts: WorkConflict[];
949
+ }
950
+
951
+ export type ConversationRef =
952
+ | { kind: 'plain'; sessionId: string }
953
+ | { kind: 'workspace'; sessionId: string }
954
+ | { kind: 'direct'; conversationId: string }
955
+ | { kind: 'group'; groupId: string }
956
+ | { kind: 'agent'; workspaceSessionId: string };
957
+
958
+ /** A lazily-created collaboration context attached to an existing conversation. */
959
+ export interface ConversationWorkspace {
960
+ conversation: ConversationRef;
961
+ workspaceId: string;
962
+ title: string;
963
+ ownerUserId: string;
964
+ participants: ProjectParticipant[];
965
+ repositories: ProjectRepository[];
966
+ tasks: WorkItem[];
967
+ handoffs: ProjectHandoff[];
968
+ decisions: ProjectDecision[];
969
+ activities: ProjectActivity[];
970
+ artifacts: ProjectArtifact[];
971
+ workspaceStatuses: WorkspaceRepositoryStatus[];
972
+ conflicts: WorkConflict[];
973
+ }
974
+
975
+ export type NodeClientFrame =
976
+ | { t: 'node/register'; token: string; name: string }
977
+ | { t: 'node/heartbeat' }
978
+ | { t: 'workspace/publish'; workspaceKey: string; displayName: string }
979
+ | { t: 'session/publish'; workspaceAgentId: string; sessionKey: string; displayName: string }
980
+ | { t: 'session/revoke'; workspaceSessionId: string }
981
+ | { t: 'workspace/revoke'; workspaceAgentId: string }
982
+ | { t: 'workspace/status'; workspaceAgentId: string; status: WorkspaceRepositoryStatus }
983
+ | { t: 'group/ack'; deliveryId: string }
984
+ | { t: 'agent/event'; requestId: string; event: AgentEvent }
985
+ | { t: 'agent/question'; requestId: string; deliveryId: string; questions: AskQuestionSpec[]; source?: AskSource }
986
+ | { t: 'agent/questionResolved'; requestId: string; deliveryId: string; state: 'answered' | 'cancelled' }
987
+ | { t: 'agent/reply'; requestId: string; text: string; files?: AgentFileMetadata[]; error?: string }
988
+ | {
989
+ /** 外部成员委托必须在 LLM 启动前获得主人批准。 */
990
+ t: 'agent/delegationRequest';
991
+ requestId: string;
992
+ deliveryId: string;
993
+ }
994
+ | {
995
+ /** 节点侧同意闸门:本机 agent 被别人(非 owner)@ 且要执行副作用操作,请求 owner 批准。
996
+ * 服务端反查 owner 并路由到 owner 客户端,回答经 agent/consentRespond 下发。 */
997
+ t: 'agent/consentRequest';
998
+ requestId: string;
999
+ deliveryId: string;
1000
+ toolName: string;
1001
+ argsPreview: string;
1002
+ };
1003
+
1004
+ export type NodeServerFrame =
1005
+ | { t: 'node/registered'; nodeId: string }
1006
+ | { t: 'workspace/published'; workspaceAgent: WorkspaceAgent }
1007
+ | { t: 'session/published'; workspaceSession: WorkspaceSessionAgent; sessionKey: string }
1008
+ | { t: 'node/error'; message: string }
1009
+ | {
1010
+ t: 'group/deliver';
1011
+ deliveryId: string;
1012
+ workspaceAgentId: string;
1013
+ /** 不透明的中央 Session Agent 标识;本机节点据此选择真实 cwd + sessionId。 */
1014
+ workspaceSessionId?: string;
1015
+ message: GroupChatMessage;
1016
+ respond: boolean;
1017
+ /** Public group context for this turn only. Never contains private Session history. */
1018
+ publicContext?: string;
1019
+ /** 该 agent 的 owner(本机主人)userId:节点侧同意闸门用它判定"这条 @ 是不是主人发的"。 */
1020
+ ownerUserId?: string;
1021
+ }
1022
+ | {
1023
+ t: 'agent/turn';
1024
+ requestId: string;
1025
+ workspaceAgentId: string;
1026
+ workspaceSessionId?: string;
1027
+ text: string;
1028
+ }
1029
+ | { t: 'agent/abort'; requestId: string }
1030
+ | { t: 'agent/answer'; requestId: string; deliveryId: string; answers: AskAnswer[] }
1031
+ | { t: 'agent/questionCancel'; requestId: string; deliveryId: string }
1032
+ | {
1033
+ /** 节点侧同意请求的裁决下发(服务端 → 节点);节点据此 resolve 挂起的 toolGate。 */
1034
+ t: 'agent/consentRespond';
1035
+ requestId: string;
1036
+ decision: 'approve' | 'deny';
1037
+ }
1038
+ | {
1039
+ t: 'agent/delegationRespond';
1040
+ requestId: string;
1041
+ grant: DelegationGrant | null;
1042
+ };
1043
+
1044
+ export interface GroupSummary {
1045
+ id: string;
1046
+ name: string;
1047
+ announcement?: string;
1048
+ /** 群主的成员 id('user:<userId>' 格式),前端据此判断是否显示"解散群"等群主专属操作。 */
1049
+ createdBy: string;
1050
+ memberCount: number;
1051
+ /** 建群时间:统一消息列表的排序兜底(尚无消息的空群不沉底)。 */
1052
+ createdAt?: number;
1053
+ lastMessageAt?: number;
1054
+ lastMessagePreview?: string;
1055
+ /** 查询者视角的未读消息数(仅 group/list 计算;group/detail 不带,前端合并时保留旧值)。 */
1056
+ unreadCount?: number;
1057
+ }
1058
+
1059
+ export interface GroupDetail extends GroupSummary {
1060
+ members: GroupMemberEntry[];
1061
+ }
1062
+
1063
+ export interface GroupMessageAttachment {
1064
+ fileId: string;
1065
+ name: string;
1066
+ mime: string;
1067
+ size: number;
1068
+ }
1069
+
1070
+ export type ConversationFileKind = 'workspace-file' | 'user-attachment' | 'group-attachment' | 'agent-file';
1071
+ export type ConversationFileActivity = 'referenced' | 'read' | 'created' | 'modified' | 'generated' | 'deleted';
1072
+
1073
+ /** Safe metadata an Agent Node may publish to a group. Absolute paths and file bytes are forbidden. */
1074
+ export interface AgentFileMetadata {
1075
+ id: string;
1076
+ ownerAgentId: string;
1077
+ name: string;
1078
+ relativePath: string;
1079
+ mime?: string;
1080
+ activity: ConversationFileActivity;
1081
+ purpose?: ConversationFilePurpose;
1082
+ lastSeenAt: number;
1083
+ }
1084
+
1085
+ /** A local-safe file reference shown beside a conversation. Absolute paths never cross this boundary. */
1086
+ export interface ConversationFileRef {
1087
+ id: string;
1088
+ conversationKey: string;
1089
+ kind: ConversationFileKind;
1090
+ name: string;
1091
+ relativePath?: string;
1092
+ mime?: string;
1093
+ size?: number;
1094
+ activity: ConversationFileActivity;
1095
+ purpose: ConversationFilePurpose;
1096
+ lastTurnId?: string;
1097
+ lastSeenAt: number;
1098
+ pinned: boolean;
1099
+ ownerAgentId?: string;
1100
+ available: boolean;
1101
+ previewable: boolean;
1102
+ previewUrl?: string;
1103
+ verification?: import('../types.js').FileVerification;
1104
+ sourceToolCallId?: string;
1105
+ sha256?: string;
1106
+ modifiedAt?: number;
1107
+ contentChanged?: boolean;
1108
+ originalAvailable?: boolean;
1109
+ archivedAvailable?: boolean;
1110
+ previewSource?: 'original' | 'archive' | 'upload';
1111
+ }
1112
+
1113
+ /** A durable, turn-scoped formal delivery. File refs are resolved at read time. */
1114
+ export interface ConversationDelivery {
1115
+ id: string;
1116
+ turnId: string;
1117
+ toolCallId?: string;
1118
+ createdAt: number;
1119
+ manifest: DeliverableManifest;
1120
+ resolvedFiles: ConversationFileRef[];
1121
+ }
1122
+
1123
+ /** Durable user-supplied and formally delivered artifacts for one user turn. */
1124
+ export interface ConversationArtifactGroup {
1125
+ turnId: string;
1126
+ createdAt: number;
1127
+ compacted: boolean;
1128
+ userAttachments: MessageAttachmentRef[];
1129
+ deliveries: ConversationDelivery[];
1130
+ }
1131
+
1132
+ export type ConversationAssetCategory = 'document' | 'code' | 'image' | 'link' | 'other';
1133
+ export type ConversationAssetOrigin = 'user-upload' | 'user-reference' | 'ai-delivery';
1134
+ export type ConversationAssetKind = 'workspace-file' | 'user-attachment' | 'web-link';
1135
+
1136
+ /** A durable, session-scoped item explicitly supplied by the user or formally delivered by the Agent. */
1137
+ export interface ConversationAsset {
1138
+ id: string;
1139
+ conversationKey: string;
1140
+ kind: ConversationAssetKind;
1141
+ category: ConversationAssetCategory;
1142
+ name: string;
1143
+ origins: ConversationAssetOrigin[];
1144
+ firstTurnId: string;
1145
+ lastTurnId: string;
1146
+ firstSeenAt: number;
1147
+ lastSeenAt: number;
1148
+ pinned: boolean;
1149
+ available: boolean;
1150
+ previewable: boolean;
1151
+ relativePath?: string;
1152
+ url?: string;
1153
+ domain?: string;
1154
+ mime?: string;
1155
+ size?: number;
1156
+ previewUrl?: string;
1157
+ verification?: import('../types.js').FileVerification;
1158
+ sha256?: string;
1159
+ modifiedAt?: number;
1160
+ contentChanged?: boolean;
1161
+ /** The original workspace file still exists at its submitted path. */
1162
+ originalAvailable?: boolean;
1163
+ /** An immutable, content-addressed copy of the submitted file is available. */
1164
+ archivedAvailable?: boolean;
1165
+ /** Which bytes are opened by the default preview action. */
1166
+ previewSource?: 'original' | 'archive' | 'upload';
1167
+ }
1168
+
1169
+ export interface GroupChatMessage {
1170
+ id: string;
1171
+ groupId: string;
1172
+ senderId: string;
1173
+ senderKind: 'human' | 'agent';
1174
+ senderName: string;
1175
+ text: string;
1176
+ mentions: string[];
1177
+ attachments?: GroupMessageAttachment[];
1178
+ agentFiles?: AgentFileMetadata[];
1179
+ createdAt: number;
1180
+ /** 'system' = 群事件系统消息(谁邀请了谁/agent 入群/改名等),居中灰字渲染,
1181
+ * 不触发 agent 路由、不计未读。缺省 = 普通聊天消息。 */
1182
+ kind?: 'system';
1183
+ }
1184
+
1185
+ /** Local, read-only social snapshot. It never contains auth tokens, absolute paths or Agent private history. */
1186
+ export interface OfflineSocialCache {
1187
+ version: 1;
1188
+ serverUrl: string;
1189
+ user: UserProfile;
1190
+ updatedAt: number;
1191
+ groups: GroupSummary[];
1192
+ groupDetails: Record<string, GroupDetail>;
1193
+ groupMessages: Record<string, GroupChatMessage[]>;
1194
+ }
1195
+
1196
+ /**
1197
+ * 用户级事件:不管用户当前打开哪个群都会推送(连接建立、解析出登录身份后订阅)。
1198
+ * 与 group/message(只推给"正打开该群"的连接)互补——未读徽标、被 @ 提醒、
1199
+ * agent 忙碌/完成通知靠这条通道。
1200
+ */
1201
+ export type UserSocialEvent =
1202
+ | {
1203
+ t: 'group/bump';
1204
+ groupId: string;
1205
+ lastMessageAt: number;
1206
+ lastMessagePreview: string;
1207
+ /** 这条消息是否 @ 了收件人本人。 */
1208
+ mentioned: boolean;
1209
+ /** true = 来自系统消息(改名/进出群等):前端只刷预览/时间,不 ++未读
1210
+ * (服务端 unreadCount 同样排除系统消息,两端一致防幽灵未读)。 */
1211
+ fromSystem?: boolean;
1212
+ }
1213
+ | {
1214
+ t: 'group/agentBusy';
1215
+ groupId: string;
1216
+ agentMemberId: string;
1217
+ displayName: string;
1218
+ busy: boolean;
1219
+ }
1220
+ | {
1221
+ t: 'conversation/bump';
1222
+ conversationId: string;
1223
+ lastMessageAt: number;
1224
+ lastMessagePreview: string;
1225
+ fromDisplayName: string;
1226
+ }
1227
+ | {
1228
+ /** 好友关系变化(申请/接受/删除)的"去刷新"信号——前端收到即重拉好友列表。 */
1229
+ t: 'social/friendsChanged';
1230
+ }
1231
+ | {
1232
+ /** 当前会话的任务、决策、仓库或交付物变化,在线成员按会话重拉。 */
1233
+ t: 'conversation/workspace/changed';
1234
+ conversation: ConversationRef;
1235
+ }
1236
+ | { t: 'agent/directMessage'; workspaceSessionId: string; message: AgentDirectMessage }
1237
+ | { t: 'agent/directEvent'; workspaceSessionId: string; event: AgentEvent }
1238
+ | {
1239
+ /** 群 Agent 的完整运行事件,仅推送给该 Agent 所有者。 */
1240
+ t: 'group/agentEvent';
1241
+ groupId: string;
1242
+ agentMemberId: string;
1243
+ displayName: string;
1244
+ event: AgentEvent;
1245
+ }
1246
+ | {
1247
+ /** 面向群成员的脱敏子任务阶段;不含工具参数、路径或私有上下文。 */
1248
+ t: 'group/agentProgress';
1249
+ groupId: string;
1250
+ agentMemberId: string;
1251
+ displayName: string;
1252
+ toolCallId: string;
1253
+ phase: 'queued' | 'preparing' | 'analyzing' | 'using_tool' | 'drafting' | 'waiting_owner' | 'completed' | 'failed';
1254
+ }
1255
+ | {
1256
+ t: 'agent/question';
1257
+ requestId: string;
1258
+ deliveryId: string;
1259
+ questions: AskQuestionSpec[];
1260
+ source?: AskSource;
1261
+ context: { kind: 'group'; groupId: string; agentMemberId: string; agentDisplayName: string } | { kind: 'direct'; workspaceSessionId: string };
1262
+ }
1263
+ | {
1264
+ t: 'agent/questionStatus';
1265
+ requestId: string;
1266
+ state: 'queued' | 'waiting' | 'answered' | 'cancelled';
1267
+ groupId?: string;
1268
+ agentMemberId?: string;
1269
+ agentDisplayName?: string;
1270
+ queuePosition?: number;
1271
+ /** 仅 Agent 所有者客户端为 true;用于本人的问答队列,不影响群内公共状态。 */
1272
+ ownerQuestion?: boolean;
1273
+ }
1274
+ | {
1275
+ /**
1276
+ * 跨机指令同意请求:别人 @ 了我拥有的 agent,且这一轮要执行副作用操作(写文件/Bash/删除等)。
1277
+ * 只推给该 agent 的 owner(本机主人)。owner 客户端弹审批卡 → group/consentRespond 回。
1278
+ * 见 core/social/consent.ts 与 host 的 pendingConsents。
1279
+ */
1280
+ t: 'group/consentRequest';
1281
+ requestId: string;
1282
+ groupId: string;
1283
+ agentMemberId: string;
1284
+ agentDisplayName: string;
1285
+ /** 发起该 @ 指令的用户显示名("是谁想驱使你的 agent")。 */
1286
+ requesterName: string;
1287
+ /** 即将执行的工具名与参数摘要(供 owner 判断风险,如 Bash: rm -rf src)。 */
1288
+ toolName: string;
1289
+ argsPreview: string;
1290
+ /** delegation 在 LLM 启动前审批;tool 是回合中的高风险工具审批。 */
1291
+ phase?: 'delegation' | 'tool';
1292
+ messagePreview?: string;
1293
+ };
1294
+
1295
+ export type ClientFrame =
1296
+ | { t: 'runtime/hello' }
1297
+ | { t: 'local/conversation/start'; requestId: string; target: ConversationTarget; text: string; attachments?: string[]; browserReferences?: BrowserElementReference[]; modelId?: string }
1298
+ | { t: 'plain/list' }
1299
+ | { t: 'plain/open'; sessionId: string; requestId?: string }
1300
+ | { t: 'plain/send'; sessionId: string; text: string; attachments?: string[]; browserReferences?: BrowserElementReference[]; requestId?: string; modelId?: string }
1301
+ | { t: 'plain/clear'; sessionId: string }
1302
+ | { t: 'plain/compact'; sessionId: string; requestId?: string }
1303
+ | { t: 'plain/rename'; sessionId: string; title: string }
1304
+ | { t: 'plain/delete'; sessionId: string }
1305
+ | { t: 'resource/files/list'; dir: string; sessionId: string }
1306
+ | { t: 'resource/assets/list'; requestId: string; target: ConversationTarget & { sessionId: string } }
1307
+ | { t: 'resource/assets/pin'; requestId: string; target: ConversationTarget & { sessionId: string }; assetId: string; pinned: boolean }
1308
+ | { t: 'resource/assets/open'; requestId: string; target: ConversationTarget & { sessionId: string }; assetId: string; source?: 'default' | 'original' | 'archive' }
1309
+ | { t: 'resource/assets/reveal'; requestId: string; target: ConversationTarget & { sessionId: string }; assetId: string; source?: 'original' | 'archive' }
1310
+ | { t: 'resource/files/open'; requestId: string; target: ConversationTarget & { sessionId: string }; relativePath: string }
1311
+ | { t: 'resource/files/pin'; dir: string; sessionId: string; relativePath: string; pinned: boolean }
1312
+ | { t: 'resource/files/reveal'; requestId?: string; dir?: string; target?: ConversationTarget & { sessionId: string }; relativePath: string }
1313
+ | { t: 'resource/memories/list'; workspaceId?: string; query?: string }
1314
+ | { t: 'resource/memories/settings/update'; autoRemember: boolean; workspaceId?: string }
1315
+ | { t: 'resource/memories/update'; id: string; scope: 'personal' | 'workspace'; expectedVersion: string; patch: MemoryUpdate; workspaceId?: string }
1316
+ | { t: 'resource/memories/confirm'; id: string; scope: 'personal' | 'workspace'; expectedVersion: string; evidenceQuote: string; sourceSessionId: string; sourceMessageId: string; workspaceId?: string }
1317
+ | { t: 'resource/memories/review'; scope?: 'personal' | 'workspace'; workspaceId?: string }
1318
+ | { t: 'resource/memories/persona/set'; content: string; evidenceQuote: string; sourceSessionId: string; sourceMessageId: string }
1319
+ | { t: 'resource/memories/persona/clear' }
1320
+ | { t: 'resource/memories/conversations/search'; requestId: string; query: string; workspaceId: string; scope?: 'workspace' | 'all'; explicitCrossWorkspace?: boolean; limit?: number }
1321
+ | { t: 'resource/memories/forget'; id: string; scope: 'personal' | 'workspace'; workspaceId?: string }
1322
+ | { t: 'resource/memories/clear'; scope: 'personal' | 'workspace'; workspaceId?: string }
1323
+ | { t: 'resource/memories/manage/load'; requestId: string }
1324
+ | { t: 'resource/memories/manage/update'; requestId: string; id: string; scope: 'personal' | 'workspace'; workspaceId?: string; expectedVersion: string; patch: MemoryEditablePatch; includeState?: boolean }
1325
+ | { t: 'resource/memories/manage/confirm'; requestId: string; id: string; scope: 'personal' | 'workspace'; workspaceId?: string; expectedVersion: string; includeState?: boolean }
1326
+ | { t: 'resource/memories/manage/persona/update'; requestId: string; content: string; expectedVersion: string; includeState?: boolean }
1327
+ | { t: 'resource/memories/manage/persona/clear'; requestId: string; expectedVersion: string; includeState?: boolean }
1328
+ | { t: 'resource/memories/manage/settings/update'; requestId: string; patch: Partial<MemorySettings>; expectedVersion: string; includeState?: boolean }
1329
+ | { t: 'resource/memories/manage/forget'; requestId: string; id: string; scope: 'personal' | 'workspace'; workspaceId?: string; expectedVersion: string; includeState?: boolean }
1330
+ | { t: 'resource/memories/manage/clear'; requestId: string; scope: 'personal' | 'workspace'; workspaceId?: string; includeState?: boolean }
1331
+ | { t: 'resource/memories/overview/load'; requestId: string; currentWorkspaceId?: string }
1332
+ | { t: 'resource/memories/topics/list'; requestId: string; scope: 'personal' | 'workspace'; workspaceId?: string; query?: string; category?: MemoryCategory | 'all'; lifecycle?: MemoryLifecycleFilter; cursor?: string; limit?: number }
1333
+ | { t: 'resource/memories/topic/detail'; requestId: string; scope: 'personal' | 'workspace'; workspaceId?: string; topicKey: string }
1334
+ | { t: 'resource/context/status'; requestId: string; target: { kind: 'plain'; sessionId: string } | { kind: 'workspace'; dir: string; sessionId: string } }
1335
+ | { t: 'resource/subagents/worktrees/diff'; requestId: string; dir: string; id: string }
1336
+ | { t: 'resource/subagents/worktrees/apply'; requestId: string; dir: string; id: string }
1337
+ | { t: 'resource/subagents/worktrees/discard'; requestId: string; dir: string; id: string }
1338
+ | { t: 'open'; dir: string; sessionId?: string; requestId?: string }
1339
+ | { t: 'send'; dir: string; text: string; sessionId?: string; attachments?: string[]; browserReferences?: BrowserElementReference[]; requestId?: string; modelId?: string }
1340
+ | { t: 'session/model/set'; target: { kind: 'plain' } | { kind: 'workspace'; dir: string }; sessionId: string; modelId: string | null }
1341
+ | { t: 'input/queue'; item: Omit<QueuedUserInput, 'id' | 'createdAt' | 'restored'> }
1342
+ | { t: 'input/queue/update'; id: string; text?: string; attachmentIds?: string[]; browserReferences?: BrowserElementReference[]; priority?: 'next' | 'interrupt'; activate?: boolean }
1343
+ | { t: 'input/queue/remove'; id: string }
1344
+ | { t: 'input/queue/get' }
1345
+ | { t: 'conversation/run/list' }
1346
+ | {
1347
+ t: 'conversation/view/open';
1348
+ requestId: string;
1349
+ target:
1350
+ | { kind: 'plain'; sessionId: string }
1351
+ | { kind: 'workspace'; dir: string; sessionId: string };
1352
+ }
1353
+ | { t: 'conversation/run/abort'; conversation: LocalConversationRef; runId: string }
1354
+ | { t: 'conversation/run/answer'; conversation: LocalConversationRef; runId: string; requestId: string; answers: AskAnswer[] }
1355
+ | { t: 'conversation/run/cancel-ask'; conversation: LocalConversationRef; runId: string; requestId: string }
1356
+ | { t: 'conversation/result/mark-seen'; conversation: LocalConversationRef; runId?: string }
1357
+ | { t: 'conversation/run/configure'; maxConcurrent: number }
1358
+ | { t: 'answer'; requestId: string; answers: AskAnswer[] }
1359
+ | { t: 'cancelAsk'; requestId: string }
1360
+ | { t: 'abort' }
1361
+ | { t: 'new'; dir: string; sessionId?: string }
1362
+ | { t: 'compact'; dir: string; sessionId?: string; requestId?: string }
1363
+ | { t: 'listDirs' }
1364
+ | { t: 'workspace/index/get' }
1365
+ | { t: 'workspace/recovery/preview' }
1366
+ | { t: 'workspace/recovery/apply' }
1367
+ | { t: 'social/cache/get'; serverUrl: string }
1368
+ | { t: 'social/cache/save'; cache: OfflineSocialCache }
1369
+ | { t: 'social/cache/clear'; serverUrl: string; userId?: string }
1370
+ | { t: 'workspace/register'; requestId: string; path: string }
1371
+ | { t: 'browseDir'; path?: string }
1372
+ | { t: 'file/browse'; requestId: string; path?: string }
1373
+ | { t: 'removeDir'; dir: string }
1374
+ | { t: 'listArchives'; dir: string }
1375
+ | { t: 'restoreArchive'; dir: string; id: string; sessionId?: string }
1376
+ | { t: 'listSessions'; dir: string }
1377
+ | { t: 'switchSession'; dir: string; sessionId: string; requestId?: string }
1378
+ | { t: 'createSession'; dir: string; title?: string }
1379
+ | { t: 'renameSession'; dir: string; sessionId: string; title: string }
1380
+ | { t: 'copySession'; dir: string; sessionId: string; title?: string }
1381
+ | { t: 'deleteSession'; dir: string; sessionId: string }
1382
+ | { t: 'config/get' }
1383
+ | { t: 'config/update'; requestId: string; revision?: number; patch: WebchatConfigPatch }
1384
+ | { t: 'config/autosave'; requestId: string; revision?: number; section: ConfigAutosaveSection; patch: WebchatConfigPatch }
1385
+ | { t: 'config/tool/test'; tool: ToolConfigName }
1386
+ /**
1387
+ * 模型列表条目的连通性测试——跟 config/tool/test 同一先例的延伸(测试从来不是配置变更,
1388
+ * 一直走独立于 patch 的姊妹帧),只是模型是开放式按 id 索引的动态集合,ToolConfigName
1389
+ * 的封闭枚举表达不了。modelId 测已保存条目;draft 测弹窗里还没提交的正在填写的值。
1390
+ */
1391
+ | { t: 'config/model/test'; requestId: string; modelId?: string; draft?: { apiFormat: ApiFormat; baseURL: string; apiKey?: string; model: string } }
1392
+ | { t: 'getSkills'; dir?: string }
1393
+ | { t: 'resource/crons/list'; filter?: CronListFilter }
1394
+ | { t: 'resource/crons/show'; id: string }
1395
+ | { t: 'resource/crons/draft'; requestId: string; text: string; cwd?: string; sessionId?: string; model?: string }
1396
+ | { t: 'resource/crons/create'; requestId: string; task: CronTaskDraft }
1397
+ | { t: 'resource/crons/update'; requestId: string; patch: CronTaskPatch }
1398
+ | { t: 'resource/crons/delete'; requestId: string; id: string }
1399
+ | { t: 'resource/crons/pause'; requestId: string; id: string }
1400
+ | { t: 'resource/crons/resume'; requestId: string; id: string }
1401
+ | { t: 'resource/crons/run'; requestId: string; id: string }
1402
+ | { t: 'resource/crons/missed' }
1403
+ | { t: 'resource/crons/mark-read'; id: string }
1404
+ | { t: 'resource/crons/mark-all-read' }
1405
+ | { t: 'resource/commands/list'; workspaceAgentId?: string; dir?: string }
1406
+ | { t: 'social/friends/list' }
1407
+ | { t: 'social/friends/search'; query: string }
1408
+ | { t: 'social/friends/request'; toUserId: string }
1409
+ | { t: 'social/friends/respond'; fromUserId: string; accept: boolean }
1410
+ | { t: 'social/friends/remove'; userId: string }
1411
+ | { t: 'conversation/list' }
1412
+ | { t: 'conversation/navigation/get' }
1413
+ | { t: 'conversation/open'; conversationId: string }
1414
+ | { t: 'conversation/start'; friendUserId: string }
1415
+ | { t: 'conversation/send'; conversationId: string; text: string; attachments?: string[] }
1416
+ | { t: 'conversation/history'; conversationId: string; beforeId?: string; limit?: number }
1417
+ | { t: 'agent/direct/open'; workspaceSessionId: string }
1418
+ | { t: 'agent/direct/send'; workspaceSessionId: string; text: string }
1419
+ | { t: 'agent/direct/abort'; workspaceSessionId: string }
1420
+ | { t: 'conversation/actions/suggest'; kind: 'group' | 'direct' | 'agent'; id: string }
1421
+ | { t: 'node/pairing/create'; name: string }
1422
+ | { t: 'node/list' }
1423
+ | { t: 'workspace/list' }
1424
+ | { t: 'conversation/workspace/open'; conversation: ConversationRef }
1425
+ | { t: 'conversation/task/save'; conversation: ConversationRef; task: Omit<WorkItemDraft, 'projectId'> }
1426
+ | { t: 'conversation/task/delete'; conversation: ConversationRef; taskId: string }
1427
+ | { t: 'conversation/decision/save'; conversation: ConversationRef; decision: Omit<ProjectDecision, 'id' | 'projectId' | 'createdAt' | 'updatedAt' | 'createdBy'> & { id?: string } }
1428
+ | { t: 'conversation/handoff/save'; conversation: ConversationRef; handoff: Omit<ProjectHandoff, 'id' | 'projectId' | 'createdAt' | 'updatedAt'> & { id?: string } }
1429
+ | { t: 'conversation/handoff/status'; conversation: ConversationRef; handoffId: string; status: HandoffStatus }
1430
+ | { t: 'conversation/repository/add'; conversation: ConversationRef; provider: ProjectProvider; remoteUrl: string; defaultBranch: string; name?: string }
1431
+ | { t: 'conversation/repository/remove'; conversation: ConversationRef; repositoryId: string }
1432
+ | { t: 'conversation/artifact/save'; conversation: ConversationRef; artifact: Omit<ProjectArtifact, 'id' | 'projectId' | 'createdAt' | 'createdBy'> & { id?: string } }
1433
+ | { t: 'conversation/artifact/delete'; conversation: ConversationRef; artifactId: string }
1434
+ | { t: 'group/list' }
1435
+ | { t: 'group/create'; name: string; memberIds?: string[]; workspaceSessionIds?: string[] }
1436
+ | { t: 'group/rename'; groupId: string; name: string }
1437
+ | { t: 'group/setAnnouncement'; groupId: string; announcement: string }
1438
+ | { t: 'group/transferOwner'; groupId: string; newOwnerUserId: string }
1439
+ | { t: 'group/delete'; groupId: string }
1440
+ | { t: 'group/addHuman'; groupId: string; friendUserId: string }
1441
+ | { t: 'group/addAgent'; groupId: string; workspaceSessionId: string }
1442
+ | { t: 'group/setMemberPolicy'; groupId: string; memberId: string; policy: 'mention' | 'proactive' | 'all' | 'disabled' }
1443
+ | { t: 'group/removeMember'; groupId: string; memberId: string }
1444
+ | { t: 'group/open'; groupId: string }
1445
+ | { t: 'group/send'; groupId: string; text: string; mentions?: string[]; attachments?: string[] }
1446
+ | { t: 'group/history'; groupId: string; beforeId?: string; limit?: number }
1447
+ | { t: 'group/read'; groupId: string; messageId: string }
1448
+ | {
1449
+ /** owner 对跨机指令同意请求的裁决;remember 记住信任(免以后再问)。 */
1450
+ t: 'group/consentRespond';
1451
+ requestId: string;
1452
+ decision: 'approve' | 'deny';
1453
+ remember?: 'person' | 'group' | '30m';
1454
+ scope?: DelegationScope;
1455
+ readScopes?: string[];
1456
+ capabilities?: string[];
1457
+ }
1458
+ | { t: 'agent/answer'; requestId: string; answers: AskAnswer[] }
1459
+ | { t: 'agent/questionCancel'; requestId: string }
1460
+ | { t: 'human-intervention/get'; requestId?: string; conversationKey?: string; runId?: string }
1461
+ | {
1462
+ t: 'human-intervention/resume';
1463
+ requestId?: string;
1464
+ interventionId: string;
1465
+ resumeToken: string;
1466
+ ownerId: string;
1467
+ conversationKey: string;
1468
+ runId: string;
1469
+ }
1470
+ | {
1471
+ t: 'human-intervention/cancel';
1472
+ requestId?: string;
1473
+ interventionId: string;
1474
+ resumeToken: string;
1475
+ ownerId: string;
1476
+ conversationKey: string;
1477
+ runId: string;
1478
+ }
1479
+ // ---- Browser automation frames (product-grade) ----
1480
+ | { t: 'browser/context/set'; conversationKey: string; runId?: string; requestId?: string }
1481
+ // Mode control
1482
+ | { t: 'browser/start'; requestId?: string; headless?: boolean; viewport?: { width: number; height: number } }
1483
+ | { t: 'browser/stop'; requestId?: string }
1484
+ | { t: 'browser/mode'; mode: 'browse' | 'assist' | 'auto'; requestId?: string }
1485
+ | { t: 'browser/control/get'; requestId?: string }
1486
+ | { t: 'browser/control/takeover'; requestId?: string }
1487
+ | { t: 'browser/control/resume'; requestId?: string; resumeToken?: string }
1488
+ | { t: 'browser/control/stop'; requestId?: string; resumeToken?: string }
1489
+ // Tab management
1490
+ | { t: 'browser/tab/new'; requestId?: string; url?: string }
1491
+ | { t: 'browser/tab/close'; requestId?: string; tabId?: string }
1492
+ | { t: 'browser/tab/switch'; tabId: string; requestId?: string }
1493
+ | { t: 'browser/tabs'; requestId?: string }
1494
+ // Navigation (user-facing)
1495
+ | { t: 'browser/navigate'; requestId?: string; url: string; newTab?: boolean }
1496
+ | { t: 'browser/back'; requestId?: string }
1497
+ | { t: 'browser/forward'; requestId?: string }
1498
+ | { t: 'browser/reload'; requestId?: string }
1499
+ // AI interaction (Agent actions)
1500
+ | { t: 'browser/snapshot'; requestId?: string; interactive?: boolean }
1501
+ | { t: 'browser/screenshot'; requestId?: string; annotate?: boolean; fullPage?: boolean; path?: string }
1502
+ | { t: 'browser/eval'; requestId?: string; js: string }
1503
+ | { t: 'browser/click'; requestId?: string; selector: string; byRef?: boolean }
1504
+ | { t: 'browser/fill'; requestId?: string; selector: string; value: string }
1505
+ | { t: 'browser/type'; requestId?: string; selector: string; value: string }
1506
+ | { t: 'browser/hover'; requestId?: string; selector: string }
1507
+ | { t: 'browser/scroll'; requestId?: string; x?: number; y?: number; selector?: string; direction?: 'up' | 'down' | 'top' | 'bottom' }
1508
+ | { t: 'browser/select'; requestId?: string; selector: string; value: string | string[] }
1509
+ | { t: 'browser/press'; requestId?: string; key: string; selector?: string }
1510
+ | { t: 'browser/wait'; requestId?: string; ms?: number; selector?: string; text?: string }
1511
+ | { t: 'browser/upload'; requestId?: string; selector: string; files: string[] }
1512
+ | { t: 'browser/drag'; requestId?: string; fromSelector: string; toSelector: string }
1513
+ // User input (browse mode - direct interaction via canvas)
1514
+ | { t: 'browser/user/input'; eventType: 'mouseMoved' | 'mousePressed' | 'mouseReleased' | 'mouseWheel' | 'keyDown' | 'keyUp' | 'char'; x?: number; y?: number; button?: string; clickCount?: number; deltaX?: number; deltaY?: number; key?: string; code?: string; text?: string; modifiers?: number; windowsVirtualKeyCode?: number }
1515
+ // JS dialog handling (alert/confirm/prompt)
1516
+ | { t: 'browser/dialog/accept'; requestId?: string; text?: string }
1517
+ | { t: 'browser/dialog/dismiss'; requestId?: string }
1518
+ // Agent pointer visualization (sent FROM server to UI to show where AI is acting)
1519
+ // Element marking (UI markers / pick mode)
1520
+ | { t: 'browser/pick'; requestId?: string; x: number; y: number }
1521
+ | { t: 'browser/mark/element'; requestId?: string; selector: string; label?: string; color?: string }
1522
+ | { t: 'browser/mark/clear'; requestId?: string }
1523
+ | { t: 'browser/mark/mode'; enabled: boolean; requestId?: string }
1524
+ // Viewport & device
1525
+ | { t: 'browser/viewport'; width: number; height: number; requestId?: string }
1526
+ | { t: 'browser/device'; preset?: string; width?: number; height?: number; requestId?: string }
1527
+ | { t: 'browser/media'; scheme?: 'light' | 'dark' | 'no-preference'; offline?: boolean; requestId?: string }
1528
+ // Recording
1529
+ | { t: 'browser/record/start'; requestId?: string; path?: string }
1530
+ | { t: 'browser/record/stop'; requestId?: string }
1531
+ // Content extraction
1532
+ | { t: 'browser/getContent'; requestId?: string; selector?: string }
1533
+ | { t: 'browser/pdf'; requestId?: string; path?: string }
1534
+ // Cookies & auth
1535
+ | { t: 'browser/cookies/get'; requestId?: string }
1536
+ | { t: 'browser/cookies/set'; requestId?: string; cookies: Array<{ name: string; value: string; domain?: string; path?: string }> }
1537
+ | { t: 'browser/cookies/clear'; requestId?: string }
1538
+ | { t: 'browser/profile/clear'; requestId?: string }
1539
+ // Read-only developer diagnostics. Full CDP access remains a separate, disabled-by-default setting.
1540
+ | { t: 'browser/debug/console'; requestId?: string }
1541
+ | { t: 'browser/debug/errors'; requestId?: string }
1542
+ | { t: 'browser/debug/network'; requestId?: string }
1543
+ | { t: 'browser/debug/styles'; requestId?: string; selector?: string }
1544
+ | { t: 'browser/debug/vitals'; requestId?: string; url?: string }
1545
+ | { t: 'browser/debug/trace/start'; requestId?: string }
1546
+ | { t: 'browser/debug/trace/stop'; requestId?: string; path?: string }
1547
+ // Agent pointer visualization control (sent to frontend to show agent cursor)
1548
+ | { t: 'browser/agent/pointer'; x: number; y: number; visible: boolean; action?: 'move' | 'click' | 'type' | 'scroll' | 'idle' | 'hover'; elementRef?: string }
1549
+ // Native desktop Computer Use is controlled by the trusted host.
1550
+ | { t: 'computer/status'; requestId?: string; conversationKey?: string; runId?: string }
1551
+ | { t: 'computer/permissions'; requestId?: string }
1552
+ | { t: 'computer/observe'; requestId?: string; conversationKey: string; runId: string }
1553
+ | { t: 'computer/control/takeover'; requestId?: string; conversationKey: string; runId: string }
1554
+ | { t: 'computer/control/resume'; requestId?: string; conversationKey: string; runId: string; interventionId?: string; resumeToken?: string; ownerId?: string }
1555
+ | { t: 'computer/control/stop'; requestId?: string; conversationKey: string; runId: string; interventionId?: string; resumeToken?: string; ownerId?: string }
1556
+ | { t: 'computer/control/emergency-stop-all'; requestId?: string }
1557
+ // 终端不走 WS:改由 Tauri 原生真 PTY(minimal-desktop src-tauri/src/pty.rs)承载。
1558
+ // ---- 工作台任意路径文件预览(工作目录内) ----
1559
+ | { t: 'file/preview/open'; requestId: string; path: string };
1560
+
1561
+ export type ServerFrame =
1562
+ | { t: 'runtime/hello'; protocolVersion: number; runtimeVersion: string; capabilities: string[] }
1563
+ | {
1564
+ t: 'human-intervention/started' | 'human-intervention/changed';
1565
+ intervention: PendingHumanInterventionSummary & {
1566
+ ownerId: string;
1567
+ conversationKey: string;
1568
+ runId: string;
1569
+ resumeToken: string;
1570
+ expiresAt?: number;
1571
+ };
1572
+ }
1573
+ | {
1574
+ t: 'human-intervention/resolved';
1575
+ resolution: import('../humanIntervention.js').HumanInterventionResolution;
1576
+ }
1577
+ | { t: 'conversation/started'; result: ConversationStartResult }
1578
+ | { t: 'plain/sessions'; sessions: SessionSummary[] }
1579
+ | { t: 'plain/history'; sessionId: string; messages: Message[] }
1580
+ | {
1581
+ t: 'conversation/view/opened';
1582
+ requestId: string;
1583
+ conversationKey: string;
1584
+ historyRevision: string;
1585
+ messages: Message[];
1586
+ deliveries?: ConversationDelivery[];
1587
+ assets?: ConversationAsset[];
1588
+ artifactGroups?: ConversationArtifactGroup[];
1589
+ runSnapshot?: ConversationRunSnapshot;
1590
+ contextUsage?: Extract<LoopEvent, { type: 'context_usage' }>;
1591
+ }
1592
+ | { t: 'conversation/delivery/changed'; conversationKey: string; delivery: ConversationDelivery }
1593
+ | { t: 'conversation/assets/changed'; conversationKey: string; assets: ConversationAsset[] }
1594
+ | { t: 'resource/files/list'; dir: string; sessionId: string; files: ConversationFileRef[] }
1595
+ | { t: 'resource/assets/list'; requestId: string; conversationKey: string; assets?: ConversationAsset[]; error?: string }
1596
+ | { t: 'resource/assets/pinned'; requestId: string; ok: boolean; error?: string }
1597
+ | { t: 'resource/assets/opened'; requestId: string; ref?: ConversationFileRef; error?: string }
1598
+ | { t: 'resource/assets/revealed'; requestId: string; ok: boolean; error?: string }
1599
+ | { t: 'resource/files/opened'; requestId: string; ref?: ConversationFileRef; error?: string }
1600
+ | { t: 'resource/files/revealed'; requestId: string; ok: boolean; error?: string }
1601
+ | { t: 'resource/memories'; records: MemoryRecord[]; settings: MemorySettings; workspaceId?: string; reviewRecords?: MemoryRecord[]; persona?: PersonaDocument | null }
1602
+ | { t: 'resource/memories/conversations'; requestId: string; results: ConversationSearchResult[]; error?: string }
1603
+ | { t: 'resource/memories/manage/state'; requestId: string; state: MemoryManagementState }
1604
+ | { t: 'resource/memories/manage/result'; requestId: string; action: MemoryManagementAction; ok: boolean; state?: MemoryManagementState; error?: string; conflict?: boolean }
1605
+ | { t: 'resource/memories/overview'; requestId: string; overview?: MemoryCenterOverview; error?: string }
1606
+ | { t: 'resource/memories/topics'; requestId: string; page?: MemoryTopicPage; error?: string; errorCode?: 'stale_cursor' }
1607
+ | { t: 'resource/memories/topic'; requestId: string; detail?: MemoryTopicDetail; error?: string }
1608
+ | { t: 'resource/context/status'; requestId: string; status?: ContextStatusView; error?: string }
1609
+ | { t: 'resource/subagents/worktree/result'; requestId: string; action: 'diff' | 'apply' | 'discard'; ok: boolean; id: string; diff?: string; changedFiles?: string[]; error?: string }
1610
+ | { t: 'ready'; dirs: RecentDir[]; workspaceIndex?: WorkspaceTreeEntry[]; defaultDir?: string; localAttachmentToken?: string }
1611
+ | { t: 'workspace/index'; workspaces: WorkspaceTreeEntry[] }
1612
+ | { t: 'workspace/index/changed'; workspaces: WorkspaceTreeEntry[] }
1613
+ | { t: 'workspace/recovery'; applied: boolean; workspaces: number; sessions: number; recoverable: Array<{ fileName: string; reason: string; suggestedPath?: string }> }
1614
+ | { t: 'social/cache'; serverUrl: string; cache: OfflineSocialCache | null }
1615
+ | { t: 'dirs'; dirs: RecentDir[] }
1616
+ | { t: 'workspace/registered'; requestId: string; dir?: RecentDir; dirs?: RecentDir[]; error?: string }
1617
+ | { t: 'dirListing'; listing: DirListing }
1618
+ | { t: 'archives'; dir: string; entries: ArchiveEntry[] }
1619
+ | { t: 'sessions'; dir: string; sessions: SessionSummary[] }
1620
+ | { t: 'history'; dir: string; sessionId?: string; messages: Message[] }
1621
+ | { t: 'event'; event: AgentEvent; dir?: string; sessionId: string; runId: string; sequence?: number }
1622
+ | { t: 'conversation/run/snapshot'; snapshot: ConversationRunSnapshot }
1623
+ | { t: 'conversation/run/changed'; snapshots: ConversationRunSnapshot[]; maxConcurrent: number }
1624
+ | { t: 'input/queue/changed'; items: QueuedUserInput[] }
1625
+ | { t: 'input/queue/started'; item: QueuedUserInput }
1626
+ | { t: 'config'; config: WebchatConfig | null }
1627
+ | { t: 'config/updated'; requestId: string; revision: number; config: WebchatConfig }
1628
+ | { t: 'config/autosaved'; requestId: string; revision: number; state: 'applied' | 'draft'; config: WebchatConfig; draftFields?: string[] }
1629
+ | { t: 'config/update-failed'; requestId: string; message: string; fieldErrors?: Record<string, string>; currentRevision?: number }
1630
+ | { t: 'config/tool/tested'; tool: ToolConfigName; ok: boolean; message: string }
1631
+ | { t: 'config/model/tested'; requestId: string; ok: boolean; message: string }
1632
+ | { t: 'skills'; skills: SkillInfo[] }
1633
+ | { t: 'server_error'; message: string }
1634
+ | { t: 'resource/crons/list'; tasks: CronTaskWithRuns[]; missedCount: number }
1635
+ | { t: 'resource/crons/draft'; draft: CronDraftResult }
1636
+ | { t: 'resource/crons/show'; task: CronTaskWithRuns | null }
1637
+ | { t: 'resource/crons/missed'; missed: CronMissedRecord[] }
1638
+ | { t: 'resource/crons/changed'; tasks: CronTaskWithRuns[]; missedCount: number }
1639
+ | { t: 'resource/commands/list'; commands: CommandDescriptor[] }
1640
+ | { t: 'social/me'; user: UserProfile | null }
1641
+ | { t: 'social/friends'; friends: FriendEntry[] }
1642
+ | { t: 'social/searchResults'; users: UserProfile[] }
1643
+ | { t: 'social/error'; message: string }
1644
+ | { t: 'conversation/list'; conversations: DirectConversationSummary[] }
1645
+ | { t: 'conversation/navigation'; navigation: ConversationNavigation }
1646
+ | { t: 'conversation/detail'; conversation: DirectConversationSummary }
1647
+ | { t: 'conversation/message'; conversationId: string; message: DirectChatMessage }
1648
+ | { t: 'conversation/history'; conversationId: string; messages: DirectChatMessage[]; hasMore: boolean }
1649
+ | { t: 'agent/direct/history'; workspaceSessionId: string; messages: AgentDirectMessage[] }
1650
+ | { t: 'agent/direct/message'; workspaceSessionId: string; message: AgentDirectMessage }
1651
+ | { t: 'agent/direct/event'; workspaceSessionId: string; event: AgentEvent }
1652
+ | { t: 'agent/direct/error'; workspaceSessionId?: string; message: string }
1653
+ | { t: 'conversation/actions'; kind: 'group' | 'direct' | 'agent'; id: string; actions: ConversationActionSuggestion[] }
1654
+ | { t: 'node/pairing'; code: string; expiresAt: number }
1655
+ | { t: 'node/list'; nodes: AgentNodeSummary[] }
1656
+ | { t: 'workspace/list'; agents: WorkspaceAgent[]; sessions: WorkspaceSessionAgent[] }
1657
+ | { t: 'conversation/workspace'; workspace: ConversationWorkspace | null }
1658
+ | { t: 'conversation/workspace/error'; message: string }
1659
+ | { t: 'group/list'; groups: GroupSummary[] }
1660
+ | { t: 'group/detail'; group: GroupDetail }
1661
+ | { t: 'group/message'; groupId: string; message: GroupChatMessage }
1662
+ | { t: 'group/history'; groupId: string; messages: GroupChatMessage[]; hasMore: boolean }
1663
+ /** agent 回合的流式预览增量(只推给正打开该群的连接);尽力而为,最终 group/message 是真值。 */
1664
+ | { t: 'group/agentStream'; groupId: string; agentMemberId: string; displayName: string; delta: string }
1665
+ | UserSocialEvent
1666
+ // ---- Browser automation server frames (product-grade) ----
1667
+ | { t: 'browser/context/changed'; requestId?: string; conversationKey: string; runId: string; tabId?: string }
1668
+ | { t: 'browser/started'; requestId?: string; streamPort: number; pid?: number; sessionId?: string; conversationKey?: string; runId?: string }
1669
+ | { t: 'browser/stopped'; requestId?: string }
1670
+ | { t: 'browser/mode'; mode: 'browse' | 'assist' | 'auto'; requestId?: string }
1671
+ | { t: 'browser/status'; connected: boolean; screencasting: boolean; viewportWidth: number; viewportHeight: number; engine: string; recording?: boolean; mode?: 'browse' | 'assist' | 'auto'; url?: string; title?: string }
1672
+ | { t: 'browser/frame'; data: string; metadata?: Record<string, unknown>; sessionId?: string; tabId?: string; conversationKey?: string; runId?: string; frameWidth?: number; frameHeight?: number; viewportWidth?: number; viewportHeight?: number; deviceScaleFactor?: number; pageRevision?: string }
1673
+ | { t: 'browser/tabs'; tabs: Array<{ id: string; url: string; title?: string; active: boolean; favicon?: string }>; timestamp?: number }
1674
+ | { t: 'browser/tab/activated'; tabId: string }
1675
+ | { t: 'browser/url'; url: string; tabId?: string }
1676
+ | { t: 'browser/title'; title: string; tabId?: string }
1677
+ | { t: 'browser/navigation'; url: string; state: 'start' | 'commit' | 'load' | 'domcontentloaded' }
1678
+ | { t: 'browser/console'; level?: string; text: string; source?: string }
1679
+ | { t: 'browser/page_error'; text: string }
1680
+ | { t: 'browser/download'; url: string; filename?: string; path?: string; state: 'start' | 'progress' | 'complete' | 'canceled'; receivedBytes?: number; totalBytes?: number }
1681
+ | { t: 'browser/dialog'; type: 'alert' | 'confirm' | 'prompt' | 'beforeunload'; message: string; defaultValue?: string }
1682
+ | { t: 'browser/snapshot'; requestId?: string; tree: string }
1683
+ | { t: 'browser/screenshot'; requestId?: string; path?: string; data?: string; error?: string }
1684
+ | { t: 'browser/content'; requestId?: string; text: string }
1685
+ | { t: 'browser/picked'; requestId?: string; reference?: BrowserElementReference; ref?: string; tag?: string; text?: string; boundingBox?: { x: number; y: number; width: number; height: number }; attributes?: Record<string, string>; error?: string }
1686
+ | { t: 'browser/marked/elements'; elements: Array<{ ref: string; tag: string; text?: string; boundingBox?: { x: number; y: number; width: number; height: number } }> }
1687
+ | { t: 'browser/agent/pointer'; x: number; y: number; visible: boolean; action?: 'move' | 'click' | 'type' | 'scroll' | 'idle' | 'hover'; elementRef?: string }
1688
+ | { t: 'browser/agent/acting'; acting: boolean; action?: string; target?: string }
1689
+ /**
1690
+ * 一次定位失败后,引擎从当前页面挑出的最像目标的元素。
1691
+ *
1692
+ * 送到面板是为了让**人**参与:AI 卡住时人一眼就能看出哪个才对,点一下把 @eN 喂回
1693
+ * 对话,比让模型再猜一轮便宜得多。候选只进对话时,盯着浏览器的人只看到 AI 忽然停住。
1694
+ */
1695
+ | {
1696
+ t: 'browser/agent/candidates';
1697
+ candidates: Array<{ ref: string; line: string }>;
1698
+ selector?: string;
1699
+ }
1700
+ /**
1701
+ * 一次动作**做完之后**的生效结论。只在结论不是「变了」时发。
1702
+ *
1703
+ * ⚠️ 刻意**不复用** `browser/agent/acting`。acting 是一个瞬态信号(动作进行中),
1704
+ * 生命周期由 `beginAgentAction`/`finally` 界定;而结论恰恰诞生于动作结束那一刻,
1705
+ * 塞进 acting 会被紧随其后的 `acting:false` 立刻抹掉——那正是它上一版**在面板上
1706
+ * 完全不可见**的原因(单测还是绿的,因为测的是字符串拆分不是可见性)。
1707
+ * 结论是有独立生命周期的状态,就该有独立的帧。
1708
+ */
1709
+ | {
1710
+ t: 'browser/agent/outcome';
1711
+ action: string;
1712
+ effect: 'unchanged' | 'unknown';
1713
+ selector?: string;
1714
+ /** 被当作页面噪声豁免掉的行数(>0 表示这个结论有保留)。 */
1715
+ maskedLines?: number;
1716
+ }
1717
+ | { t: 'browser/control/changed'; state: BrowserControlState }
1718
+ | {
1719
+ t: 'browser/challenge/detected';
1720
+ reason: Exclude<import('../humanIntervention.js').HumanInterventionReason, 'manual'>;
1721
+ summary: string;
1722
+ resumeToken: string;
1723
+ runId: string;
1724
+ conversationKey?: string;
1725
+ }
1726
+ | { t: 'browser/result'; requestId?: string; action: string; ok: boolean; conversationKey?: string; runId?: string; tabId?: string; content?: string; error?: string; data?: unknown }
1727
+ | { t: 'browser/cookies'; requestId?: string; cookies: Array<{ name: string; value: string; domain?: string; path?: string }> }
1728
+ | { t: 'browser/device'; preset?: string; width: number; height: number }
1729
+ | { t: 'browser/profile/status'; configured: boolean; profileId: 'default'; developerMode: boolean; engine: string }
1730
+ | { t: 'browser/error'; message: string; code?: string }
1731
+ | { t: 'computer/status'; requestId?: string; available: boolean; serviceVersion?: string; implementation?: string; capabilities?: string[]; error?: string }
1732
+ | { t: 'computer/permissions'; requestId?: string; permissions?: unknown; error?: string }
1733
+ | { t: 'computer/observed'; requestId?: string; conversationKey: string; runId: string; state?: ComputerObservation; data?: unknown; error?: string }
1734
+ /**
1735
+ * A privacy-preserving live action cue for the supervised Computer Use
1736
+ * workbench. It intentionally carries neither typed text nor an absolute
1737
+ * screen coordinate: x/y stay in the existing 0-1000 display-relative space.
1738
+ */
1739
+ | { t: 'computer/action'; conversationKey: string; runId: string; action: string; x?: number; y?: number; displayId?: string; occurredAt: number }
1740
+ | {
1741
+ t: 'computer/control/changed';
1742
+ /**
1743
+ * ⚠️ **每个变体都必须带 `conversationKey` + `runId`,`idle` 也不例外。**
1744
+ *
1745
+ * 早先 `idle` 是唯一无作用域的变体,于是一个运行结束就广播一条「谁也不知道
1746
+ * 说的是哪个会话」的空闲状态:另一个会话明明还在移鼠标,它的工作台却显示
1747
+ * 「已就绪」。屏幕是唯一物理资源,这种误报比看不到状态更危险 —— 用户会以为
1748
+ * 可以安全地去动键盘。
1749
+ *
1750
+ * 真正全局的状态(服务不可用、helper 缺失)走 `computer/status`,不混进来。
1751
+ */
1752
+ state:
1753
+ | { owner: 'none'; status: 'idle'; conversationKey: string; runId: string }
1754
+ | { owner: 'agent'; status: 'running'; conversationKey: string; runId: string; action?: string; targetApp?: string }
1755
+ | { owner: 'user'; status: 'interactive'; conversationKey: string; runId: string }
1756
+ | {
1757
+ owner: 'user';
1758
+ status: 'waiting_human';
1759
+ conversationKey: string;
1760
+ runId: string;
1761
+ reason: PendingHumanInterventionSummary['reason'];
1762
+ ownerId: string;
1763
+ interventionId: string;
1764
+ resumeToken: string;
1765
+ sanitizedSummary: string;
1766
+ }
1767
+ | { owner: 'none'; status: 'error'; conversationKey: string; runId: string; message: string };
1768
+ }
1769
+ // 终端不走 WS:改由 Tauri 原生真 PTY 承载(server 帧无 terminal/*)。
1770
+ | { t: 'file/preview/opened'; requestId: string; ref?: ConversationFileRef; error?: string }
1771
+ | { t: 'file/browse/result'; requestId: string; listing: FileBrowserListing };
1772
+
1773
+ export interface CommandDescriptor {
1774
+ id: string;
1775
+ slash: string;
1776
+ title: string;
1777
+ description: string;
1778
+ category: 'context' | 'collaboration' | 'workflow' | 'schedule' | 'system';
1779
+ requiresWorkspace: boolean;
1780
+ available: boolean;
1781
+ unavailableReason?: string;
1782
+ argumentHint?: string;
1783
+ }
1784
+
1785
+ export type {
1786
+ AskAnswer,
1787
+ AskOption,
1788
+ AskQuestionSpec,
1789
+ AskSource,
1790
+ CronMissedRecord,
1791
+ CronRunRecord,
1792
+ CronTask,
1793
+ CronTaskDraft,
1794
+ CronTaskPatch,
1795
+ CronListFilter,
1796
+ LoopEvent,
1797
+ Message,
1798
+ ProgressStage,
1799
+ ToolCall,
1800
+ ToolResultMetadata,
1801
+ AgentResultMetadata,
1802
+ SubagentProgress,
1803
+ ToolProgressDetail,
1804
+ };