Repository navigation
fix(heartbeat): stop losing coding activity - #16
Conversation
The server builds coding sessions from heartbeats and closes a session after a 10 minute gap, so lost or wrong heartbeats skew measured effort. - Re-queue heartbeats when the send to the daemon fails instead of dropping them; the queue is capped at 5000 (oldest dropped first). - Flush pending heartbeats on VimLeavePre, waiting up to 1.5s. Sessions shorter than the 2 minute flush interval were lost entirely on :wq. - Use the autocmd's buffer (args.buf) instead of the current buffer, so :wa / :wqa record a write for each written file rather than N writes for the current one. The cursor comes from a window showing that buffer, or is omitted. - Only apply the same-cursor duplicate check to navigation events; edits that keep the cursor in place (x, dd) were dropped. - Escape the dot in the .git pattern; '/.git/' also matched '/egit/'. - Build UUIDs from uv.random. Reseeding math.random from the clock on every call made collisions likely across Neovim instances, and the server silently drops a heartbeat whose id already exists. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01X5wQC8wrU4kY1jBfbzdquX
|
You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard. |
ReviewOverall this is a solid, well-scoped fix. The Potential issues
Nits / tests
Security: no concerns. Using OS randomness for IDs is an improvement. LGTM with the optional follow-ups above. |
During BufWritePost for :wa / :wqa, Neovim makes the written buffer current (aucmd_prepbuf), so nvim_get_current_buf() already pointed at the right file and the args.buf change fixed nothing. The test that seemed to show the bug relied on nvim_exec_autocmds not switching buffers, which Neovim nightly now does, so it failed there. Restore the original buffer and cursor lookup and rewrite the integration specs to make the buffer current first. Verified on Neovim 0.11.4 and nightly (0.13.0-dev). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01X5wQC8wrU4kY1jBfbzdquX
ReviewOverall this is a solid, well-scoped fix, and the tests cover each behavior change. I found no blockers. Notes below, roughly by importance. I haven't run the suite myself; this is from reading the diff. Potential issues
Nits
Security / performance
Nice work on the correction note about |
Why
The server builds coding sessions from heartbeats (
server/tasks/activity.sessions.go). A session closes after a 10-minute gap, and effort issession_end - session_start. Every heartbeat that is dropped shortens the measured effort.What changed
send_heartbeatsused to empty the queue and drop the batch on any error, while:ShellTimeStatusreported the heartbeats as "queued". The newheartbeat.requeue()puts them back. The queue is capped at 5000 and drops the oldest first.:wq) was lost completely.sender.start()now registers aVimLeavePreautocmd that calls the newsender.flush_sync(), which waits up to 1.5 s.x,dd) were being skipped..gitpattern escapes its dot. In a Lua pattern,'/.git/'also matches/egit/,/_git/and similar.uv.random.uuid()reseededmath.randomwithos.time() + os.clock()*1e6on every call, so seeds overlap across Neovim instances.heartbeat_idis globally unique on the server and inserts useON CONFLICT DO NOTHING, so a collision silently drops a heartbeat. It now usesuv.random(16). The fallback,math.random, is seeded once.Correction: the first commit also switched the autocmds to
args.buf, to fix what looked like:warecording every write against the current buffer. That bug doesn't exist. DuringBufWritePostNeovim makes the written buffer current (aucmd_prepbuf), which I checked with a real:wa. The test that seemed to show the bug relied onnvim_exec_autocmdsnot switching buffers, and Neovim nightly does switch, so CI failed there. bf135ae reverts that part.Testing
./scripts/test.shwith plenary passes on Neovim 0.11.4 and on nightly (0.13.0-dev): 263 passed, 0 failed. The new specs cover:flush_sync, including its timeoutVimLeavePreautocmd.gitvsegitpatternUnrelated issue I noticed but didn't change:
./scripts/test.sh <file>fails with "cannot open … {minimal_init = …}", becausePlenaryBustedFiletakes no options argument.Companion PRs fix the same kinds of bugs in the VS Code and JetBrains plugins.
🤖 Generated with Claude Code
https://claude.ai/code/session_01X5wQC8wrU4kY1jBfbzdquX