anomalyco / anomalyco/opencode
fix(tui): Thai grapheme truncation splits Lo+Mn leaving orphan <0e31>
Nobody has claimed this yet.
- Dominant language
- TypeScript
- Stars
- 209k
- Forks
- 27.5k
- PR merge metrics
- PR metrics pending
Description
Bug
Thai TUI renders พลังภาษาไทยกำลังทดสอบ as พล<0e31>งภาษาไทยกำล<0e31>งทดสอบ in session titles and other truncated text (while Konsole renders correctly).
Root cause: packages/opencode/src/util/locale.ts truncate/truncateMiddle used str.length + str.slice (codepoints) instead of graphemes. Thai upper vowels/tone marks (e.g. ั U+0E31) are Mn width 0 and must stay attached to preceding Lo consonant as one grapheme cluster (ล U+0E25 + ั → ลั). Splitting them orphans ั which opentui escapes as <0e31>.
Example: พลัง is 4 codepoints but 3 graphemes. truncate(3) gave พล… instead of พลั….
Proposed fix: Use Intl.Segmenter({granularity:"grapheme"}) in locale.ts (same pattern already correct in prompt/display.ts). See PR #50001.
Repro: bun run /tmp/opencode/thai-fix/repro-buggy-vs-fixed.mjs
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start in packages/opencode/src/util/locale.ts and compare its truncate and truncateMiddle behavior with the grapheme handling in prompt/display.ts. Run bun run /tmp/opencode/thai-fix/repro-buggy-vs-fixed.mjs, then verify that truncation preserves Thai grapheme clusters and no longer emits orphan combining marks; PR #50001 shows related work already underway.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- typescript
- Domain
- cli
- Issue type
- Bug
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Activity status
- Stale
- Clarity
- Clearly specified
- Newbie friendliness
- 35/100