# AgentTeam Token 消耗诊断

> Canonical path：`specs/daemon/token-optimization.md`
> 范围：用最小本地证据链解释 AgentTeam 为什么比直接使用同一 runtime 消耗更多 Token，并指出 AgentTeam 可以优先优化的部分。
> 状态：已实现最小诊断契约。本文同时明确当前不支持的证据，避免把 launch 级归因误称为完整任务级因果分析。
> 相关规范：[Context 归因](./token-context-attribution.md)、[Run Usage 证据](./token-run-evidence.md)、[Token 对比](./token-comparison.md)、[Prompt Compiler Architecture](./prompt-compiler-architecture.md) 和 [AgentTeam Daemon](./daemon.md)。

## 1. 要解决的问题

用户观察到：通过 AgentTeam 使用 Codex、Claude Code 等 runtime 时，完成类似任务可能比直接使用相同 runtime 多消耗数倍 Token，但目前无法回答原因。

第一版只需要区分两类放大：

```text
总观测 input
    = root runtime input
    + unattributed usage

root runtime input
    = root 平均每次可识别 model invocation 的 input
    × root 可识别 model invocation 数
```

因此产品必须首先回答：

1. **Input size amplification**：AgentTeam 是否让每次 runtime input 更大？
2. **Invocation count amplification**：AgentTeam 是否触发了更多 model invocation、continuation 或 retry？

然后把 AgentTeam 装配的 Context 进一步拆成：

```text
AgentTeam-compiled Context
    = AgentTeam-controllable Context
    + required user/Workspace payload
    + unknown compiled Context
```

第一版的成功标准不是自动证明因果，也不是建立通用 Token observability 平台，而是让开发者能够用明确数据回答：

- 在 runtime 提供可信 invocation identity 时，主要成本来自更大的单次输入还是更多 model invocation；
- 哪些 AgentTeam semantic block 累计贡献最大；
- 哪些成本由 AgentTeam 直接控制或可通过无损装配优化；
- 修改一个候选点后，同一受控复现的 launch-level usage 是否下降。

当前可为提供 stable invocation identity 且能证明 usage 属于 root Process Context
的 runtime 回答 persistent Context exposure；其他 runtime 保持 `unsupported`，
不会用 turn 或 usage observation 数近似。

## 2. 产品边界

本产品优化 AgentTeam，不优化 runtime 内部实现。

### 2.1 Origin

每个 AgentTeam-compiled block 使用以下 `origin`：

| Origin | 含义 |
| --- | --- |
| `agentteam_policy` | AgentTeam 编写的行为、安全或协作契约。 |
| `agentteam_generated` | AgentTeam 生成的 catalog、reference、routing 或 protocol framing。 |
| `workspace_configuration` | Workspace 或 Agent 拥有、由 AgentTeam 装配的配置。 |
| `user_task_payload` | 用户消息、任务正文、任务约束或 requested evidence。 |
| `unknown` | 无法安全确认来源。 |

Runtime-native 和 provider-native 内容不属于 compiler block，只作为 runtime usage 与未归因差值观测。

### 2.2 Control

每个 block 同时使用以下 `control`：

| Control | AgentTeam 权限 |
| --- | --- |
| `direct` | AgentTeam 可以改变内容和注入策略。 |
| `assembly` | AgentTeam 只能改变选择、排序、去重、包装或生命周期，不能改变权威内容。 |
| `none` | AgentTeam 不能把该内容作为优化对象。 |
| `unknown` | 无法证明控制权。 |

只有 `direct` 和符合内容所有权约束的 `assembly` block 可以进入优化机会：

- `agentteam_policy` 和 AgentTeam 自行生成的 protocol/catalog 通常为 `direct`；
- `workspace_configuration` 只能为 `assembly`；
- `user_task_payload` 保留在完整 ledger 中，但不进入通用压缩榜单；
- 未知内容不能成为优化机会。

规范术语：

- **AgentTeam-compiled Context**：AgentTeam 在 runtime input boundary 装配的全部内容；
- **AgentTeam-controllable Context**：其中 `direct` 和符合条件的 `assembly` 子集；
- **Runtime-observed usage**：runtime/provider 报告的 input、cache 和 output；
- **Unattributed input**：runtime input 与可关联的 AgentTeam-compiled estimate 之间的差值；该差值不是 AgentTeam overhead，也不能进一步推断内容来源。

AgentTeam materialize 一个 block 的次数，不等于 provider 处理该 block 的次数。Session-persistent instruction 可能只由 AgentTeam 注入一次，却在后续多个 model invocation 中反复进入 runtime Context。证据充分时应分别报告：

- **Materialized estimate**：AgentTeam 实际装配和投递的 estimate；
- **Exposure estimate**：根据 block lifetime 和可信 invocation correlation，估算该 block 被 runtime 处理的累计 exposure。

当前实现对 OpenCode root `step-finish` 提供 exposure estimate；Codex、Claude 和
Kimi 保持 `unsupported` 或 `limited`。Kimi ACP 的 `usage_update` 只提供会话当前
Context 占用量和窗口大小，不提供可信 invocation identity。

## 3. 最小证据模型

第一版只有三个核心实体。

### 3.1 `AnalysisRun`

理想的任务级 `AnalysisRun` 表示一次显式有界的 AgentTeam 工作尝试。当前最小实现
先使用 runtime launch 作为 `Run` 聚合键，并明确标为 launch-level evidence：

- internal run ID；
- owning Agent；
- runtime 和 exact model；
- `root`；

当前不记录可信的任务 start/end、outcome 或 parent/child edge，也不声称 launch
就是用户任务。Runtime-native subagent、server/MaaS model call、retrieval/summarization
model call 和 child tree 不进入 complete total；无法关联的成本报告为
`unattributedInput` 或 `unsupported`。

不得通过 timestamp proximity、shared Session 或 inactivity window 合成 Run 或 parent-child edge。

### 3.2 `InputBoundary`

表示一次 AgentTeam 向 runtime materialize model-visible Context 的边界：

- launch-level run ID；
- event ID 和 event kind；
- optional turn/request correlation；
- complete semantic block ledger；
- AgentTeam-compiled estimate；
- AgentTeam-controllable estimate；
- required-payload estimate。

每个 block 还记录 model-visible lifetime：

- `boundary_only`：只属于当前 input boundary；
- `session_persistent`：从当前 boundary 起在同一 runtime Session 的后续 invocation 中持续有效；
- `until_replaced`：持续有效，直到 typed replacement boundary；
- `unknown`：无法安全推导 exposure。

当前 materialized attribution 覆盖：

- thread start/resume；
- wake/live delivery；
- steer；
- deferred、compaction 和 output-truncation continuation；
- final visible reply check；
- attachment 和 reference Context。

同一个 delivery retry、renderer mirror、inspect 或 cumulative snapshot 必须去重。

### 3.3 `UsageObservation`

表示一次 runtime/provider usage observation：

- launch-level run ID；
- optional unique model invocation ID；
- runtime；
- input；
- cache read；
- output。

只有存在 unique model invocation ID 时才能计算 invocation count 和 average input per invocation。Usage notification 数不能冒充 request 或 invocation 数。

第一版不要求单独输出 cache write、reasoning output、provider USD cost 或
runtime-native child tree。Runtime adapter 已可信提供这些 Token 时，可以把它们纳入
归一化的 inclusive input/output，但不得伪造独立字段或 child edge。

## 4. 必须输出的原因分解

`agentteam token analyze` 的首要结果不是 Session 列表，而是原因分解。

### 4.1 量级概览

报告 scope 与每个 launch-level Run 输出：

| 指标 | 含义 |
| --- | --- |
| Runtime cumulative input | 所有可信 usage delta 的 input 总和。 |
| Runtime cache read | 可用时的 cache-read 总和。 |
| Runtime output | output 总和。 |
| Usage observations | 纳入的 normalized usage observation 数，仅用于 data quality。 |
| Model invocations | 可通过 unique invocation ID 去重的模型调用数。 |
| Average input per invocation | cumulative input / model invocations；无法识别 invocation 时不可用。 |
| Root runtime input | root Run 的累计 input。 |
| AgentTeam-compiled materialized estimate | 所有去重 InputBoundary 的 compiler estimate 之和。 |
| AgentTeam-controllable materialized estimate | materialized estimate 中的 AgentTeam 可控子集。 |
| AgentTeam-controllable exposure estimate | 按 lifetime 和 invocation correlation 估算的累计可控 exposure。 |
| Required-payload materialized estimate | user/Workspace 必要 payload 子集。 |
| Unattributed usage | 已观测但不能可靠关联到支持范围内 Run/boundary 的 usage。 |

Compiler estimate 和 runtime counter 必须分栏展示，不能相加。

### 4.2 放大来源

没有 raw/control report 时，展示：

- root average input per model invocation；
- root model invocation count；
- AgentTeam-controllable materialized/exposure estimate；
- Top cumulative block contributions。

目标上存在可比 raw/control report 时可以额外计算以下比率；当前最小 comparison
尚未产出受控 benchmark fingerprint，因此只输出描述性 cumulative delta，不展示
input-size、invocation-count 或 overall amplification：

```text
inputSizeAmplification
  = AgentTeam average input per model invocation
    / control average input per model invocation

invocationCountAmplification
  = AgentTeam model invocations
    / control model invocations

overallObservedAmplification
  = AgentTeam total observed input / control total observed input
```

分母为零、数据缺失或 report 不可比时，对应值为 unavailable，不能显示为 `0×` 或 `1×`。

这些比率用于定位方向，不声称某个单一因素独立造成 overall amplification。尤其不能把三个比率机械相乘并称为精确因果分解。

### 4.3 Block 累计贡献

每个 semantic block 展示：

- origin/control；
- mean estimated tokens when injected；
- injection count；
- injection coverage；
- cumulative materialized estimate；
- cumulative exposure estimate；
- cumulative controllable exposure estimate；
- one code-controlled suggested action；
- required validation。

机会按以下值排序：

```text
cumulativeAddressableExposureEstimate
  = max(
      cumulativeControllableExposureEstimate
      - cumulativeTargetExposureEstimate,
      0
    )
```

Target 必须与 estimate 使用相同 scope。Registry 保存 per-injection target 时，必须使用同一 lifetime/exposure 规则计算 cumulative target。

完整 ledger 与 Top-N opportunity 必须分开；comparison 使用完整 ledger。

## 5. Runtime Usage 最小语义

当前报告只消费各 runtime 适配器已经归一化为 delta 的 usage event。跨 runtime 的
公共口径是：

- `input` 是 inclusive total input，包含 non-cached input、cache read 和
  cache creation/write；
- `cached input` 只表示 cache-read 子集；
- `output` 是 adapter 可验证的 total output；OpenCode 会把 reasoning 纳入 output；
- total Token 为 `input + output`，不得再次加上 cached input。

单独的 cache creation/write 和 reasoning 字段不是最小报告契约。新增或改变 runtime
usage 适配时必须验证：

- input 是否包含 cached input；
- cache read 是否是 input 的 subset；
- output 是否为累计值；
- usage event 是 delta 还是 cumulative；
- reset/replacement 如何识别；
- observation 对应 request、turn 还是 Session；
- 是否能够提供 unique model invocation identity。

规则：

- 当 input inclusive 且 cache read 是 subset 时，uncached input 可推导为 `input - cache read`；
- cache read 不能再次加到 inclusive input；
- missing field 是 `unsupported` 或 `no_data`，不是零；
- unknown runtime/version 为 `limited` 或 `unsupported`，不能继承未经验证的语义；
- 第一版的 primary observed metric 是 cumulative input；只有 runtime capability 可信时才额外展示 uncached input；
- invocation identity 不可用时，cumulative input 仍可用，但 input-size 与 invocation-count 分解必须标记 `unsupported`。

当前 capability：

- Codex 提供 `thread/tokenUsage/updated.last` delta；`turnId` 是 runtime turn，不是
  provider model-call identity；
- Claude 提供 top-level result usage，但没有可用于去重的 stable invocation ID；
- OpenCode 的每个 `step-finish` part 表示一次 model invocation，稳定 part ID 用于
  invocation identity 和重放去重；current-Runner root step 可关联 Process active
  Context，内部 compaction summary step 不套用 root Context；
- Kimi ACP 的 `usage_update` 只更新会话当前 Context 占用量和窗口大小；它不表示
  一次 provider invocation，也不用于推导 input/output token、调用次数或 exposure；
- provider cost 以及无法归一化的独立 cache/reasoning 分类不进入最小报告。

## 6. 命令与 UI

正式发行的 `agentteam` executable 提供：

```bash
agentteam token analyze
agentteam token compare
agentteam token ui
```

不提供 secondary binary、alias 或第二套 report builder。

### 6.1 Analyze

```bash
agentteam token analyze --window 1d
agentteam token analyze --run <run-ref> --format json
agentteam token analyze --agent <agent-ref> --format json
agentteam token analyze --output analysis.json
agentteam token analyze --stop
```

- 支持 `6h`、`12h`、`1d`/`24h`、`3d`、`1w`，输出统一规范化为 `1d`，默认 `1d`；
- Human daemon owner 默认看到所有 configured Agent，包括 `no_data` Agent；
- Agent caller 只能分析自身 Agent 和自身 Run，不支持 cross-Agent delegation；
- Human daemon owner 在采集关闭时执行普通 `analyze` 会自动开启本次 daemon
  lifetime 的详细诊断采集；该次输出明确说明采集不追溯历史，用户需要复现问题后再次分析；
- `--stop` 在生成当前报告后关闭详细诊断采集；
- `--stop` 不会为了生成报告而先开启已关闭的采集；
- Agent caller 只能读取，不能开启或关闭 machine-wide 采集；
- Agent report 用 `callerCanControl=false` 和
  `collection_enable_requires_human_owner` 明确提示：由 Human 在本机 Token UI
  开启，或从 Human shell 运行 analyze 后再复现；
- raw ID 不进入 CLI/local report，精确筛选使用 daemon-lifetime opaque ref；
- table 和 UI 首屏优先展示 §4 原因分解；
- run-scoped report 输出 `snapshotAt`、可信 launch `startedAt` 和
  `activeAtSnapshot`；导出冻结 point-in-time artifact，active 仅表示后续刷新可能增长；
- 受控 export 可以声明 `case`、唯一 `changed-variable`、Workspace revision、
  tool profile、cache state 和 outcome；
- JSON 使用 `agentteam-token-analysis/v2`；
- export 使用 owner-only permission。

### 6.2 Compare

`agentteam token compare` 使用 [Token 对比](./token-comparison.md) 定义的最小 comparability contract。第一版不自动启动 benchmark 或 raw runtime。

### 6.3 UI

`agentteam token ui` 手动启动本地界面，不进入 Desktop/Browser navigation、Machine tab 或 Settings。

UI 只需要：

- 顶部一个直接控制详细诊断采集的开关和当前状态；
- 时间窗口；
- 原因分解 overview；
- configured Agent 总量和按 input 排序的 launch-level Run 明细；
- cumulative block contribution table；
- Top opportunities；
- baseline/candidate comparison；
- data quality 和 no-data diagnosis；
- sanitized export/import。

第一版不需要：

- UI 内 Agent/Run 选择器；相应精确筛选由 CLI 提供；
- benchmark authoring；
- experiment registry；
- confidence interval；
- Human rubric；
- CI budget；
-长期 trend。

## 7. Daemon 与权限

Daemon 是唯一分析 owner：

- join Agent catalog、InputBoundary 和 UsageObservation；
-构建 report；
- CLI 和 UI 只做 adapter/presentation；
- Agent runtime 使用 daemon-owned compatible `agentteam` binary。

第一版 daemon 不可用时直接返回 `daemon_unavailable`。不实现 offline snapshot fallback。

权限：

- Human daemon owner：读取本机全部 Agent/Run；
- Agent：只读自身 Agent/Run；
-知道 opaque ref 不构成权限；
- Analysis credential 不能 stop、adopt、reconfigure 或控制 daemon；
- daemon owner/control capability 不得交给 Agent。

Agent 调用必须显式执行 `agentteam token analyze --format json`，不自动注入 Prompt，不注册为 MCP tool，也不实现为 `agentteam exec` action。

## 8. 采集、保留和隐私

产品专用高基数证据默认关闭。它不使用环境变量或普通 Desktop Settings：

- Human daemon owner 执行 `agentteam token analyze` 时自动开启；
- `agentteam token ui` 内的一个开关可以开启或关闭；
- `agentteam token analyze --stop` 在输出报告后关闭；
- 状态只属于当前 daemon lifetime；daemon 重启后恢复关闭；
- CLI 和 UI 调用 daemon-owned 同一开关，不存在第二套配置；
- Agent caller 永远不能改变该开关。

Desktop Machine Overview 中的 Token attribution 是另一条默认可用的低基数产品面：

- 它只回答某个 canonical tool/command 之后观测到多少 runtime usage；
- 它复用本规范的 inclusive input/cache/output 口径，但使用独立的
  `tokentracking.tsdb`、有限 label 和 Machine/Workspace 权限；
- 它不记录 launch/session/invocation ID，不提供 Prompt/Context ledger、Run
  分解或 comparison；
- `agentteam token` 不读取它来伪造 Run correlation；两者只共享 normalized usage event，
  不能重复计入同一个总量。

关闭时：

- 停止新的 InputBoundary、block 和 launch-level UsageObservation；
- 普通低基数 per-Agent runtime usage 继续按现有 metrics contract 记录；
- Context 和 Run analysis 为 `disabled`；
- 不提前删除 retention 内的历史证据。

任务级 AnalysisRun、parent edge 和 request/turn correlation 当前本来就不记录，
不能把开关描述成在控制尚不存在的数据面。

开启不追溯之前缺失的高基数证据。首次自动开启的 `analyze` 可以展示已有低基数
usage 和保留期内历史证据，但必须提示用户复现目标任务后再次分析。对于开启时仍
存活的 Process，daemon 会补记该 Process 已持有的、无正文的 launch Context ledger；
之前发生的 delivery 和 usage 不补录。

Raw high-cardinality evidence 最多保留七天，并设置：

- query sample bound；
- report ledger bound；
- import/export byte bound。

采集门控、写入失败或查询截断不能影响 Prompt compilation、delivery 或 runtime
execution；query/report truncation 必须显示为 `limited`。第一版复用已有七天
Desktop metrics TSDB，不增加第二套 store 或独立磁盘配额。

不得收集或输出：

- Prompt/user/task/tool/retrieval/transcript 正文；
- source ID、path、file、line、symbol、source map 或 code snippet；
- credential 或 secret；
- portable Agent/Run ref，以及 raw Agent、Session、launch、turn、request 或 machine ID。

Machine-local UI 可以显示 exact runtime/model、本地 Agent display name 和 daemon-lifetime opaque ref；portable export 删除 Agent/Run 明细，并把 exact runtime/model 转换为 comparability fingerprint。诊断所需信息不应因 portable privacy 规则而从本地 UI 消失。

## 9. 状态

Category state：

- `available`；
- `no_data`；
- `unsupported`；
- `limited`；
- `disabled`。

Missing value 为 `null` 或省略，不能使用 numeric zero 表示。

Diagnostic 使用有限 code registry，至少区分：

- no usage；
- no boundaries；
- invocation identity unsupported；
- exposure correlation unsupported；
- exposure correlation incomplete；
- truncated evidence；
- attribution disabled；
- usage correlation incomplete；
- run/ledger truncation。

## 10. 非目标

第一版不负责自动运行 benchmark/raw runtime、完整递归调用树、统计实验平台、CI/长期趋势、跨 Agent delegation、offline fallback 或 provider billing reconstruction。只有最小证据链证明某项能力是定位主要元凶的必要条件时，才通过 focused spec amendment 纳入。

## 11. 验证要求

当前最小实现必须验证：

- thread start、wake、delivery、steer 和 continuation boundary 均被记录且去重；
- origin/control 分类及 protocol framing/payload 拆分；
- 已支持 runtime 的 normalized delta 与 cache-read 语义；
- launch-level root usage 与 unattributed usage 分栏；
-累计原因分解、run 级 usage/context join 和完整 block ledger；
- opportunity 按 cumulative addressable estimate 排序；
- no-data/unsupported/limited/disabled 行为；
- Human 全局与 Agent self-only authorization；
- daemon unavailable fail-closed；
- local UI 与 portable export privacy 差异；
- bounded retention/query/report；
-普通 Desktop/Browser 中没有 navigation 或自动 Prompt injection。

当前明确不支持：

- 任务级 Run start/end、outcome 和 parent/child edge；
- Codex、Claude 和 Kimi 的调用次数及 invocation exposure；Kimi ACP 的
  `usage_update` 也不能冒充调用次数或 exposure；
- raw runtime benchmark 与自然流量的因果可比性。
