fix(redstone): close race in withSlowToolIndicator orphaning wiki loop
The setTimeout callback awaited sendMessage before installing the rotation interval. If the tool resolved during that await, the finally cleanup ran before rotateTimer existed, leaving an interval that edited the "reading the wiki…" placeholder forever. Added a `done` flag so the callback bails (and deletes the placeholder) if the tool already finished.
This commit is contained in:
10
bot/bot.ts
10
bot/bot.ts
@@ -1524,10 +1524,19 @@ async function withSlowToolIndicator<T>(chatId: number, toolName: string, fn: ()
|
|||||||
if (!WIKI_TOOL_RE.test(toolName)) return fn();
|
if (!WIKI_TOOL_RE.test(toolName)) return fn();
|
||||||
let placeholderId: number | null = null;
|
let placeholderId: number | null = null;
|
||||||
let rotateTimer: ReturnType<typeof setInterval> | null = null;
|
let rotateTimer: ReturnType<typeof setInterval> | null = null;
|
||||||
|
let done = false;
|
||||||
let phraseIdx = 0;
|
let phraseIdx = 0;
|
||||||
const showTimer = setTimeout(async () => {
|
const showTimer = setTimeout(async () => {
|
||||||
try {
|
try {
|
||||||
const m = await bot.api.sendMessage(chatId, SLOW_TOOL_PHRASES[0]);
|
const m = await bot.api.sendMessage(chatId, SLOW_TOOL_PHRASES[0]);
|
||||||
|
// fn() may have resolved while sendMessage was in flight — if so the
|
||||||
|
// finally block already ran and saw no placeholder/timer to clean up.
|
||||||
|
// Delete the just-sent message and bail instead of installing an
|
||||||
|
// orphaned rotation loop that nothing will ever clear.
|
||||||
|
if (done) {
|
||||||
|
try { await bot.api.deleteMessage(chatId, m.message_id); } catch { /* ignore */ }
|
||||||
|
return;
|
||||||
|
}
|
||||||
placeholderId = m.message_id;
|
placeholderId = m.message_id;
|
||||||
rotateTimer = setInterval(async () => {
|
rotateTimer = setInterval(async () => {
|
||||||
phraseIdx = (phraseIdx + 1) % SLOW_TOOL_PHRASES.length;
|
phraseIdx = (phraseIdx + 1) % SLOW_TOOL_PHRASES.length;
|
||||||
@@ -1539,6 +1548,7 @@ async function withSlowToolIndicator<T>(chatId: number, toolName: string, fn: ()
|
|||||||
try {
|
try {
|
||||||
return await fn();
|
return await fn();
|
||||||
} finally {
|
} finally {
|
||||||
|
done = true;
|
||||||
clearTimeout(showTimer);
|
clearTimeout(showTimer);
|
||||||
if (rotateTimer) clearInterval(rotateTimer);
|
if (rotateTimer) clearInterval(rotateTimer);
|
||||||
if (placeholderId != null) {
|
if (placeholderId != null) {
|
||||||
|
|||||||
Reference in New Issue
Block a user