fix(dashboard): cap useLiveTranscript entries to prevent heap exhaustion

The hook was prepending every SSE log entry into React state without bound.
Long-lived active agents flooded the array (hundreds of MB) and the dashboard
eventually died with an out-of-memory crash. Cap the buffer at 200 entries —
the UI only ever renders the first 20, so the cap is generous but finite.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
gsxdsm
2026-04-24 23:16:29 -07:00
parent f44310a46d
commit 28eef80b26

View File

@@ -1,6 +1,11 @@
import { useState, useEffect, useRef } from "react";
import { subscribeSse } from "../sse-bus";
// Render shows only the first 20 entries; keep a small buffer above that for
// hot-reconnect/scrollback but never let the array grow unbounded — long-lived
// active agents would otherwise leak hundreds of MB into React state.
const MAX_TRANSCRIPT_ENTRIES = 200;
/**
* Log entry from an agent's execution stream.
*
@@ -94,7 +99,12 @@ export function useLiveTranscript(taskId: string | undefined, projectId?: string
timestamp: raw.timestamp,
content: raw.content,
};
setEntries(prev => [entry, ...prev]);
setEntries(prev => {
const next = [entry, ...prev];
return next.length > MAX_TRANSCRIPT_ENTRIES
? next.slice(0, MAX_TRANSCRIPT_ENTRIES)
: next;
});
} catch { /* skip malformed events */ }
},
},