mirror of
https://github.com/getcompanion-ai/co-mono.git
synced 2026-04-16 19:04:37 +00:00
fix(coding-agent): show unknown context usage after compaction, fix multi-compaction boundary
After compaction, context token count is unknown until the next LLM response. Instead of showing stale pre-compaction values or heuristic estimates, the footer now shows ?/200k. ContextUsage.tokens and ContextUsage.percent are now number | null (breaking change). Removed usageTokens, trailingTokens, lastUsageIndex from ContextUsage (internal details). Also fixed _checkCompaction() using .find() (first compaction) instead of getLatestCompactionEntry() (latest), which caused incorrect overflow detection with multiple compactions. Closes #1382
This commit is contained in:
parent
1e88c5e463
commit
7eb969ddb1
5 changed files with 56 additions and 29 deletions
|
|
@ -68,6 +68,7 @@ import type { ModelRegistry } from "./model-registry.js";
|
|||
import { expandPromptTemplate, type PromptTemplate } from "./prompt-templates.js";
|
||||
import type { ResourceExtensionPaths, ResourceLoader } from "./resource-loader.js";
|
||||
import type { BranchSummaryEntry, CompactionEntry, SessionManager } from "./session-manager.js";
|
||||
import { getLatestCompactionEntry } from "./session-manager.js";
|
||||
import type { SettingsManager } from "./settings-manager.js";
|
||||
import { BUILTIN_SLASH_COMMANDS, type SlashCommandInfo, type SlashCommandLocation } from "./slash-commands.js";
|
||||
import { buildSystemPrompt } from "./system-prompt.js";
|
||||
|
|
@ -1531,9 +1532,9 @@ export class AgentSession {
|
|||
// The error shouldn't trigger another compaction since we already compacted.
|
||||
// Example: opus fails → switch to codex → compact → switch back to opus → opus error
|
||||
// is still in context but shouldn't trigger compaction again.
|
||||
const compactionEntry = this.sessionManager.getBranch().find((e) => e.type === "compaction");
|
||||
const compactionEntry = getLatestCompactionEntry(this.sessionManager.getBranch());
|
||||
const errorIsFromBeforeCompaction =
|
||||
compactionEntry && assistantMessage.timestamp < new Date(compactionEntry.timestamp).getTime();
|
||||
compactionEntry !== null && assistantMessage.timestamp < new Date(compactionEntry.timestamp).getTime();
|
||||
|
||||
// Case 1: Overflow - LLM returned context overflow error
|
||||
if (sameModel && !errorIsFromBeforeCompaction && isContextOverflow(assistantMessage, contextWindow)) {
|
||||
|
|
@ -2697,6 +2698,35 @@ export class AgentSession {
|
|||
const contextWindow = model.contextWindow ?? 0;
|
||||
if (contextWindow <= 0) return undefined;
|
||||
|
||||
// After compaction, the last assistant usage reflects pre-compaction context size.
|
||||
// We can only trust usage from an assistant that responded after the latest compaction.
|
||||
// If no such assistant exists, context token count is unknown until the next LLM response.
|
||||
const branchEntries = this.sessionManager.getBranch();
|
||||
const latestCompaction = getLatestCompactionEntry(branchEntries);
|
||||
|
||||
if (latestCompaction) {
|
||||
// Check if there's a valid assistant usage after the compaction boundary
|
||||
const compactionIndex = branchEntries.lastIndexOf(latestCompaction);
|
||||
let hasPostCompactionUsage = false;
|
||||
for (let i = branchEntries.length - 1; i > compactionIndex; i--) {
|
||||
const entry = branchEntries[i];
|
||||
if (entry.type === "message" && entry.message.role === "assistant") {
|
||||
const assistant = entry.message;
|
||||
if (assistant.stopReason !== "aborted" && assistant.stopReason !== "error") {
|
||||
const contextTokens = calculateContextTokens(assistant.usage);
|
||||
if (contextTokens > 0) {
|
||||
hasPostCompactionUsage = true;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!hasPostCompactionUsage) {
|
||||
return { tokens: null, contextWindow, percent: null };
|
||||
}
|
||||
}
|
||||
|
||||
const estimate = estimateContextTokens(this.messages);
|
||||
const percent = (estimate.tokens / contextWindow) * 100;
|
||||
|
||||
|
|
@ -2704,9 +2734,6 @@ export class AgentSession {
|
|||
tokens: estimate.tokens,
|
||||
contextWindow,
|
||||
percent,
|
||||
usageTokens: estimate.usageTokens,
|
||||
trailingTokens: estimate.trailingTokens,
|
||||
lastUsageIndex: estimate.lastUsageIndex,
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue