diff --git a/mateclaw-server/src/main/resources/docs/en/agents.md b/mateclaw-server/src/main/resources/docs/en/agents.md index 699b260f..5a45ac63 100644 --- a/mateclaw-server/src/main/resources/docs/en/agents.md +++ b/mateclaw-server/src/main/resources/docs/en/agents.md @@ -123,6 +123,33 @@ Three delegation tools, one per cadence: - **`delegateParallel`** — fan out. Delegate to several children at once; each runs in its own isolated session and the results are collected together. - **`delegateAsync`** — background. Returns a `task_id` immediately while the child runs in the background; fetch the result later with **`taskOutput`**. Background runs have a bounded execution budget (default 3600 seconds, configurable with `mateclaw.delegation.async-timeout-seconds`, or per call with `timeoutSeconds`, max 86400). On timeout MateClaw stops the child session and persists a failed result instead of leaving an orphan run. `taskOutput` has an **attribution gate** — only the **same conversation + the same user** that spawned the task can read its result, preventing cross-conversation / cross-user leakage. +#### Async long tasks: scheduling, polling, and acceptance + +`delegateAsync` uses the shared async-task pool. A user can currently run at most **3** async tasks at once; delegation, image, video, and other async workloads share that allowance. For a batch, start at most three tasks, poll until one reaches a terminal state, and then refill the free slot. A call rejected by the concurrency limit returns no `task_id` and must not be counted as started. + +`taskOutput` parameters and response semantics: + +| Field | Meaning | +|---|---| +| `taskId` | Required; pass the `task_id` returned by `delegateAsync` | +| `block` | Optional, default `false`; when `true`, wait for a terminal state within this call | +| `timeoutSeconds` | Controls only one blocking poll, default 30 seconds and max 120; it does not change the child's execution budget | +| `status` | `pending` / `running` / `succeeded` / `failed` | +| `progress` | Lifecycle progress; local delegation currently usually stays at 0 while running and becomes 100 at termination, so it is not content-completion percentage | +| `duration_ms` | Wall-clock duration, returned only for a terminal task | + +::: warning `succeeded` does not mean the deliverable passed acceptance +`succeeded` only means that the child did not finish with a runtime exception or timeout. A model may return only an outline, a required tool may have failed, or a quantitative target may be missed while the task still becomes `succeeded`. The parent must verify business evidence before aggregating the result or completing a goal. +::: + +Use at least these acceptance gates: + +1. Required files, links, or structured results actually exist and are readable; do not rely only on a claim that they were generated. +2. Word, chapter, scenario, and similar quantitative targets have reproducible counts. +3. No plan or checklist items remain, and the final answer contains no “continue later” or “remaining work” declaration. +4. Critical write, read, and execution tools succeeded; if content was returned inline after an artifact failure, record that fallback explicitly. +5. Put this evidence into the [goal checklist](./goals), and complete the goal only when every criterion passes. + Children deny a default set of tools so the tree can't run away: - `delegateToAgent` / `delegateParallel` / `listAvailableAgents` (recursion guard — children can't launch their own synchronous/parallel delegations and can't enumerate sibling agents) diff --git a/mateclaw-server/src/main/resources/docs/en/chat.md b/mateclaw-server/src/main/resources/docs/en/chat.md index 2ded2226..2113509b 100644 --- a/mateclaw-server/src/main/resources/docs/en/chat.md +++ b/mateclaw-server/src/main/resources/docs/en/chat.md @@ -49,6 +49,10 @@ Long tasks (multi-step plans, multi-agent collaboration) used to mean scrolling The rail **collapses to a badged strip**; below 1280px it degrades to a **floating drawer** so it never squeezes the conversation column. It's pure frontend with zero new endpoints, reusing the existing SSE event stream — so the delegation tree still appears inline in the message too; the rail just lifts the "current / active" overview into a persistent place. +::: tip Observing long tasks +Run Overview is a live projection of SSE events, not the authoritative async-task store. After a refresh, reconnect, or for a background delegation started earlier, a child may be temporarily absent from the tree; confirm terminal state with `taskOutput(taskId)` from the spawning conversation. Running `progress` may also remain at 0 and jump directly to 100 at termination, so use tool calls, plan checklists, and final artifacts to judge actual completion. +::: + --- ## Thinking, tool calls, and what to trust diff --git a/mateclaw-server/src/main/resources/docs/en/goals.md b/mateclaw-server/src/main/resources/docs/en/goals.md index 86bb5802..0bc7b2e6 100644 --- a/mateclaw-server/src/main/resources/docs/en/goals.md +++ b/mateclaw-server/src/main/resources/docs/en/goals.md @@ -179,6 +179,10 @@ Both modes use **structured output** — the evaluator returns a typed object (c **Completion is deterministic.** Only when **every criterion passes** is the goal done. 19 of 20 passed (a 0.95 score) is still "continue" — miss one and one is missing, no fuzzy threshold. +::: warning Verify deliverable evidence for long tasks +An async child task's `status=succeeded` and `progress=100` are lifecycle terminal signals, not evidence that a criterion passed. For files, long-form writing, test cases, and similar deliverables, make criteria reproducible: for example, “the target file exists and can be read back,” “body text contains at least N characters,” or “at least N independent scenarios can be enumerated.” If a write or execution tool failed, only an outline was produced, or work remains pending, keep that criterion unpassed. +::: + **Three ways to add a checklist:** - **At creation** — pass `criteria: ["DNS resolves", "SSL valid", "tests green"]` to the `setGoal` tool, or `criteria` to `POST /api/v1/goals`. Skips the bootstrap round. diff --git a/mateclaw-server/src/main/resources/docs/zh/agents.md b/mateclaw-server/src/main/resources/docs/zh/agents.md index 17752614..17d9fb7f 100644 --- a/mateclaw-server/src/main/resources/docs/zh/agents.md +++ b/mateclaw-server/src/main/resources/docs/zh/agents.md @@ -123,6 +123,33 @@ head: - **`delegateParallel`** —— 扇出委派。同时派给多个子员工,各自在隔离会话里跑,结果统一收集回来。 - **`delegateAsync`** —— 后台委派。立刻返回一个 `task_id`,子员工在后台跑;之后用 **`taskOutput`** 取结果。后台任务默认有 3600 秒执行预算,可通过 `mateclaw.delegation.async-timeout-seconds` 配置,或在单次调用中用 `timeoutSeconds` 调整(最大 86400 秒);超时后 MateClaw 会停止子会话并持久化失败结果,避免遗留孤儿任务。`taskOutput` 带**归属闸门**——只有最初发起委派的**同一个会话 + 同一个用户**才能读到结果,防止跨会话/跨用户泄露。 +#### 异步长任务:调度、轮询与验收 + +`delegateAsync` 走通用异步任务池。当前每个用户最多同时运行 **3 个**异步任务,这个额度由委派、图片、视频等异步任务共享。批量任务应按“最多启动 3 个 → 轮询到至少一个终态 → 再补位”的方式滚动执行;触发并发上限的调用不会返回 `task_id`,不能把它计入已启动任务。 + +`taskOutput` 的参数与返回语义: + +| 项 | 语义 | +|---|---| +| `taskId` | 必填,使用 `delegateAsync` 返回的 `task_id` | +| `block` | 可选,默认 `false`;设为 `true` 时在本次调用里等待终态 | +| `timeoutSeconds` | 只控制一次阻塞轮询,默认 30 秒、最大 120 秒;不改变子任务的执行预算 | +| `status` | `pending` / `running` / `succeeded` / `failed` | +| `progress` | 运行态的生命周期进度;本地委派目前通常保持 0,终态变为 100,不代表内容完成百分比 | +| `duration_ms` | 仅终态返回的墙钟耗时 | + +::: warning `succeeded` 不等于交付验收通过 +`succeeded` 只表示子任务没有以运行时异常或超时结束。模型可能只返回提纲、工具调用可能失败、目标字数可能未达到,任务仍会进入 `succeeded`。父员工在汇总或完成目标前,必须再次检查业务证据。 +::: + +建议至少设置以下验收门禁: + +1. 要求的文件、链接或结构化结果真实存在并且可读;不要只相信回答中的“已生成”。 +2. 字数、章节数、场景数等量化要求有可复核计数。 +3. 计划或清单没有待办项,最终回答没有“后续继续”“其余待补”等未完成声明。 +4. 关键写入、读取、执行工具没有失败;若工具失败后改为正文交付,要明确记录降级方式。 +5. 父员工把上述证据写进[目标清单](./goals),只有全部准则通过后才完成目标。 + 子员工默认被拒绝一组工具,保证树不失控: - `delegateToAgent` / `delegateParallel` / `listAvailableAgents`(递归护栏——子员工不能再发起同步/并行委派,也不能枚举兄弟员工) diff --git a/mateclaw-server/src/main/resources/docs/zh/chat.md b/mateclaw-server/src/main/resources/docs/zh/chat.md index e2774b41..402c84e4 100644 --- a/mateclaw-server/src/main/resources/docs/zh/chat.md +++ b/mateclaw-server/src/main/resources/docs/zh/chat.md @@ -49,6 +49,10 @@ Segment 是**渐进到达**的。每个 segment 一落盘就立刻持久化到 侧栏可**折叠为带角标的竖条**;窄屏(< 1280px)自动降级为**浮层抽屉**,不挤占对话区。它纯前端实现、零新增接口,完全复用现有 SSE 事件流——所以委派树也仍会内联在消息里,侧栏只是把「当前 / 活跃」的总览拎出来常驻。 +::: tip 长任务观测建议 +运行总览是 SSE 事件的实时投影,不是异步任务记录的权威查询面。刷新、重连或较早启动的后台委派可能暂时不在子 Agent 树中;需要确认终态时,仍以发起会话里的 `taskOutput(taskId)` 为准。运行态 `progress` 也可能保持 0 到终态后直接变成 100,请结合工具调用、计划清单和最终工件判断真实完成度。 +::: + --- ## 思考、工具调用、以及"该不该信" diff --git a/mateclaw-server/src/main/resources/docs/zh/goals.md b/mateclaw-server/src/main/resources/docs/zh/goals.md index 654020f3..a8f1f468 100644 --- a/mateclaw-server/src/main/resources/docs/zh/goals.md +++ b/mateclaw-server/src/main/resources/docs/zh/goals.md @@ -177,6 +177,10 @@ Plan-Execute 模式下,单个步骤可能**抛异常**,也可能陷入**停 **完成判定是确定性的。** 只有当**每一条准则都通过**,才判完成。20 条里过了 19 条(0.95 分)依然是"继续"——差一条就还差一条,没有模糊阈值。 +::: warning 长任务要验证交付证据 +异步子任务的 `status=succeeded`、`progress=100` 只是运行生命周期终态,不能直接作为准则通过的证据。对文件、长文、测试场景等交付,准则应写成可复核形式,例如“目标文件存在且回读成功”“正文字符数不少于 N”“至少有 N 条独立场景并可枚举”。若写文件或执行工具失败、只生成了提纲、仍有待办项,对应准则必须保持未通过。 +::: + **怎么给目标加清单——三种途径:** - **创建时直接带**——`setGoal` 工具传 `criteria: ["DNS 解析正确", "SSL 有效", "测试全绿"]`,或 `POST /api/v1/goals` 传 `criteria`。省去 bootstrap 那一轮。