get_stack_trace
Retrieve the current call stack trace from a debugging session to identify execution flow and locate errors in Python, JavaScript, or Rust programs.
Instructions
Get stack trace
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| sessionId | Yes | ||
| includeInternals | No | Include internal/framework frames (e.g., Node.js internals). Default: false for cleaner output. |
Implementation Reference
- src/server.ts:480-481 (schema)Schema definition for the 'get_stack_trace' tool including input parameters: sessionId (required string) and includeInternals (optional boolean). Returned by list_tools request.{ name: 'get_stack_trace', description: 'Get stack trace', inputSchema: { type: 'object', properties: { sessionId: { type: 'string' }, includeInternals: { type: 'boolean', description: 'Include internal/framework frames (e.g., Node.js internals). Default: false for cleaner output.' } }, required: ['sessionId'] } }, { name: 'get_scopes', description: 'Get scopes for a stack frame', inputSchema: { type: 'object', properties: { sessionId: { type: 'string' }, frameId: { type: 'number', description: "The ID of the stack frame from a stackTrace response" } }, required: ['sessionId', 'frameId'] } },
- src/server.ts:831-852 (handler)Primary MCP tool handler for 'get_stack_trace'. Validates sessionId, delegates to this.getStackTrace(), formats JSON response with stackFrames, handles session/proxy errors gracefully.case 'get_stack_trace': { if (!args.sessionId) { throw new McpError(McpErrorCode.InvalidParams, 'Missing required sessionId'); } try { // Default to false for cleaner output const includeInternals = args.includeInternals ?? false; const stackFrames = await this.getStackTrace(args.sessionId, includeInternals); result = { content: [{ type: 'text', text: JSON.stringify({ success: true, stackFrames, count: stackFrames.length, includeInternals }) }] }; } catch (error) { // Handle validation errors specifically if (error instanceof SessionTerminatedError || error instanceof SessionNotFoundError || error instanceof ProxyNotRunningError) { result = { content: [{ type: 'text', text: JSON.stringify({ success: false, error: error.message }) }] }; } else { // Re-throw unexpected errors throw error; } } break;
- src/server.ts:290-298 (helper)Helper method on DebugMcpServer that validates session, determines current threadId, and delegates to SessionManager.getStackTrace.public async getStackTrace(sessionId: string, includeInternals: boolean = false): Promise<StackFrame[]> { this.validateSession(sessionId); const session = this.sessionManager.getSession(sessionId); const currentThreadId = session?.proxyManager?.getCurrentThreadId(); if (!session || !session.proxyManager || typeof currentThreadId !== 'number') { throw new ProxyNotRunningError(sessionId || 'unknown', 'get stack trace'); } return this.sessionManager.getStackTrace(sessionId, currentThreadId, includeInternals); }
- Core implementation of stack trace retrieval. Sends DAP 'stackTrace' request to proxy, parses stackFrames, applies language-specific filtering based on includeInternals flag, returns StackFrame[] or empty on error/not paused.async getStackTrace(sessionId: string, threadId?: number, includeInternals: boolean = false): Promise<StackFrame[]> { const session = this._getSessionById(sessionId); const currentThreadId = session.proxyManager?.getCurrentThreadId(); this.logger.info(`[SM getStackTrace ${sessionId}] Entered. Requested threadId: ${threadId}, Current state: ${session.state}, Actual currentThreadId: ${currentThreadId}, includeInternals: ${includeInternals}`); if (!session.proxyManager || !session.proxyManager.isRunning()) { this.logger.warn(`[SM getStackTrace ${sessionId}] No active proxy.`); return []; } if (session.state !== SessionState.PAUSED) { this.logger.warn(`[SM getStackTrace ${sessionId}] Session not paused. State: ${session.state}.`); return []; } const currentThreadForRequest = threadId || currentThreadId; if (typeof currentThreadForRequest !== 'number') { this.logger.warn(`[SM getStackTrace ${sessionId}] No effective thread ID to use.`); return []; } try { this.logger.info(`[SM getStackTrace ${sessionId}] Sending DAP 'stackTrace' for threadId ${currentThreadForRequest}.`); const response = await session.proxyManager.sendDapRequest<DebugProtocol.StackTraceResponse>('stackTrace', { threadId: currentThreadForRequest }); this.logger.info(`[SM getStackTrace ${sessionId}] DAP 'stackTrace' response received. Body:`, response?.body); if (response && response.body && response.body.stackFrames) { let frames: StackFrame[] = response.body.stackFrames.map((sf: DebugProtocol.StackFrame) => ({ id: sf.id, name: sf.name, file: sf.source?.path || sf.source?.name || "<unknown_source>", line: sf.line, column: sf.column })); // Apply filtering using the language's policy const policy = this.selectPolicy(session.language); if (policy.filterStackFrames) { this.logger.info(`[SM getStackTrace ${sessionId}] Applying stack frame filtering for ${session.language}. Original count: ${frames.length}`); frames = policy.filterStackFrames(frames, includeInternals); this.logger.info(`[SM getStackTrace ${sessionId}] After filtering: ${frames.length} frames`); } this.logger.info(`[SM getStackTrace ${sessionId}] Parsed stack frames (top 3):`, frames.slice(0,3).map(f => ({name:f.name, file:f.file, line:f.line}))); return frames; } this.logger.warn(`[SM getStackTrace ${sessionId}] No stackFrames in response body. Response:`, response); return []; } catch (error) { this.logger.error(`[SM getStackTrace ${sessionId}] Error getting stack trace:`, error); return []; } }