{"record":{"id":"4f8be526e232b246","repo":"xpipe-io/xpipe","slug":"failure-getthrowable","errorCode":null,"errorMessage":"failure.getThrowable()","messagePattern":"failure\\.getThrowable\\(\\)","errorType":"exception","errorClass":"BeaconServerException","httpStatus":null,"severity":"error","filePath":"app/src/main/java/io/xpipe/app/terminal/TerminalLaunchRequest.java","lineNumber":67,"sourceCode":"        this.workingDirectory = workingDirectory;\n        this.shellPid = -1;\n    }\n\n    public Path waitForCompletion() throws BeaconServerException {\n        while (true) {\n            if (latch.getCount() > 0) {\n                ThreadHelper.sleep(10);\n                continue;\n            }\n\n            if (getResult() == null) {\n                throw ErrorEventFactory.expected(new BeaconServerException(\"Launch request aborted\"));\n            }\n\n            var r = getResult();\n            if (r instanceof TerminalLaunchResult.ResultFailure failure) {\n                var t = failure.getThrowable();\n                throw new BeaconServerException(t);\n            }\n\n            return ((TerminalLaunchResult.ResultSuccess) r).getTargetScript();\n        }\n    }\n\n    public void setupRequestAsync() {\n        if (latch == null || latch.getCount() == 0) {\n            latch = new CountDownLatch(1);\n        }\n        ThreadHelper.runAsync(() -> {\n            setupRequest();\n            latch.countDown();\n        });\n    }\n\n    public void abort() {\n        latch.countDown();","sourceCodeStart":49,"sourceCodeEnd":85,"githubUrl":"https://github.com/xpipe-io/xpipe/blob/d85ca821baa46092a320ebb13546d7240adb74f8/app/src/main/java/io/xpipe/app/terminal/TerminalLaunchRequest.java#L49-L85","documentation":"In TerminalLaunchRequest.waitForCompletion(), when the terminal launch finishes with a ResultFailure, the underlying throwable is extracted and rethrown wrapped in a BeaconServerException. This propagates the actual cause of a failed terminal launch (raised on the beacon/server side) back to the caller of sshLaunchExchange/waitExchange instead of silently swallowing it.","triggerScenarios":"A terminal launch request registered with TerminalLauncherManager completes with TerminalLaunchResult.ResultFailure (e.g. the spawned shell or target script failed), and the caller invokes waitForCompletion() (via sshLaunchExchange or waitExchange).","commonSituations":"Target script execution error on the remote/local terminal; shell exited before handshake; launch aborted on the server side; permission or command-not-found errors during terminal startup surfaced through the beacon protocol.","solutions":["Inspect the cause (failure.getThrowable()) in the BeaconServerException to find the real launch failure","Fix the underlying terminal launch problem (script path, shell command, permissions)","Re-run the launch and ensure the request completes with ResultSuccess","Check that the target script content is valid for the target shell"],"exampleFix":"// before\ndoTerminalLaunch(script); // may complete as ResultFailure\n// after\ntry {\n    doTerminalLaunch(script);\n} catch (BeaconServerException e) {\n    // e.getCause() is the original launch throwable; fix and retry\n    log.error(\"Terminal launch failed\", e.getCause());\n}","handlingStrategy":"try-catch","validationCode":"// check result state before unwrapping\nvar r = request.getResult();\nboolean failed = r instanceof TerminalLaunchResult.ResultFailure;\n","typeGuard":"if (r instanceof TerminalLaunchResult.ResultFailure failure) { /* handle failure.getThrowable() */ }","tryCatchPattern":"try {\n    request.waitForCompletion();\n} catch (BeaconServerException e) {\n    Throwable cause = e.getCause(); // original terminal launch failure\n    handleLaunchFailure(cause);\n}","preventionTips":["Log the cause chain of BeaconServerException, not just its message","Validate target scripts and shell commands before launching","Keep terminal windows open until the launch handshake completes","Monitor beacon-side logs for the original failure"],"tags":["terminal","beacon","launch-failure","wrapped-exception"],"backgroundTag":"api-error-response","analyzedSha":"d85ca821baa46092a320ebb13546d7240adb74f8","analyzedAt":"2026-09-06T14:30:08.251Z","contentChangedAt":"2026-09-06T14:30:08.251Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}