From 8a632a82052892af6584a7f33af448abb1ce878d Mon Sep 17 00:00:00 2001 From: Charles Vien Date: Tue, 7 Apr 2026 18:55:19 -0700 Subject: [PATCH 1/5] Dedupe recordActivity calls on session connect --- .../features/sessions/hooks/useSessionConnection.ts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/apps/code/src/renderer/features/sessions/hooks/useSessionConnection.ts b/apps/code/src/renderer/features/sessions/hooks/useSessionConnection.ts index 8fd117c77..92e9b4e52 100644 --- a/apps/code/src/renderer/features/sessions/hooks/useSessionConnection.ts +++ b/apps/code/src/renderer/features/sessions/hooks/useSessionConnection.ts @@ -11,6 +11,7 @@ import { useChatTitleGenerator } from "./useChatTitleGenerator"; const log = logger.scope("session-connection"); const connectingTasks = new Set(); +const activityRecorded = new Set(); interface UseSessionConnectionOptions { taskId: string; @@ -37,7 +38,10 @@ export function useSessionConnection({ useEffect(() => { const taskRunId = session?.taskRunId; if (!taskRunId) return; - trpcClient.agent.recordActivity.mutate({ taskRunId }).catch(() => {}); + if (!activityRecorded.has(taskRunId)) { + activityRecorded.add(taskRunId); + trpcClient.agent.recordActivity.mutate({ taskRunId }).catch(() => {}); + } const heartbeat = setInterval( () => { trpcClient.agent.recordActivity.mutate({ taskRunId }).catch(() => {}); From 93608dbaff3d3cf9d7720e1dbd207ad0100b07b5 Mon Sep 17 00:00:00 2001 From: Charles Vien Date: Tue, 7 Apr 2026 18:55:25 -0700 Subject: [PATCH 2/5] Fix markAsViewed re-firing on every render --- .../command-center/components/CommandCenterView.tsx | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/apps/code/src/renderer/features/command-center/components/CommandCenterView.tsx b/apps/code/src/renderer/features/command-center/components/CommandCenterView.tsx index 76eb6f9e3..1eaf69cda 100644 --- a/apps/code/src/renderer/features/command-center/components/CommandCenterView.tsx +++ b/apps/code/src/renderer/features/command-center/components/CommandCenterView.tsx @@ -13,16 +13,17 @@ export function CommandCenterView() { const { cells, summary } = useCommandCenterData(); const { markAsViewed } = useTaskViewed(); - const visibleTaskIds = useMemo( - () => cells.map((c) => c.taskId).filter((id): id is string => id != null), - [cells], - ); + const visibleTaskIdsKey = cells + .map((c) => c.taskId) + .filter(Boolean) + .join(","); useEffect(() => { - for (const taskId of visibleTaskIds) { + if (!visibleTaskIdsKey) return; + for (const taskId of visibleTaskIdsKey.split(",")) { markAsViewed(taskId); } - }, [visibleTaskIds, markAsViewed]); + }, [visibleTaskIdsKey, markAsViewed]); const headerContent = useMemo( () => ( From b2bc1cff2f23056d45488c597cbb03d17f7b99da Mon Sep 17 00:00:00 2001 From: Charles Vien Date: Tue, 7 Apr 2026 18:56:23 -0700 Subject: [PATCH 3/5] Add IPC timing middleware during boot --- apps/code/src/main/trpc/trpc.ts | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/apps/code/src/main/trpc/trpc.ts b/apps/code/src/main/trpc/trpc.ts index 96e6ad3c5..ce38c417e 100644 --- a/apps/code/src/main/trpc/trpc.ts +++ b/apps/code/src/main/trpc/trpc.ts @@ -1,4 +1,5 @@ import { initTRPC } from "@trpc/server"; +import log from "electron-log/main"; const trpc = initTRPC.create({ isServer: true, @@ -9,7 +10,24 @@ const CALL_RATE_THRESHOLD = 50; const callCounts: Record = {}; -const callRateMonitor = trpc.middleware(async ({ path, next }) => { +const ipcTimingEnabled = process.env.IPC_TIMINGS === "true"; +const ipcTimingBootMs = 15_000; +const bootTime = Date.now(); + +const callRateMonitor = trpc.middleware(async ({ path, next, type }) => { + if (ipcTimingEnabled) { + const elapsed = Date.now() - bootTime; + if (elapsed < ipcTimingBootMs) { + const t = performance.now(); + log.info(`[ipc-timing] >> ${type} ${path}`); + const result = await next(); + log.info( + `[ipc-timing] << ${type} ${path}: ${(performance.now() - t).toFixed(0)}ms`, + ); + return result; + } + } + if (process.env.NODE_ENV !== "development") { return next(); } From a58e4aae29e19551766aabd378405884e5d1a4f2 Mon Sep 17 00:00:00 2001 From: Charles Vien Date: Tue, 7 Apr 2026 20:46:05 -0700 Subject: [PATCH 4/5] Clean up IPC middleware and activity dedup --- apps/code/src/main/trpc/trpc.ts | 54 ++++++++++--------- .../sessions/hooks/useSessionConnection.ts | 5 +- 2 files changed, 33 insertions(+), 26 deletions(-) diff --git a/apps/code/src/main/trpc/trpc.ts b/apps/code/src/main/trpc/trpc.ts index ce38c417e..1ece08b7b 100644 --- a/apps/code/src/main/trpc/trpc.ts +++ b/apps/code/src/main/trpc/trpc.ts @@ -15,40 +15,44 @@ const ipcTimingBootMs = 15_000; const bootTime = Date.now(); const callRateMonitor = trpc.middleware(async ({ path, next, type }) => { - if (ipcTimingEnabled) { - const elapsed = Date.now() - bootTime; - if (elapsed < ipcTimingBootMs) { - const t = performance.now(); - log.info(`[ipc-timing] >> ${type} ${path}`); - const result = await next(); - log.info( - `[ipc-timing] << ${type} ${path}: ${(performance.now() - t).toFixed(0)}ms`, - ); - return result; - } - } + const shouldTime = + ipcTimingEnabled && Date.now() - bootTime < ipcTimingBootMs; + const t = shouldTime ? performance.now() : 0; - if (process.env.NODE_ENV !== "development") { - return next(); + if (shouldTime) { + log.info(`[ipc-timing] >> ${type} ${path}`); } - const now = Date.now(); - if (!callCounts[path]) { - callCounts[path] = []; - } + if (process.env.NODE_ENV === "development") { + const now = Date.now(); + if (!callCounts[path]) { + callCounts[path] = []; + } - const timestamps = callCounts[path]; - timestamps.push(now); + const timestamps = callCounts[path]; + timestamps.push(now); - const cutoff = now - CALL_RATE_WINDOW_MS; - while (timestamps.length > 0 && timestamps[0] < cutoff) { - timestamps.shift(); + const cutoff = now - CALL_RATE_WINDOW_MS; + while (timestamps.length > 0 && timestamps[0] < cutoff) { + timestamps.shift(); + } + + if (timestamps.length >= CALL_RATE_THRESHOLD) { + log.warn( + `[ipc-rate] ${path} called ${timestamps.length} times in ${CALL_RATE_WINDOW_MS}ms`, + ); + } } - if (timestamps.length >= CALL_RATE_THRESHOLD) { + const result = await next(); + + if (shouldTime) { + log.info( + `[ipc-timing] << ${type} ${path}: ${(performance.now() - t).toFixed(0)}ms`, + ); } - return next(); + return result; }); export const router = trpc.router; diff --git a/apps/code/src/renderer/features/sessions/hooks/useSessionConnection.ts b/apps/code/src/renderer/features/sessions/hooks/useSessionConnection.ts index 92e9b4e52..f8afc734d 100644 --- a/apps/code/src/renderer/features/sessions/hooks/useSessionConnection.ts +++ b/apps/code/src/renderer/features/sessions/hooks/useSessionConnection.ts @@ -48,7 +48,10 @@ export function useSessionConnection({ }, 5 * 60 * 1000, ); - return () => clearInterval(heartbeat); + return () => { + clearInterval(heartbeat); + activityRecorded.delete(taskRunId); + }; }, [session?.taskRunId]); useEffect(() => { From d4708b9266a66ecde44f271072da0c244d0f33c1 Mon Sep 17 00:00:00 2001 From: Charles Vien Date: Tue, 7 Apr 2026 20:48:22 -0700 Subject: [PATCH 5/5] Include procedure type in rate monitor warning --- apps/code/src/main/trpc/trpc.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/code/src/main/trpc/trpc.ts b/apps/code/src/main/trpc/trpc.ts index 1ece08b7b..32992a377 100644 --- a/apps/code/src/main/trpc/trpc.ts +++ b/apps/code/src/main/trpc/trpc.ts @@ -39,7 +39,7 @@ const callRateMonitor = trpc.middleware(async ({ path, next, type }) => { if (timestamps.length >= CALL_RATE_THRESHOLD) { log.warn( - `[ipc-rate] ${path} called ${timestamps.length} times in ${CALL_RATE_WINDOW_MS}ms`, + `[ipc-rate] ${type} ${path} called ${timestamps.length} times in ${CALL_RATE_WINDOW_MS}ms`, ); } }