openclaw - 💡(How to fix) Fix [Bug]: WebChat: user-uploaded images vanish from bubble after assistant reply (chat.history projection hard-deletes image.data; MediaPath never linked to sidecar) [1 comments, 2 participants]

Official PRs (…)
ON THIS PAGE

Recommended Tools

×6

Utilities matched from this issue’s tags and category — try them while you read without losing context.

GitHub issue graph ai analysis

Paste a GitHub issue URL. We fetch that issue, discover linked issues from bodies/comments/timeline, collect linked pull requests, and produce a structured English report.

The report is written in English Markdown for sharing and archival.

Helpful · Quick feedback

Loading…
GitHub stats
openclaw/openclaw#81285Fetched 2026-05-14 03:33:41
View on GitHub
Comments
1
Participants
2
Timeline
4
Reactions
2
Author
Timeline (top)
labeled ×2closed ×1commented ×1

When a user uploads an image (paste / drag / file picker) into WebChat, it renders in the optimistic local bubble and the model receives it correctly, but the image disappears from the user bubble the moment the assistant reply lands — not on page refresh, the same turn. The image file is still persisted at ~/.openclaw/media/inbound/<uuid>.png, but the transcript user message has no MediaPath linking back, so the UI has nothing to render once chat.history reloads.

Root Cause

Root cause traced through gateway dist:

Fix Action

Fix / Workaround

Frequency: 100% reproducible. Workaround: save the image to a workspace path and paste the path as text instead of pasting the image bytes.

Code Example



---

return extractTranscriptUserText(message.content) === params.message;

---

if (type === "image" && typeof entry.data === "string") {
  const bytes = Buffer.byteLength(entry.data, "utf8");
  delete entry.data;
  entry.omitted = true;
  entry.bytes = bytes;
}
RAW_BUFFERClick to expand / collapse

Bug type

Regression (worked before, now fails)

Beta release blocker

No

Summary

When a user uploads an image (paste / drag / file picker) into WebChat, it renders in the optimistic local bubble and the model receives it correctly, but the image disappears from the user bubble the moment the assistant reply lands — not on page refresh, the same turn. The image file is still persisted at ~/.openclaw/media/inbound/<uuid>.png, but the transcript user message has no MediaPath linking back, so the UI has nothing to render once chat.history reloads.

Steps to reproduce

  1. Open WebChat (Control UI) on a recent OpenClaw build.
  2. In a chat, paste or drop an image into the composer with a short prompt like "analyze this image".
  3. Send.
  4. Wait for the assistant reply to stream and complete.

Expected behavior

Image stays in the user bubble across the assistant reply, page refresh, and session reloads — identical to how assistant-generated images persist via managed media URLs.

Actual behavior

The image vanishes from the user bubble the instant the assistant reply completes and the Control UI merges chat.history. Only the text portion of the user message remains. The image file is still on disk at ~/.openclaw/media/inbound/<uuid>.png, just not linked from the transcript entry.

OpenClaw version

2026.5.7

Operating system

macOS 25.5.0 (arm64, Apple M4 Pro 24GB)

Install method

npm global

Model

anthropic/claude-opus-4-7

Provider / routing chain

direct anthropic (no proxy)

Additional provider/model setup details

Direct chat session, agent=main, Opus 4.7. No special config. Reproduces on a fresh install with no plugins.

Logs, screenshots, and evidence

Impact and severity

Severity: medium-high. Image-driven conversations (screenshots, photos, diagrams) lose their visual context the moment the assistant replies, breaking the "scroll up to see what I asked" model.

Asymmetry: assistant-generated images persist correctly via managed media URLs — only user-uploaded images are affected. This makes the loss feel like a bug rather than a deliberate design choice.

Frequency: 100% reproducible. Workaround: save the image to a workspace path and paste the path as text instead of pasting the image bytes.

Additional information

Root cause traced through gateway dist:

Issue 1rewriteChatSendUserTurnMediaPaths (in chat-3xUbD00m.js) matches the target transcript entry by strict text equality:

return extractTranscriptUserText(message.content) === params.message;

But params.message is the raw parsedMessage (before timestamp injection), while the transcript content has the inbound timestamp prefix prepended via injectTimestamp(messageForAgent, timestampOptsFromConfig(cfg)). Example: transcript stores [Wed 2026-05-13 12:11 GMT+8] analyze this image, but params.message is analyze this image. Match always fails → target is undefined → MediaPath/MediaPaths are never written onto the user transcript entry. Confirmed against a live session JSONL: the user msg has only top-level keys ['role', 'content', 'timestamp'] despite the sidecar PNG existing.

Issue 2chat-display-projection-S_bLdIwq.js (~line 79–86) unconditionally strips image base64 with no URL fallback:

if (type === "image" && typeof entry.data === "string") {
  const bytes = Buffer.byteLength(entry.data, "utf8");
  delete entry.data;
  entry.omitted = true;
  entry.bytes = bytes;
}

Combined with Issue 1, the UI receives { type: "image", omitted: true, bytes: N } with no way to recover the image.

Suggested fix — Option A (root cause): make rewriteChatSendUserTurnMediaPaths ignore the timestamp prefix when comparing, or match by entry id / timestamp / recently-emitted user transcript entry instead of strict text equality.

Suggested fix — Option B (defense in depth): in chat-display-projection, when stripping entry.data, attempt to substitute back an authenticated managed media URL from MediaPath/MediaPaths sibling fields (or by timestamp-window match against media/inbound/).

Note for triagers: sharp is a red herring. The Optional dependency sharp is required for image attachment processing warning comes from the media-understanding pipeline (extensions/media-understanding-core/image-ops.js), not from chat send / transcript / display projection. Installing sharp does NOT fix this bug.

Vote matrix · Quick signals

Works
Did the solution work? Tap to confirm.
Easy Fix
Was it a quick fix?
Time Saver
Did it save you time?
Blocking
Was it severely blocking?
Common Issue
Are others likely hitting this too?
Flaky / Intermittent
Is it intermittent?
Verified / Reproducible
Can you reproduce it reliably?
Loading…

FAQ

Expected behavior

Image stays in the user bubble across the assistant reply, page refresh, and session reloads — identical to how assistant-generated images persist via managed media URLs.

Still need to ship something?

×6

Another batch ranked right after the header list — different links, same matching logic.

Back to top recommendations

TRENDING

openclaw - 💡(How to fix) Fix [Bug]: WebChat: user-uploaded images vanish from bubble after assistant reply (chat.history projection hard-deletes image.data; MediaPath never linked to sidecar) [1 comments, 2 participants]