perf: fix streaming lag, memory leaks, stuck spinners, and proxy timeout (#483)
* perf: fix streaming lag, memory leaks, and proxy timeout
- PERF-001: Batch all streaming parts via requestAnimationFrame instead of
per-token Zustand set() calls (~100/sec → 1 per frame)
- PERF-002: Fix direct state.sessionMemoryState mutation inside set() callback
- PERF-003: Debounce messageStore→sessionStore subscription via rAF + 500ms
title computation delay
- PERF-004: Stabilize SSE callbacks with refs to prevent reconnection storms;
add 5-min stuck session idle timeout
- PERF-005: Bound messageCache (500 max, LRU eviction), cap registry Maps,
cleanup on session eviction
- PERF-006: Replace toast duration: Infinity with 30s + id-based dedup
- Fix proxy timeout: POST /session/:id/message 45s → 4min (matches CLI)
- Add vitest + jsdom test infrastructure (61 tests across 7 files)
Addresses: #476 (stuck spinner), #358 (34GB memory leak), #190 (browser lag)
* perf: virtualize tool output rendering (read, edit, write)
- PERF-007: Replace per-line <SyntaxHighlighter> with VirtualizedCodeBlock:
- ONE Prism.highlight() call for entire file instead of N per-line calls
- @tanstack/react-virtual renders only visible rows (~30 vs 2000+)
- Applied to: ToolPart (read, DiffPreview, WriteInputPreview) and
ToolOutputDialog (unified diff, read content)
- PERF-008: Memoize parseReadToolOutput/parseDiffToUnified via useMemo
to prevent re-parsing on every re-render
A 2000-line file read now mounts ~30 DOM nodes instead of 2000
SyntaxHighlighter instances, eliminating the main-thread blocking
that caused UI freezes during file operations.
* fix: resolve lint errors (unused vars in tests and VirtualizedCodeBlock)
* chore: trim PR scope to core perf fixes
* fix: restore tool-card highlight stability
---------
Co-authored-by: Bohdan Triapitsyn <artmore@protonmail.com>