fixed telegram issues.

This commit is contained in:
lsamc 2025-09-04 21:02:19 +08:00
parent eafe594a66
commit f608aed3c2
7 changed files with 407 additions and 71 deletions

View File

@ -6,7 +6,32 @@
}, },
"email": { "email": {
"type": "email", "type": "email",
"enabled": true "enabled": true,
"config": {
"smtp": {
"host": "smtp.gmail.com",
"port": 465,
"secure": true,
"auth": {
"user": "2322176165lsa@gmail.com",
"pass": "frkxntpirpfrhqre"
}
},
"imap": {
"host": "imap.gmail.com",
"port": 993,
"secure": true,
"auth": {
"user": "2322176165lsa@gmail.com",
"pass": "frkxntpirpfrhqre"
}
},
"from": "2322176165lsa@gmail.com",
"to": "2322176165@qq.com",
"template": {
"checkInterval": 20
}
}
}, },
"discord": { "discord": {
"type": "chat", "type": "chat",
@ -24,8 +49,8 @@
"botToken": "", "botToken": "",
"chatId": "", "chatId": "",
"groupId": "", "groupId": "",
"whitelist": [], "forceIPv4": false,
"forceIPv4": false "whitelist": []
} }
}, },
"whatsapp": { "whatsapp": {

View File

@ -20,7 +20,7 @@ const TelegramChannel = require('./src/channels/telegram/telegram');
class SmartMonitor { class SmartMonitor {
constructor() { constructor() {
this.sessionName = process.env.TMUX_SESSION || 'claude-real'; this.sessionName = process.env.TMUX_SESSION || 'claude-session';
this.lastOutput = ''; this.lastOutput = '';
this.processedResponses = new Set(); // 記錄已處理的回應 this.processedResponses = new Set(); // 記錄已處理的回應
this.checkInterval = 1000; // Check every 1 second this.checkInterval = 1000; // Check every 1 second
@ -290,4 +290,4 @@ process.on('SIGTERM', () => {
}); });
// Start monitoring // Start monitoring
monitor.start(); monitor.start();

View File

@ -538,5 +538,284 @@
"sessionId": "10cd6e52-91a8-476a-af0a-1fe2c2929ab6", "sessionId": "10cd6e52-91a8-476a-af0a-1fe2c2929ab6",
"tmuxSession": "claude-hook-test", "tmuxSession": "claude-hook-test",
"description": "completed - Claude-Code-Remote" "description": "completed - Claude-Code-Remote"
},
"M4769IDR": {
"type": "pty",
"createdAt": 1756981849,
"expiresAt": 1757068249,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "56e2eb19-9b1e-4b49-b3b3-f99149a9e244",
"tmuxSession": "test-session",
"description": "completed - Claude-Code-Remote-Test"
},
"UG0HP8QJ": {
"type": "pty",
"createdAt": 1756982044,
"expiresAt": 1757068444,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "925e4a47-174f-4b48-a666-12ca707c18d1",
"tmuxSession": "claude-code-remote",
"description": "completed - ecllipse"
},
"OGKAMMS0": {
"type": "pty",
"createdAt": 1756982145,
"expiresAt": 1757068545,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "2cf5a9ef-eb34-4cf0-8118-a2471f557320",
"tmuxSession": "0",
"description": "completed - ecllipse"
},
"IJYBTZ1M": {
"type": "pty",
"createdAt": 1756982185,
"expiresAt": 1757068585,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "6474c5f8-4234-417b-8149-060e6a091035",
"tmuxSession": "0",
"description": "completed - ecllipse"
},
"PQECZXRL": {
"type": "pty",
"createdAt": 1756983489,
"expiresAt": 1757069889,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "1b68620f-7199-40fe-b6fa-e57b3f36e346",
"tmuxSession": "claude-hook-test",
"description": "completed - ecllipse"
},
"BTEAWB0A": {
"type": "pty",
"createdAt": 1756983654,
"expiresAt": 1757070054,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "6a21e7b9-f95b-419f-8267-c7ab939ebb64",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"W2JST4BL": {
"type": "pty",
"createdAt": 1756984158,
"expiresAt": 1757070558,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "70221d98-958e-4084-91ca-971127620375",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"7YGTUNQI": {
"type": "pty",
"createdAt": 1756984735,
"expiresAt": 1757071135,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "b21eecfb-5566-4329-b7f6-e9ee5b8c5b87",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"JN9R6ORI": {
"type": "pty",
"createdAt": 1756984808,
"expiresAt": 1757071208,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "0eb2f38b-b5f3-4cd2-a096-fdbb50f6b4a3",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"G15979CU": {
"type": "pty",
"createdAt": 1756984876,
"expiresAt": 1757071276,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "05abff6e-1f11-4662-bede-9cc40dba095b",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"XO7ZYYCD": {
"type": "pty",
"createdAt": 1756985082,
"expiresAt": 1757071482,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "650de5dc-e5a5-406c-9ff0-e6b658b7639d",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"297WCHFD": {
"type": "pty",
"createdAt": 1756985194,
"expiresAt": 1757071594,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "e3cdc11d-2aef-4a0e-b8cc-0112889498a9",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"TUBTGR8Z": {
"type": "pty",
"createdAt": 1756985273,
"expiresAt": 1757071673,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "e7ca8ded-58ed-4a39-b676-d8fedef37e74",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"5YCUAO3D": {
"type": "pty",
"createdAt": 1756985483,
"expiresAt": 1757071883,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "9c7ab226-b2b3-4a52-b884-37ba050e71ac",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"2VCH8RD0": {
"type": "pty",
"createdAt": 1756986019,
"expiresAt": 1757072419,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "d5eebf40-762c-42f0-9a9e-6f38eb1e131f",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"3WMICU56": {
"type": "pty",
"createdAt": 1756987089,
"expiresAt": 1757073489,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "2a135963-ca49-425f-aa41-433154c4f70d",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"05BC2ZC2": {
"type": "pty",
"createdAt": 1756987248,
"expiresAt": 1757073648,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "84037cac-6d82-454e-ae12-66b59baf9d8f",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"M9SZFQ16": {
"type": "pty",
"createdAt": 1756987334,
"expiresAt": 1757073734,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "562fcfeb-8b0d-4ae2-87c5-6a6fafe7c53f",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"6G3CXZ8Y": {
"type": "pty",
"createdAt": 1756987424,
"expiresAt": 1757073824,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "3cf3c431-0aed-4097-a594-47144bf08a62",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"I5LFQWV0": {
"type": "pty",
"createdAt": 1756987485,
"expiresAt": 1757073885,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "ba716dd3-e2c2-4886-9e42-17c1b8d060ae",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"JLROEO9E": {
"type": "pty",
"createdAt": 1756987634,
"expiresAt": 1757074034,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "3db165f7-e6ea-4d47-82d0-c11f8e32127e",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"K38PPZ6B": {
"type": "pty",
"createdAt": 1756988634,
"expiresAt": 1757075034,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "379f517e-b533-47b8-a9f4-134565e03e6a",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"JFRFCCUN": {
"type": "pty",
"createdAt": 1756990126,
"expiresAt": 1757076526,
"cwd": "/home/lsamc/.local/src/Claude-Code-Remote",
"sessionId": "868c8e44-ed03-40bd-bfa1-05c62b852e52",
"tmuxSession": "claude-session",
"description": "completed - Claude-Code-Remote"
},
"TDO4OJHV": {
"type": "pty",
"createdAt": 1756990188,
"expiresAt": 1757076588,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "10dfce8a-7602-4f0d-8c4f-d7292ba769cf",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"L1WV5FAM": {
"type": "pty",
"createdAt": 1756990266,
"expiresAt": 1757076666,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "6f1193e8-da56-4dde-b898-e7e756a86b51",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"U9ERQKL6": {
"type": "pty",
"createdAt": 1756990314,
"expiresAt": 1757076714,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "7e3faaa7-73a4-4cfc-a9b6-34994c7f847f",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"O6D5M0TE": {
"type": "pty",
"createdAt": 1756990348,
"expiresAt": 1757076748,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "e31e9b64-a65b-4336-ad80-d465482842a6",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"A08Q192M": {
"type": "pty",
"createdAt": 1756990442,
"expiresAt": 1757076842,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "51d7c124-9978-4598-ab91-988fd489918f",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"WANYF73Z": {
"type": "pty",
"createdAt": 1756990505,
"expiresAt": 1757076905,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "281cf8ad-6e3b-4add-ba99-81d781b5da94",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"X6ILHKQN": {
"type": "pty",
"createdAt": 1756990584,
"expiresAt": 1757076984,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "0e4ac6fa-8808-4a68-9ebe-b97537c596a9",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
},
"JSJBJIU3": {
"type": "pty",
"createdAt": 1756990621,
"expiresAt": 1757077021,
"cwd": "/home/lsamc/develop/ecllipse",
"sessionId": "dbd1f477-0550-463b-b147-fcdf78720177",
"tmuxSession": "claude-session",
"description": "completed - ecllipse"
} }
} }

View File

@ -11,7 +11,7 @@ const Logger = require('../core/logger');
class ControllerInjector { class ControllerInjector {
constructor(config = {}) { constructor(config = {}) {
this.logger = new Logger('ControllerInjector'); this.logger = new Logger('ControllerInjector');
this.mode = config.mode || process.env.INJECTION_MODE || 'pty'; this.mode = config.mode || process.env.INJECTION_MODE || 'tmux';
this.defaultSession = config.defaultSession || process.env.TMUX_SESSION || 'claude-code'; this.defaultSession = config.defaultSession || process.env.TMUX_SESSION || 'claude-code';
} }
@ -107,4 +107,4 @@ class ControllerInjector {
} }
} }
module.exports = ControllerInjector; module.exports = ControllerInjector;

View File

@ -609,92 +609,102 @@ class TmuxMonitor extends EventEmitter {
extractConversation(text, sessionName = null) { extractConversation(text, sessionName = null) {
const lines = text.split('\n'); const lines = text.split('\n');
console.log(`[DEBUG] extractConversation called for session: ${sessionName}`);
console.log(`[DEBUG] Total lines in buffer: ${lines.length}`);
console.log(`[DEBUG] Last 5 lines:`, lines.slice(-5));
let userQuestion = ''; let userQuestion = '';
let claudeResponse = ''; let claudeResponse = '';
let responseLines = []; let responseLines = [];
let inResponse = false; let lastUserIndex = -1;
// Find the most recent user question and Claude response
let inUserInput = false;
let userQuestionLines = [];
for (let i = 0; i < lines.length; i++) { // First pass: Find the most recent user input
for (let i = lines.length - 1; i >= 0; i--) {
const line = lines[i].trim(); const line = lines[i].trim();
// Detect user input (line starting with "> " followed by content)
if (line.startsWith('> ') && line.length > 2) { if (line.startsWith('> ') && line.length > 2) {
userQuestionLines = [line.substring(2).trim()]; lastUserIndex = i;
inUserInput = true; userQuestion = line.substring(2).trim();
inResponse = false; // Reset response capture console.log(`[DEBUG] Found user question at line ${i}: ${userQuestion}`);
responseLines = []; // Clear previous response break;
}
}
// If we found a user question, look for the response after it
if (lastUserIndex >= 0) {
let foundResponseStart = false;
for (let i = lastUserIndex + 1; i < lines.length; i++) {
const line = lines[i].trim();
// Record user input timestamp if session name provided // Skip empty lines and system lines
if (sessionName) { if (!line ||
this.traceCapture.recordUserInput(sessionName); line.includes('? for shortcuts') ||
line.match(/^[╭╰│─]+$/) ||
line.startsWith('$') ||
line.startsWith('#') ||
line.startsWith('[')) {
continue;
} }
continue; // Multiple patterns to detect Claude responses
} const isClaudeResponse =
line.startsWith('⏺ ') || // Traditional marker
// Continue capturing multi-line user input line.startsWith('I\'ll ') || // Common Claude opening
if (inUserInput && !line.startsWith('⏺') && line.length > 0) { line.startsWith('I can ') ||
userQuestionLines.push(line); line.startsWith('Let me ') ||
continue; line.startsWith('Here') ||
} line.startsWith('Sure') ||
line.startsWith('Yes') ||
// End of user input line.startsWith('No') ||
if (inUserInput && (line.startsWith('⏺') || line.length === 0)) { line.includes('```') || // Code blocks
inUserInput = false; /^[A-Z][a-z]/.test(line); // Sentences starting with capital letter
userQuestion = userQuestionLines.join(' ');
}
// Detect Claude response (line starting with "⏺ " or other response indicators)
if (line.startsWith('⏺ ') ||
(inResponse && line.length > 0 &&
!line.startsWith('╭') && !line.startsWith('│') && !line.startsWith('╰') &&
!line.startsWith('> ') && !line.includes('? for shortcuts'))) {
if (line.startsWith('⏺ ')) { if (isClaudeResponse && !foundResponseStart) {
inResponse = true; foundResponseStart = true;
responseLines = [line.substring(2).trim()]; // Remove "⏺ " prefix responseLines = [line.startsWith('⏺ ') ? line.substring(2).trim() : line];
} else if (inResponse) { console.log(`[DEBUG] Found response start at line ${i}: ${line}`);
} else if (foundResponseStart) {
// Stop if we hit another user input or prompt
if (line.startsWith('> ') || line.includes('│ > │') || line.startsWith('╭')) {
console.log(`[DEBUG] Stopping response collection at line ${i}: ${line}`);
break;
}
responseLines.push(line); responseLines.push(line);
} }
} }
}
// Fallback: Look for any Claude response pattern in the last 20 lines
if (responseLines.length === 0) {
console.log(`[DEBUG] No response found after user input, trying fallback method`);
const recentLines = lines.slice(-20);
// Stop capturing response when we hit another prompt or box boundary for (let i = 0; i < recentLines.length; i++) {
if (inResponse && (line.startsWith('╭') || line.startsWith('│ > ') || line.includes('? for shortcuts'))) { const line = recentLines[i].trim();
inResponse = false;
if (line.startsWith('⏺ ') ||
(line.length > 10 && !line.startsWith('> ') && !line.includes('? for shortcuts'))) {
responseLines.push(line.startsWith('⏺ ') ? line.substring(2).trim() : line);
console.log(`[DEBUG] Fallback found response line: ${line}`);
}
} }
} }
// Join response lines and clean up // Join response lines and clean up
claudeResponse = responseLines.join('\n').trim(); claudeResponse = responseLines.join('\n').trim();
// Remove box characters but preserve formatting // Remove box characters but preserve formatting
claudeResponse = claudeResponse claudeResponse = claudeResponse
.replace(/[╭╰]/g, '') .replace(/[╭╰]/g, '')
.replace(/^\s*│\s*/gm, '') .replace(/^\s*│\s*/gm, '')
// Don't collapse multiple spaces - preserve code formatting .replace(/│\s*$/gm, '')
// .replace(/\s+/g, ' ')
.trim(); .trim();
// Don't limit response length - we want the full response console.log(`[DEBUG] Final extraction result:`);
// if (claudeResponse.length > 500) { console.log(`[DEBUG] User Question: "${userQuestion}"`);
// claudeResponse = claudeResponse.substring(0, 497) + '...'; console.log(`[DEBUG] Claude Response: "${claudeResponse.substring(0, 100)}${claudeResponse.length > 100 ? '...' : ''}"`);
// } console.log(`[DEBUG] Response lines count: ${responseLines.length}`);
// If we didn't find a question in the standard format, look for any recent text input
if (!userQuestion) {
for (let i = lines.length - 1; i >= 0; i--) {
const line = lines[i].trim();
if (line.startsWith('> ') && line.length > 2) {
userQuestion = line.substring(2).trim();
break;
}
}
}
return { return {
userQuestion: userQuestion || 'No user input', userQuestion: userQuestion || 'No user input',
claudeResponse: claudeResponse || 'No Claude response' claudeResponse: claudeResponse || 'No Claude response'

22
test-extraction-fix.js Normal file
View File

@ -0,0 +1,22 @@
#!/usr/bin/env node
/**
* Test script for extractConversation function fix
* Tests the improved response detection logic
*/
const TmuxMonitor = require('./src/utils/tmux-monitor');
// Create test tmux buffer content that mimics actual Claude Code output
const testBuffer1 = `
Welcome to Claude Code
? for shortcuts
> what does this project do?
I'll help you understand what this project does. Let me analyze the codebase structure first.
<function_calls>
<invoke name="Read">
<parameter name="file_path">/path/to/file.js

View File

@ -31,4 +31,4 @@ async function testInjection() {
} }
} }
testInjection().catch(console.error); < /dev/null testInjection().catch(console.error);