{"record":{"id":"ed38d2c356921616","repo":"alibaba/arthas","slug":"timeout-waiting-for-response-to-request-for-tas","errorCode":null,"errorMessage":"Timeout waiting for response to request {} for task {}","messagePattern":"Timeout waiting for response to request (.+?) for task (.+?)","errorType":"exception","errorClass":"TimeoutException","httpStatus":null,"severity":"error","filePath":"arthas-mcp-server/src/main/java/com/taobao/arthas/mcp/server/task/InMemoryTaskMessageQueue.java","lineNumber":116,"sourceCode":"                        if (requestId.equals(response.requestId())) {\n                            queue.remove(response);\n                            logger.debug(\"waitForResponse: Found response for request {} in task {}\",\n                                    requestId, taskId);\n                            return response;\n                        }\n                    }\n                }\n                try {\n                    Thread.sleep(pollInterval);\n                } catch (InterruptedException e) {\n                    Thread.currentThread().interrupt();\n                    throw new CompletionException(\"Interrupted while waiting for response\", e);\n                }\n            }\n\n            logger.warn(\"waitForResponse: Timeout waiting for response to request {} for task {}\",\n                    requestId, taskId);\n            throw new CompletionException(new TimeoutException(\n                    \"Timeout waiting for response to request \" + requestId + \" for task \" + taskId));\n        });\n    }\n\n    @Override\n    public CompletableFuture<Void> clearTask(String taskId) {\n        return CompletableFuture.runAsync(() -> {\n            ConcurrentLinkedQueue<QueuedMessage> actionableQueue = actionableQueues.remove(taskId);\n            ConcurrentLinkedQueue<QueuedMessage.Response> responseQueue = responseQueues.remove(taskId);\n            int totalCleared = 0;\n            if (actionableQueue != null) totalCleared += actionableQueue.size();\n            if (responseQueue != null) totalCleared += responseQueue.size();\n            if (totalCleared > 0) {\n                logger.debug(\"Cleared {} messages for task {}\", totalCleared, taskId);\n            }\n        });\n    }\n","sourceCodeStart":98,"sourceCodeEnd":134,"githubUrl":"https://github.com/alibaba/arthas/blob/21cf2e9ba52b305290be7223b980ff504bb9cb5b/arthas-mcp-server/src/main/java/com/taobao/arthas/mcp/server/task/InMemoryTaskMessageQueue.java#L98-L134","documentation":"InMemoryTaskMessageQueue.waitForResponse polls a per-task response queue (polling on an interval) for a specific requestId. If no matching Response object lands in responseQueues[taskId] before the deadline elapses, the CompletableFuture completes exceptionally with a CompletionException wrapping a TimeoutException. This is the MCP server's mechanism for correlating an asynchronous tool request with its reply from the task consumer thread.","triggerScenarios":"Calling waitForResponse(requestId, taskId, timeout) when the task's consumer thread is not draining actionableQueues[taskId], when the producer enqueues a Response under a different requestId, when clearTask(taskId) ran and removed responseQueues[taskId] mid-wait, or when the target task simply never produces a reply within the configured timeout.","commonSituations":"Target JVM/Arthas session is busy or hung and cannot service the request; the MCP transport disconnects after the request but before the response; requestId correlation is broken by a buggy tool implementation; the configured timeout is too short for a heavy operation (e.g. heap dump, large trace); a race where clearTask is invoked concurrently with an outstanding request.","solutions":["Verify the task consumer is still alive and draining the actionable queue for that taskId.","Increase the timeout passed to waitForResponse for long-running operations (heap dump, profiler).","Ensure no concurrent clearTask(taskId) is cancelling the task while a response is pending.","Check that the response is enqueued with the exact same requestId used in the request (correlation key match).","If the target process is genuinely unresponsive, restart the Arthas session and reissue the request."],"exampleFix":"// before\nqueue.waitForResponse(reqId, taskId, Duration.ofSeconds(5));\n\n// after - size the timeout to the operation's real cost\nlong secs = isHeavyOp ? 120 : 5;\nqueue.waitForResponse(reqId, taskId, Duration.ofSeconds(secs));","handlingStrategy":"try-catch","validationCode":"long deadline = System.nanoTime() + timeout.toNanos();\nif (!queue.hasLiveConsumer(taskId)) {\n    // consumer missing; do not bother waiting\n    return;\n}","typeGuard":null,"tryCatchPattern":"try {\n    queue.waitForResponse(reqId, taskId, timeout).join();\n} catch (CompletionException ce) {\n    if (ce.getCause() instanceof TimeoutException) {\n        logger.warn(\"response timeout for task {} req {}\", taskId, reqId);\n        // optionally retry once or fall back\n    } else {\n        throw ce;\n    }\n}","preventionTips":["Size the timeout to the real cost of the operation (heap dumps/profiling need minutes).","Avoid calling clearTask while a waitForResponse is outstanding for that taskId.","Log requestId correlation at enqueue and dequeue to catch mismatches early.","Health-check the task consumer thread and restart dead consumers."],"tags":["concurrency","timeout","mcp","task-queue","async"],"backgroundTag":null,"analyzedSha":"21cf2e9ba52b305290be7223b980ff504bb9cb5b","analyzedAt":"2026-08-14T00:57:07.243Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}