From 5fa2827ed6306ae80f2d73c9cadd7f79e9389fe8 Mon Sep 17 00:00:00 2001 From: dsh-agent Date: Mon, 14 Sep 2026 19:16:28 +0800 Subject: [PATCH] =?UTF-8?q?feat(tg):=20=E5=8E=BB=E6=8E=89=20'>=20Thinking?= =?UTF-8?q?=E2=80=A6'=20=E6=80=9D=E8=80=83=E6=8F=90=E7=A4=BA=E6=B5=81?= =?UTF-8?q?=E6=B0=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 用户要求:不再发送思考指示(assistant/chunk 的 reasoning 分支整段移除, 连带 thinkingSessions 状态与相关清理)。tool/call、tool/result、todo/write、 turn/end 的流水保持不变。 --- lib/bridge.d.ts | 2 -- lib/bridge.js | 19 ------------------- src/bridge.ts | 20 -------------------- 3 files changed, 41 deletions(-) diff --git a/lib/bridge.d.ts b/lib/bridge.d.ts index ba0f826..e3e5cb4 100644 --- a/lib/bridge.d.ts +++ b/lib/bridge.d.ts @@ -45,8 +45,6 @@ export declare class TelegramBridge { private disposeApprovalHook; /** dsh 0.1.5 起 ask 走 'user-questions/request' waterfall(不再有 userQuestions.provider)。 */ private disposeUserQuestionHook; - /** sessionId → thinking indicator state (one notice per reasoning phase) */ - private readonly thinkingSessions; /** callId → tool name (tool/result failure notices) */ private readonly callNames; /** sessionId → latest todo snapshot (/mission) */ diff --git a/lib/bridge.js b/lib/bridge.js index d9d697d..8dfe9ff 100644 --- a/lib/bridge.js +++ b/lib/bridge.js @@ -113,8 +113,6 @@ export class TelegramBridge { disposeApprovalHook; /** dsh 0.1.5 起 ask 走 'user-questions/request' waterfall(不再有 userQuestions.provider)。 */ disposeUserQuestionHook; - /** sessionId → thinking indicator state (one notice per reasoning phase) */ - thinkingSessions = new Map(); /** callId → tool name (tool/result failure notices) */ callNames = new Map(); /** sessionId → latest todo snapshot (/mission) */ @@ -199,7 +197,6 @@ export class TelegramBridge { this.noticeQueue.clear(); this.pendingAsks.clear(); this.pendingApprovalsTG.clear(); - this.thinkingSessions.clear(); this.callNames.clear(); this.lastTodos.clear(); for (const controller of this.compactAborts.values()) @@ -1101,7 +1098,6 @@ export class TelegramBridge { } if (event.type === 'turn/end') { this.busySessions.delete(id); - this.thinkingSessions.delete(id); for (const b of targets) this.stopTypingHeartbeat(b.chatId); // Abnormal endings (API failure / abort / crash-recovery) must be @@ -1129,7 +1125,6 @@ export class TelegramBridge { const name = event.data?.name ?? 'tool'; if (name === 'ask_user_question') return; - this.thinkingSessions.set(id, false); if (event.data?.callId !== undefined) { if (this.callNames.size > 400) { const first = this.callNames.keys().next().value; @@ -1147,25 +1142,11 @@ export class TelegramBridge { } if (event.type === 'assistant/message') { const text = contentToText(event.data.message.content); - this.thinkingSessions.set(id, false); if (!text) return; await Promise.all(targets.map((b) => this.deliver(b.chatId, text))); return; } - if (event.type === 'assistant/chunk') { - // Thinking indicator: once per reasoning phase, status only (no content). - const chunk = event.data?.chunk; - const ctype = String(chunk?.type ?? ''); - const btype = String(chunk?.block?.type ?? ''); - const isReasoning = ctype.includes('reasoning') || btype.includes('reasoning') || btype.includes('think'); - if (isReasoning && this.thinkingSessions.get(id) !== true) { - this.thinkingSessions.set(id, true); - for (const b of targets) - this.enqueueNotice(b.chatId, '> Thinking…'); - } - return; - } if (event.type === 'tool/result') { // Only failures — successful results are too noisy for the phone. const data = event.data; diff --git a/src/bridge.ts b/src/bridge.ts index 29e67fa..a78ce23 100644 --- a/src/bridge.ts +++ b/src/bridge.ts @@ -254,8 +254,6 @@ export class TelegramBridge { private disposeApprovalHook: (() => void) | undefined /** dsh 0.1.5 起 ask 走 'user-questions/request' waterfall(不再有 userQuestions.provider)。 */ private disposeUserQuestionHook: (() => void) | undefined - /** sessionId → thinking indicator state (one notice per reasoning phase) */ - private readonly thinkingSessions = new Map() /** callId → tool name (tool/result failure notices) */ private readonly callNames = new Map() /** sessionId → latest todo snapshot (/mission) */ @@ -348,7 +346,6 @@ export class TelegramBridge { this.noticeQueue.clear() this.pendingAsks.clear() this.pendingApprovalsTG.clear() - this.thinkingSessions.clear() this.callNames.clear() this.lastTodos.clear() for (const controller of this.compactAborts.values()) controller.abort() @@ -1276,7 +1273,6 @@ export class TelegramBridge { if (event.type === 'turn/end') { this.busySessions.delete(id) - this.thinkingSessions.delete(id) for (const b of targets) this.stopTypingHeartbeat(b.chatId) // Abnormal endings (API failure / abort / crash-recovery) must be // visible on the phone — previously they ended in silence. @@ -1301,7 +1297,6 @@ export class TelegramBridge { // Progress summary; ask_user is owned by the provider hook (avoids duplicates). const name = event.data?.name ?? 'tool' if (name === 'ask_user_question') return - this.thinkingSessions.set(id, false) if (event.data?.callId !== undefined) { if (this.callNames.size > 400) { const first = this.callNames.keys().next().value @@ -1319,26 +1314,11 @@ export class TelegramBridge { if (event.type === 'assistant/message') { const text = contentToText(event.data.message.content) - this.thinkingSessions.set(id, false) if (!text) return await Promise.all(targets.map((b) => this.deliver(b.chatId, text))) return } - if (event.type === 'assistant/chunk') { - // Thinking indicator: once per reasoning phase, status only (no content). - const chunk = event.data?.chunk as { type?: string; block?: { type?: string } } | undefined - const ctype = String(chunk?.type ?? '') - const btype = String(chunk?.block?.type ?? '') - const isReasoning = ctype.includes('reasoning') || btype.includes('reasoning') || btype.includes('think') - if (isReasoning && this.thinkingSessions.get(id) !== true) { - this.thinkingSessions.set(id, true) - for (const b of targets) - this.enqueueNotice(b.chatId, '> Thinking…') - } - return - } - if (event.type === 'tool/result') { // Only failures — successful results are too noisy for the phone. const data = event.data as { error?: { name?: string; code?: string }; message?: { tool_use_id?: string; callId?: string } }