[P1/高] TokenEstimator estimateMessagesTokens 忽略 toolCall.name 和 toolCall.id #50

Open
opened 2026-07-21 21:56:15 +08:00 by thzxx · 0 comments
Owner

问题类型

缺陷 / 高 / Agent 引擎

文件位置

electron/harness/utils/token-estimator.ts

问题描述

estimateMessagesTokens 处理 assistant 消息时:

if (msg.toolCalls) {
  msg.toolCalls.forEach(tc => {
    total += estimateTextTokens(JSON.stringify(tc.args));
    // 忽略 tc.name 和 tc.id
  });
}

未计算 tc.name(工具名)和 tc.id(调用 ID)的 token。
实际上 OpenAI tokenizer 会将 tool_call 的完整结构(id、name、args)都计入 token。

影响

  • 估算偏低(每个 tool_call 少算 5-10 tokens)
  • 多轮工具调用下偏差累积

建议修复

if (msg.toolCalls) {
  msg.toolCalls.forEach(tc => {
    // id 通常 24 字符 (call_xxx)
    total += estimateTextTokens(tc.id ?? '');
    // name 通常 5-20 字符
    total += estimateTextTokens(tc.name ?? '');
    // args JSON
    total += estimateTextTokens(JSON.stringify(tc.args ?? {}));
    // 结构开销
    total += 8; // {"id":"","name":"","arguments":""} 等结构字符
  });
}

同时处理 tool 消息的 tool_call_id 字段。

## 问题类型 缺陷 / 高 / Agent 引擎 ## 文件位置 `electron/harness/utils/token-estimator.ts` ## 问题描述 estimateMessagesTokens 处理 assistant 消息时: ```ts if (msg.toolCalls) { msg.toolCalls.forEach(tc => { total += estimateTextTokens(JSON.stringify(tc.args)); // 忽略 tc.name 和 tc.id }); } ``` 未计算 `tc.name`(工具名)和 `tc.id`(调用 ID)的 token。 实际上 OpenAI tokenizer 会将 tool_call 的完整结构(id、name、args)都计入 token。 ## 影响 - 估算偏低(每个 tool_call 少算 5-10 tokens) - 多轮工具调用下偏差累积 ## 建议修复 ```ts if (msg.toolCalls) { msg.toolCalls.forEach(tc => { // id 通常 24 字符 (call_xxx) total += estimateTextTokens(tc.id ?? ''); // name 通常 5-20 字符 total += estimateTextTokens(tc.name ?? ''); // args JSON total += estimateTextTokens(JSON.stringify(tc.args ?? {})); // 结构开销 total += 8; // {"id":"","name":"","arguments":""} 等结构字符 }); } ``` 同时处理 tool 消息的 tool_call_id 字段。
thzxx added the Agent????? labels 2026-07-21 21:56:15 +08:00
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: MetonaTeam/metona-ai-desktop#50