From ca54412bd4a78761c231cfc1c3242ed7e3338909 Mon Sep 17 00:00:00 2001 From: spiceoogway Date: Fri, 30 Jan 2026 00:59:18 -0500 Subject: [PATCH] fix: use null check instead of typeof number for thread IDs in queue drain Slack thread_ts values are always strings (e.g. "1769742846.264069"), so the typeof === "number" checks never matched, causing queued replies to lose their thread context and post as top-level channel messages. Replace all three typeof === "number" checks with != null to handle both string (Slack) and numeric thread IDs. Fixes #4380 --- src/auto-reply/reply/queue/drain.ts | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/src/auto-reply/reply/queue/drain.ts b/src/auto-reply/reply/queue/drain.ts index 01361a1ec..593e35e6d 100644 --- a/src/auto-reply/reply/queue/drain.ts +++ b/src/auto-reply/reply/queue/drain.ts @@ -40,13 +40,13 @@ export function scheduleFollowupDrain( const to = item.originatingTo; const accountId = item.originatingAccountId; const threadId = item.originatingThreadId; - if (!channel && !to && !accountId && typeof threadId !== "number") { + if (!channel && !to && !accountId && threadId == null) { return {}; } if (!isRoutableChannel(channel) || !to) { return { cross: true }; } - const threadKey = typeof threadId === "number" ? String(threadId) : ""; + const threadKey = threadId != null ? String(threadId) : ""; return { key: [channel, to, accountId || "", threadKey].join("|"), }; @@ -61,7 +61,10 @@ export function scheduleFollowupDrain( } const items = queue.items.splice(0, queue.items.length); - const summary = buildQueueSummaryPrompt({ state: queue, noun: "message" }); + const summary = buildQueueSummaryPrompt({ + state: queue, + noun: "message", + }); const run = items.at(-1)?.run ?? queue.lastRun; if (!run) break; @@ -72,7 +75,7 @@ export function scheduleFollowupDrain( (i) => i.originatingAccountId, )?.originatingAccountId; const originatingThreadId = items.find( - (i) => typeof i.originatingThreadId === "number", + (i) => i.originatingThreadId != null, )?.originatingThreadId; const prompt = buildCollectPrompt({ @@ -93,7 +96,10 @@ export function scheduleFollowupDrain( continue; } - const summaryPrompt = buildQueueSummaryPrompt({ state: queue, noun: "message" }); + const summaryPrompt = buildQueueSummaryPrompt({ + state: queue, + noun: "message", + }); if (summaryPrompt) { const run = queue.lastRun; if (!run) break;