{"record":{"id":"4c6ffcec8b59c7f8","repo":"Kuberwastaken/claurst","slug":"connection-closed-while-awaiting-response-to","errorCode":null,"errorMessage":"connection closed while awaiting response to '{}'","messagePattern":"connection closed while awaiting response to '(.+?)'","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src-rust/crates/acp/src/connection.rs","lineNumber":143,"sourceCode":"        let params_value = serde_json::to_value(params)?;\n        let msg = serde_json::json!({\n            \"jsonrpc\": JSONRPC_VERSION,\n            \"id\": raw_id,\n            \"method\": method,\n            \"params\": params_value,\n        });\n        if let Err(e) = self.write_line(&msg).await {\n            self.pending.remove(&id_key);\n            return Err(e);\n        }\n\n        match rx.await {\n            Ok(Ok(value)) => {\n                let typed: R = serde_json::from_value(value)?;\n                Ok(Ok(typed))\n            }\n            Ok(Err(err)) => Ok(Err(err)),\n            Err(_) => Err(anyhow::anyhow!(\n                \"connection closed while awaiting response to '{}'\",\n                method\n            )),\n        }\n    }\n\n    async fn write_line(self: &Arc<Self>, value: &Value) -> anyhow::Result<()> {\n        let mut buf = serde_json::to_vec(value)?;\n        buf.push(b'\\n');\n        let mut w = self.writer.lock().await;\n        w.write_all(&buf).await?;\n        w.flush().await?;\n        trace!(bytes = buf.len(), \"ACP wire send\");\n        Ok(())\n    }\n\n    /// Look up and resolve a pending outbound request when a response arrives.\n    fn complete_pending(&self, id: &acp::RequestId, payload: Result<Value, acp::Error>) {","sourceCodeStart":125,"sourceCodeEnd":161,"githubUrl":"https://github.com/Kuberwastaken/claurst/blob/b0637c97ec34144387cbf2f74f65df6d16a6cef1/src-rust/crates/acp/src/connection.rs#L125-L161","documentation":"This error is thrown by the ACP connection's request/response correlator when the channel on which a pending response would arrive is dropped — i.e. the connection task shut down (or the connection was closed) before any response to the outstanding request arrived. The library uses a oneshot channel per in-flight request; `Err(_)` from `rx.await` means the sender half was dropped, so the response can never arrive.","triggerScenarios":"Calling `connection.send_request(method, ...)` and the connection is closed/aborted while the request is still in flight: remote peer disconnected, the reader loop exited, or the connection object was dropped/shut down mid-request.","commonSituations":"An ACP agent/subprocess crashes or exits while the client awaits a tool or session response; a network drop between IDE and agent; shutting down the connection on timeout without cancelling in-flight requests; server restart during an active session.","solutions":["Check that the ACP peer process is still running and inspect its stderr/logs for a crash or panic just before the error.","Add a response timeout and reconnect logic: treat this error as 'connection lost', re-establish the connection, and resend the request.","Ensure your code keeps the connection (and its background reader task) alive for the duration of awaited requests — do not drop the transport while requests are pending.","Verify protocol/version compatibility: a peer that closes the socket on an unsupported method will surface as this error."],"exampleFix":"// before\nlet resp = connection.send_request(\"session/prompt\", params).await?;\n// after\nlet resp = match connection.send_request(\"session/prompt\", params).await {\n    Ok(r) => r,\n    Err(e) if e.to_string().contains(\"connection closed\") => {\n        connection = reconnect().await?; // re-establish and retry once\n        connection.send_request(\"session/prompt\", params).await??\n    }\n    Err(e) => return Err(e.into()),\n};","handlingStrategy":"try-catch","validationCode":"// Rust: check the connection is open before sending\nif !connection.is_open() {\n    connection = reconnect().await?;\n}","typeGuard":null,"tryCatchPattern":"// match on the send_request Result and treat 'connection closed' as reconnectable\nmatch connection.send_request(method, params).await {\n    Ok(Ok(v)) => Ok(v),\n    Ok(Err(e)) => Err(e),\n    Err(e) if e.to_string().contains(\"connection closed\") => reconnect_and_retry().await,\n    Err(e) => Err(e),\n}","preventionTips":["Keep the connection/transport alive while requests are awaited; scope lifetimes accordingly.","Implement a reconnect-with-retry wrapper around send_request.","Monitor peer process health (exit events) to close sessions cleanly instead of letting awaits fail.","Add a per-request timeout so hangs surface as timeouts, not silent closes."],"tags":["network","acp","connection-closed","async"],"backgroundTag":"connection-refused","analyzedSha":"b0637c97ec34144387cbf2f74f65df6d16a6cef1","analyzedAt":"2026-09-10T00:24:58.650Z","contentChangedAt":"2026-09-10T00:24:58.650Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}