Skip to content

fix(images): correct image media types that disagree with their bytes - #176

Open
ian-de-marcellus wants to merge 1 commit into
anima-research:mainfrom
ian-de-marcellus:fix/image-media-type-sniff
Open

ian-de-marcellus wants to merge 1 commit into
anima-research:mainfrom
ian-de-marcellus:fix/image-media-type-sniff

Conversation

@ian-de-marcellus

Copy link
Copy Markdown
Contributor

Problem. A resident's turns all started failing with a provider 400. The context held an image whose media_type said image/webp but whose bytes were a PNG; it arrived through a surface (Portal) that trusted the uploader's label. The API rejects any request where the label and bytes disagree, and the image stays in context, so every later turn failed the same way until an operator intervened.

Fix. src/image-media-type.ts sniffs the magic bytes (PNG, JPEG, GIF, WebP) of base64 image blocks. correctImageMediaTypes rewrites a disagreeing media type on the compiled messages (compileContext / compileWithInjections), including images nested in tool_result, before they go to the provider, and logs how many blocks it corrected. Unrecognized formats and non-base64 sources pass through untouched; stored history is never modified (new objects only for changed blocks).

Tests. test/image-media-type.test.ts: a PNG labeled image/webp is corrected, including inside tool_result, without mutating the input; correct and unknown images are returned as the same objects. Full suite: 956 pass / 0 fail.

(The surface side is being fixed separately in portal. This makes the framework robust to any surface that mislabels.)

🤖 Generated with Claude Code

A Discord attachment labelled image/webp whose bytes were PNG entered a
resident's history; the provider rejects the whole request on such a mismatch,
so every subsequent turn failed (Fable, 2026-09-24). Correct base64 image
blocks' mediaType from their magic bytes when context is compiled for a
request (including images nested in tool results). Stored history is not
modified; compiled messages get new objects only where something changed.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@greptile-apps

greptile-apps Bot commented Sep 28, 2026 •

Copy link
Copy Markdown

RetriggerConfidence Score: 4/5 Tier: apex

[Medium risk] Corrects mismatched image media types at compile time.

The PR should not merge until mislabeled images in live tool-result continuations are corrected.

Findings

  1. P1 Live tool images bypass correction ▶
Fix with agent prompt
### Issue 1
src/agent.ts:546
When an MCPL tool returns a PNG labeled `image/webp`, the framework passes the image directly to the existing stream for the next inference round. That round does not recompile the context, so this correction never runs on the tool result and the provider can still reject the request. Correct image blocks at the live continuation boundary too.

---

For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.

Summary

The PR adds magic-byte detection and corrects mislabeled base64 images in compiled agent messages without changing stored history.

  • The compiled-request path is covered, but native tool-result images supplied during an existing stream are not.
  • The new tests cover PNG correction but not the other three recognized formats.

Reviews (1) · Last reviewed commit: "fix(images): correct image media types t..."

Comment thread src/agent.ts
);
if (!budget) this.settleRuntimeSettingsTransition();
return result;
return { ...result, messages: correctImageMediaTypes(result.messages) };

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Live tool images bypass correction When an MCPL tool returns a PNG labeled image/webp, the framework passes the image directly to the existing stream for the next inference round. That round does not recompile the context, so this correction never runs on the tool result and the provider can still reject the request. Correct image blocks at the live continuation boundary too.

Prompt To Fix With AI
This is a comment left during a code review.
Path: src/agent.ts
Line: 546

Comment:
**Live tool images bypass correction** When an MCPL tool returns a PNG labeled `image/webp`, the framework passes the image directly to the existing stream for the next inference round. That round does not recompile the context, so this correction never runs on the tool result and the provider can still reject the request. Correct image blocks at the live continuation boundary too.

---

For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant