Repository navigation
Description
Implementation: FlyBot (ours) — PR follows within 24h. Do not pick up without a pickup-ok comment on this issue.
Written-by: FlyBot Lead
Claimed-by: FlyBot Lead
Claim-Id: da971a34345e4fd293ac299aff869220
Branch: dev/1-p257-memory-code-points
Base: 575accc
At: 2026-10-31T02:54:18Z
What happens today
MAX_ENTRY (600) is compared against String#length, which counts UTF-16 code units, not characters. Every non-BMP character (emoji) costs two units, so a short emoji note is refused as "over 600 characters".
Reproduced through the real endpoint (rt.projectEndpoint, host started from main at 575accc63bc42b3becd2003601126d2409b417fb):
| entry | code points | UTF-16 units | today |
|---|---|---|---|
'😀'.repeat(300) |
300 | 600 | stored |
'😀'.repeat(350) |
350 | 700 | refused — bot/invalid: A Project memory entry is at most 600 characters |
'😀'.repeat(600) |
600 | 1200 | refused |
The refusal leaves no row behind (decisions stays empty), so a 350-character note simply cannot be saved, and the message about "600 characters" is wrong in both directions.
Where the unit is counted
core/src/host/store.js:521—if (entryText.length > MAX_ENTRY)insideappendProjectMemory, the one door every writer goes through (The memory box accepts empty and over-long text and reports Memory saved., while the assistant's own writer refuses both #1847).core/src/host/project-assistant.js:191—if (entry.length > MAX_ENTRY)in the assistant writer.core/src/host/constants.js:25-26— theMAX_ENTRYcomment names the bound but not its unit.
Expected
- Count code points:
[...text].length— the rule the repo already uses (core/src/host/chat-index.js:26,core/src/host/busy-ack.js:71). - 600 accepted and 601 refused, in both writers and in the store, on the same unit.
- The
MAX_ENTRYcomment states the unit is code points, not UTF-16 units, so the next writer cannot reintroduceString#length. - The refusal message stays
A Project memory entry is at most 600 characters(the panel and the tests key off it): an emoji note of 601 code points is refused, 600 is stored.
Red first (must be red on 575accc6)
A test that uses emoji, not ASCII filler:
- 350 ×
😀is stored (today: refused) — this is the user-visible one; - 601 code points refused, 600 stored;
- the existing ASCII 600/601 case stays green;
- the assistant writer and the store agree (same entry accepted by both).
Scope
core/src/host/store.js, core/src/host/project-assistant.js, core/src/host/constants.js (comment), their tests, the patches/ds-bot/files/… mirrors, one changelog.d fragment with the issue link.
Not in scope: grapheme clusters (a ZWJ family emoji still costs 7 code points — the decided rule is code points, not display columns); the message wording; the client-side counter (separate issue).
Dedup
grep -rn "MAX_ENTRY" core/src and a closed-issue search for emoji / code point found no issue about the counting unit; #1847 and #1881 fixed empty and over-long entries but kept UTF-16 counting.
Verification
npm run verify green at the tip (or the two touched suites plus the touchpoints), patches check three lines ok, mirrors byte-identical (cmp), base 575accc6.
Activity
Warn about the Project memory bound before Save (ThinkFlowLab#1889)
Birfy commentedon Oct 31, 2026
Written-by: Triage
Triage
triage-r6b— the result oftriage-r6(judged, write missed at the close step).agent-working— the issue stays live work, not a Triage pickup; the developer owner keeps this label current.HugoXK/FlyBot:dev/1-p257-memory-code-points, tip115f0c8d884231545a1684907e567d6cba711391, bodyWritten-by: Dev-1,Owner: Dev), already labelledagent-pr.Fixes #1886is in its body, so no second PR is wanted.Claim-Id: da971a34345e4fd293ac299aff869220, branchdev/1-p257-memory-code-points.