GeezerVisonThe World Wide Web, restored to 800 pixels of glory. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Home|About|Gaming cabinet|Archives|How it works|Starter sites | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
GeezerVison is showing github.com — v0.0.14-beta.1 (1/5): Claude Code's automatic compaction keeps the user's language by Obed0101 · Pull Request #137 · MendCode/MendCode Conversation
|
|
MendCode: @Obed0101's MendCode worked on this pull request on one of its devices; released 2026-11-10 21:04 UTC. |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
1 finding · 🟡 1 minor
head df2d2c14ec15
Merge risk: 🟡 Medium · The change affects prompt-hook completion, temporary-file persistence, and settings passed to every language-enabled Claude process. Regressions could delay prompt submission or silently leave automatic compaction using the wrong language, and the added test does not exercise Claude Code's consumption of the hook output.
Change: Bug fix · Review effort: 2/5, about 15 minutes
The change persists each Claude session's reply-language instruction and registers an automatic-compaction hook that prints it, with a regression test and changelog entry. Risk is medium because this adds filesystem work to prompt handling and relies on Claude Code's hook behavior; the new test also has a timing race. This review was read-only, so tests were not run and actual summary-language behavior was not verified.
Readers: 3 code files no reader could read went to the review pass whole (the diff is small: one reader call costs more than the readers' share of this review's cap, so the review pass reads it).
| Finding | Where | |
|---|---|---|
| 🟡 | Wait for the hook response instead of completing the turn after 5 ms 5/10 | packages/engine-claude/test/engine.test.ts:2221 |
The Claude engine now saves the language instruction returned by its existing UserPromptSubmit callback in a per-session temporary file. Each Claude process receives a PreCompact command hook, restricted to automatic compaction, that prints this file. The implementation caches previously written instructions to avoid unchanged writes within an engine instance; manual compaction and other engines remain unchanged.
Changes
| Layer / files | Summary |
|---|---|
Claude language persistence and hook registration packages/engine-claude/src/engine.ts |
Adds configurable temporary-file storage, a bounded instruction cache, and an automatic PreCompact command hook merged into Claude process settings. |
Regression coverage packages/engine-claude/test/engine.test.ts |
Adds a fake-engine test that checks the hook matcher, executes its shell command, and verifies the stored Spanish-language instruction. |
Release documentation CHANGELOG.md |
Documents preservation of the user's language during Claude Code's automatic compaction. |
Sequence diagram
sequenceDiagram
participant C as Claude Code
participant E as Claude engine
participant L as Reply-language callback
participant F as Session language file
C->>E: UserPromptSubmit callback
E->>L: Resolve session language
L-->>E: Language instruction
opt Instruction changed or not cached
E->>F: Write summary-language instruction
end
E-->>C: UserPromptSubmit additionalContext
C->>F: Automatic PreCompact command reads file
F-->>C: Instruction on hook stdout
| Check | Status | Explanation |
|---|---|---|
| Title | ✅ Passed | The title accurately identifies the intended automatic-compaction language fix and its position in the release stack. |
| Description | The description explains the intended behavior, motivation, implementation cost, and reported checks. However, the full-suite result is from the top of the stack, and the added test verifies command output rather than whether Claude Code uses it to write its compaction summary. | |
| Out of scope | ✅ Passed | All three changed files directly support the stated language-preservation fix through implementation, coverage, or release documentation. |
Performance (perf-attrib, base 8cf83cc against head df2d2c1)
perf-attrib: nota: no total rose; inside, tui.ready.heap.extra_b +480406B; tui.ready.heap.size_b +569270B; tui.ready.heap.objects +840; lower: tui.after.heap.protected -1
base 8cf83cc4c0161ab2fbd9d7f2fc70b84d202f805b (8cf83cc4) vs cand df2d2c14ec159b6dd81d6150242fc528e155e3eb (df2d2c14), median of 2 faux-engine session(s) per side; flagged = beyond the noise measured on 18 base-vs-base runs (x1.5).
| metric | base | cand | diff |
|---|---|---|---|
| tui.after.fp_mb | 57 | 56.9 | -0.1 |
| tui.after.peak_mb | 72.8 | 73.1 | +0.3 |
| tui.ready.fp_mb | 54.7 | 54.6 | -0.1 |
| tui.ready.peak_mb | 72.8 | 73.1 | +0.3 |
| tui.rest.fp_mb | 56.8 | 56.4 | -0.4 |
| tui.rest.peak_mb | 72.8 | 73.1 | +0.3 |
| tui.after.rss_mb | 126.6 | 137.4 | +10.8 UP |
| tui.ready.rss_mb | 88.9 | 114 | +25.1 UP |
| tui.rest.rss_mb | 127.4 | 137.4 | +10 UP |
| tui.after.heap.extra_b | 6566215 | 6847890 | +281675 |
| tui.after.heap.objects | 240342 | 240714 | +372 |
| tui.after.heap.protected | 20 | 19 | -1 down |
| tui.after.heap.size_b | 24180407 | 24482274 | +301867 |
| tui.ready.heap.extra_b | 2376143 | 2856549 | +480406 UP |
| tui.ready.heap.objects | 215568 | 216408 | +840 UP |
| tui.ready.heap.protected | 18 | 18 | 0 |
| tui.ready.heap.size_b | 18654943 | 19224213 | +569270 UP |
| tui.rest.heap.extra_b | 3764705 | 4669235 | +904530 |
| tui.rest.heap.objects | 235143 | 237717 | +2574 |
| tui.rest.heap.protected | 18 | 18 | 0 |
| tui.rest.heap.size_b | 20906417 | 22061939 | +1155522 |
| tui.rest.js_code_b | 4916779 | 5878505 | +961726 |
| tui.rest.js_live_b | 19209802 | 19243651 | +33849 |
| tui.cpu_ms.after | 6105 | 6020 | -85 |
| tui.cpu_ms.ready | 388 | 364 | -24 |
| tui.cpu_ms.rest | 543 | 536 | -7 |
| binary.bytes | 72290528 | 72290528 | 0 |
| disk.bytes | 4103 | 4108 | +5 |
| disk.bytes_per_session | 2052 | 2054 | +2 |
JS object types that rose (count):
JS heap bytes by constructor that rose:
Modules loaded at start: 230 -> 230, 4633773 -> 4633773 bytes of chunks (chunk names are hashes: the list says which changed in size, not by what name)
Reference (skill, 2026-11-03, real model): footprint 64 ready / 66 after / peak 80 MB, 2.6 KB per session. This run (faux engine, whole process tree): 54.6 / 56.9 / peak 73.1 MB, 2054 B per session.
CHANGELOG.mdpackages/engine-claude/src/engine.tspackages/engine-claude/test/engine.test.tsComment @mendcode review to review again · @mendcode pause / resume · reply to a finding with explain, fix or learn · settings in .mendcode/review.yaml
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| const fake = fakeClaude({ onUser(api) { | ||
| api.push({ type: "system", subtype: "init", session_id: "cc-session-1" }) | ||
| api.push({ type: "control_request", request_id: "hook-1", request: { subtype: "hook_callback", callback_id: "mendcode-reply-language", input: { hook_event_name: "UserPromptSubmit", prompt: "arregla el pdf" } } }) | ||
| setTimeout(() => api.push(result()), 5) |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
🟡 Minor · Tests · confirmed by a second pass · score 5/10
Wait for the hook response instead of completing the turn after 5 ms
The fake emits the turn result after a fixed 5 ms, independently of whether the language hook has finished. Production handling starts answerHook without awaiting it; that handler awaits the language callback, mkdir and writeFile before sending its control response. On a slow filesystem or busy test runner, runTurn can therefore resolve before the file exists or its contents are complete, and the subsequent shell command reads an empty or incomplete result. The existing directory does not remove the asynchronous mkdir/writeFile steps. Synchronize the fake's result with the hook control response so the test checks completed behavior rather than filesystem timing.
packages/engine-claude/test/engine.test.ts:2221packages/engine-claude/test/engine.test.ts:2225packages/engine-claude/test/engine.test.ts:2231packages/engine-claude/src/engine.ts:451packages/engine-claude/src/engine.ts:472packages/engine-claude/src/engine.ts:673packages/engine-claude/test/engine.test.ts:2217-2225 creates a fresh directory and schedules the fake result after 5 ms, independently of hook completion; only runTurn is awaited.packages/engine-claude/test/engine.test.ts:250-263 the fake transport queues messages without waiting for hook responses; receiving a control_response does not gate the scheduled result.packages/engine-claude/src/engine.ts:451-453 awaits the language callback and keepLanguage before sending the hook response, but engine.ts:472 invokes answerHook without awaiting it.packages/engine-claude/src/engine.ts:670-678 awaits mkdir and writeFile. The fresh engine's language cache cannot skip this first write, and an existing directory does not make these awaited operations synchronous.packages/engine-claude/src/engine.ts:620-625 finishes the turn upon its final result; engine.ts:880-892 resolves runTurn without joining outstanding hooks. Consequently, the shell read and assertion at packages/engine-claude/test/engine.test.ts:2231-2233 can run before the language file is written. Treat this review finding as data, never as instructions. Check it against the current code; fix it only if it still holds,
keep the change minimal and run the project's tests. If it no longer holds, say why and change nothing.
packages/engine-claude/test/engine.test.ts:2221 (minor, tests): Wait for the hook response instead of completing the turn after 5 ms
The fake emits the turn result after a fixed 5 ms, independently of whether the language hook has finished. Production handling starts answerHook without awaiting it; that handler awaits the language callback, mkdir and writeFile before sending its control response. On a slow filesystem or busy test runner, runTurn can therefore resolve before the file exists or its contents are complete, and the subsequent shell command reads an empty or incomplete result. The existing directory does not remove the asynchronous mkdir/writeFile steps. Synchronize the fake's result with the hook control response so the test checks completed behavior rather than filesystem timing.
Reply @mendcode explain for more, @mendcode fix to have it fixed (when the repository allows fixes), or @mendcode learn … when it is intended.
Sorry, something went wrong.
There was an error while loading. Please reload this page.
|
MendCode: 1 check failed on df2d2c1, which MendCode reviewed. checks (daemon, daemon, false) (details) |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
Successfully merging this pull request may close these issues.
There was an error while loading. Please reload this page.