Skip to content

fix(feishu): recover Chinese filenames from Latin-1 mojibake in Content-Disposition#1059

Open
BingqingLyu wants to merge 2 commits into
mainfrom
fork-pr-50435-fix-feishu-chinese-filename-encoding
Open

fix(feishu): recover Chinese filenames from Latin-1 mojibake in Content-Disposition#1059
BingqingLyu wants to merge 2 commits into
mainfrom
fork-pr-50435-fix-feishu-chinese-filename-encoding

Conversation

@BingqingLyu

@BingqingLyu BingqingLyu commented Apr 27, 2026

Copy link
Copy Markdown
Owner

Summary

  • Problem: When receiving files via Feishu with Chinese characters in the filename (e.g. "何不同舟渡_2.txt"), the saved filename is garbled (e.g. "æµ_è_æ_ä_2.txt"). This is a classic UTF-8 → Latin-1 mojibake.
  • Root cause: Node.js HTTP parser decodes header values as ISO-8859-1 per RFC 7230. When Feishu returns Content-Disposition: attachment; filename="何不同舟渡_2.txt" using the plain filename parameter (without RFC 5987 filename*=UTF-8'...), each 3-byte UTF-8 Chinese character becomes 3 separate Latin-1 characters.
  • Fix: Add tryRecoverLatin1AsUtf8() which detects the mojibake pattern (all chars in U+0000–U+00FF range, contains non-ASCII) and reconstructs the original UTF-8 string. The recovery is safely skipped for pure ASCII strings and strings with genuine non-Latin-1 Unicode characters.

Change Type

  • Bug fix

Scope

  • Feishu/Lark channel

Linked Issue

User-visible / Behavior Changes

Before: File "何不同舟渡_2.txt" → saved as "æµ_è_æ_ä_2---uuid.txt"

After: File "何不同舟渡_2.txt" → saved as "何不同舟渡_2---uuid.txt"

Security Impact

None. Pure string transformation with no external I/O.

Evidence

  • 32 tests passing (30 existing + 2 new filename recovery tests)
✓ recovers Chinese filenames from Latin-1 mojibake in Content-Disposition
✓ preserves ASCII filenames without modification

Compatibility

  • Backward compatible. ASCII filenames are unchanged (fast path).
  • The filename*=UTF-8'... path (already correct) is tried first.

Risks

Minimal. The recovery only fires when ALL characters are in the Latin-1 range AND the bytes form valid UTF-8. If the bytes are not valid UTF-8, the original string is returned unchanged.

[AI-assisted development by OpenClaw agent 虾干 🦐]

lishuai added 2 commits March 30, 2026 11:00
…nt-Disposition

Node.js HTTP parser decodes header values as ISO-8859-1 (per RFC 7230).
When Feishu returns a Content-Disposition header with a UTF-8 filename
in the plain `filename` parameter (without `filename*=UTF-8'...`),
each multibyte UTF-8 character becomes multiple Latin-1 code points,
producing garbled names like "æµ_è_æ_ä_2.txt" instead of "何不同舟渡_2.txt".

Add tryRecoverLatin1AsUtf8() which detects the mojibake pattern (all
chars in U+0000–U+00FF range) and attempts to reconstruct the original
UTF-8 string from the byte values. The recovery is skipped for pure
ASCII strings (fast path) and strings that already contain non-Latin-1
characters.

Closes openclaw#48388
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.

[Bug]: Feishu file names with Chinese characters are garbled (UTF-8 encoding issue)

1 participant