fix(core): preserve text attachments in context estimate

This commit is contained in:
Aiden Cline 2026-07-06 17:58:17 -05:00
commit ad550c544e
2 changed files with 14 additions and 29 deletions

View file

@ -84,23 +84,18 @@ const estimate = (value: unknown) => Token.estimate(JSON.stringify(value))
const textContext = (request: LLMRequest) => ({
system: request.system,
// TODO: Replace blanket attachment exclusion with model-aware media and file token accounting.
messages: request.messages
// Text attachments are lowered into dedicated marked messages; the original prompt is emitted separately.
.filter((message) => message.metadata?.attachment === undefined)
.map((message) => ({
id: message.id,
role: message.role,
content: message.content.flatMap((part) => {
if (part.type === "media") return []
if (part.type !== "tool-result" || part.result.type !== "content") return [part]
return [
{ ...part, result: { ...part.result, value: part.result.value.filter((item) => item.type === "text") } },
]
}),
metadata: message.metadata,
native: message.native,
})),
// TODO: Replace media exclusion with model-aware attachment token accounting.
messages: request.messages.map((message) => ({
id: message.id,
role: message.role,
content: message.content.flatMap((part) => {
if (part.type === "media") return []
if (part.type !== "tool-result" || part.result.type !== "content") return [part]
return [{ ...part, result: { ...part.result, value: part.result.value.filter((item) => item.type === "text") } }]
}),
metadata: message.metadata,
native: message.native,
})),
tools: request.tools,
})

View file

@ -72,7 +72,7 @@ test("compaction describes tool media without embedding base64", () => {
expect(serialized).not.toContain(base64)
})
it.effect("does not count file attachments as text context", () =>
it.effect("does not count image attachments as text context", () =>
Effect.gen(function* () {
requests = []
const compaction = yield* SessionCompaction.Service
@ -84,12 +84,6 @@ it.effect("does not count file attachments as text context", () =>
source: { type: "inline" },
name: "screenshot.png",
})
const document = FileAttachment.make({
data: Base64.make(Buffer.alloc(64 * 1024, "a").toString("base64")),
mime: "text/plain",
source: { type: "inline" },
name: "notes.txt",
})
const inputModel = Model.make({
id: "media-model",
provider: "test",
@ -110,7 +104,7 @@ it.effect("does not count file attachments as text context", () =>
id: SessionMessage.ID.create(),
type: "user",
text: "Inspect this image",
files: [document, image],
files: [image],
time: { created: DateTime.makeUnsafe(1) },
}),
]
@ -125,10 +119,6 @@ it.effect("does not count file attachments as text context", () =>
data,
filename: "screenshot.png",
})
expect(request.messages[1]?.content[0]).toMatchObject({
type: "text",
text: expect.stringContaining("Attached file: notes.txt"),
})
expect(
yield* compaction.compactIfNeeded({